Assign experiments and datasets to correct org
This commit is contained in:
@@ -15,6 +15,7 @@ import { useRouter } from "next/router";
|
||||
import { BsPlusSquare } from "react-icons/bs";
|
||||
import { api } from "~/utils/api";
|
||||
import { useHandledAsyncCallback } from "~/utils/hooks";
|
||||
import { useAppStore } from "~/state/store";
|
||||
|
||||
type DatasetData = {
|
||||
name: string;
|
||||
@@ -71,11 +72,12 @@ const CountLabel = ({ label, count }: { label: string; count: number }) => {
|
||||
|
||||
export const NewDatasetCard = () => {
|
||||
const router = useRouter();
|
||||
const selectedOrgId = useAppStore((s) => s.selectedOrgId);
|
||||
const createMutation = api.datasets.create.useMutation();
|
||||
const [createDataset, isLoading] = useHandledAsyncCallback(async () => {
|
||||
const newDataset = await createMutation.mutateAsync({ label: "New Dataset" });
|
||||
const newDataset = await createMutation.mutateAsync({ organizationId: selectedOrgId ?? "" });
|
||||
await router.push({ pathname: "/data/[id]", query: { id: newDataset.id } });
|
||||
}, [createMutation, router]);
|
||||
}, [createMutation, router, selectedOrgId]);
|
||||
|
||||
return (
|
||||
<AspectRatio ratio={1.2} w="full">
|
||||
|
||||
@@ -15,6 +15,7 @@ import { useRouter } from "next/router";
|
||||
import { BsPlusSquare } from "react-icons/bs";
|
||||
import { api } from "~/utils/api";
|
||||
import { useHandledAsyncCallback } from "~/utils/hooks";
|
||||
import { useAppStore } from "~/state/store";
|
||||
|
||||
type ExperimentData = {
|
||||
testScenarioCount: number;
|
||||
@@ -75,11 +76,17 @@ const CountLabel = ({ label, count }: { label: string; count: number }) => {
|
||||
|
||||
export const NewExperimentCard = () => {
|
||||
const router = useRouter();
|
||||
const selectedOrgId = useAppStore((s) => s.selectedOrgId);
|
||||
const createMutation = api.experiments.create.useMutation();
|
||||
const [createExperiment, isLoading] = useHandledAsyncCallback(async () => {
|
||||
const newExperiment = await createMutation.mutateAsync({ label: "New Experiment" });
|
||||
await router.push({ pathname: "/experiments/[id]", query: { id: newExperiment.id } });
|
||||
}, [createMutation, router]);
|
||||
const newExperiment = await createMutation.mutateAsync({
|
||||
organizationId: selectedOrgId ?? "",
|
||||
});
|
||||
await router.push({
|
||||
pathname: "/experiments/[id]",
|
||||
query: { id: newExperiment.id },
|
||||
});
|
||||
}, [createMutation, router, selectedOrgId]);
|
||||
|
||||
return (
|
||||
<AspectRatio ratio={1.2} w="full">
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
import { HStack, Flex, Text } from "@chakra-ui/react";
|
||||
import Link from "next/link";
|
||||
|
||||
import { useSelectedOrg } from "~/utils/hooks";
|
||||
|
||||
// Have to export only contents here instead of full BreadcrumbItem because Chakra doesn't
|
||||
// recognize a BreadcrumbItem exported with this component as a valid child of Breadcrumb.
|
||||
|
||||
export default function ProjectBreadcrumbContents() {
|
||||
export default function ProjectBreadcrumbContents({ orgName = "" }: { orgName?: string }) {
|
||||
const { data: selectedOrg } = useSelectedOrg();
|
||||
|
||||
orgName = orgName || selectedOrg?.name || "";
|
||||
|
||||
return (
|
||||
<Link href="/home">
|
||||
<HStack w="full">
|
||||
@@ -23,10 +23,10 @@ export default function ProjectBreadcrumbContents() {
|
||||
alignItems="center"
|
||||
justifyContent="center"
|
||||
>
|
||||
<Text>{selectedOrg?.name[0]?.toUpperCase()}</Text>
|
||||
<Text>{orgName[0]?.toUpperCase()}</Text>
|
||||
</Flex>
|
||||
<Text display={{ base: "none", md: "block" }} py={1}>
|
||||
{selectedOrg?.name}
|
||||
{orgName}
|
||||
</Text>
|
||||
</HStack>
|
||||
</Link>
|
||||
|
||||
@@ -60,7 +60,7 @@ export default function Dataset() {
|
||||
<PageHeaderContainer>
|
||||
<Breadcrumb>
|
||||
<BreadcrumbItem>
|
||||
<ProjectBreadcrumbContents />
|
||||
<ProjectBreadcrumbContents orgName={dataset.data?.organization?.name} />
|
||||
</BreadcrumbItem>
|
||||
<BreadcrumbItem>
|
||||
<Link href="/data">
|
||||
|
||||
@@ -110,7 +110,7 @@ export default function Experiment() {
|
||||
<PageHeaderContainer>
|
||||
<Breadcrumb>
|
||||
<BreadcrumbItem>
|
||||
<ProjectBreadcrumbContents />
|
||||
<ProjectBreadcrumbContents orgName={experiment.data?.organization?.name} />
|
||||
</BreadcrumbItem>
|
||||
<BreadcrumbItem>
|
||||
<Link href="/experiments">
|
||||
|
||||
@@ -3,11 +3,10 @@ import { createTRPCRouter, protectedProcedure, publicProcedure } from "~/server/
|
||||
import { prisma } from "~/server/db";
|
||||
import {
|
||||
requireCanModifyDataset,
|
||||
requireCanModifyOrganization,
|
||||
requireCanViewDataset,
|
||||
requireCanViewOrganization,
|
||||
requireNothing,
|
||||
} from "~/utils/accessControl";
|
||||
import userOrg from "~/server/utils/userOrg";
|
||||
|
||||
export const datasetsRouter = createTRPCRouter({
|
||||
list: protectedProcedure
|
||||
@@ -36,27 +35,27 @@ export const datasetsRouter = createTRPCRouter({
|
||||
await requireCanViewDataset(input.id, ctx);
|
||||
return await prisma.dataset.findFirstOrThrow({
|
||||
where: { id: input.id },
|
||||
include: {
|
||||
organization: true,
|
||||
},
|
||||
});
|
||||
}),
|
||||
|
||||
create: protectedProcedure.input(z.object({})).mutation(async ({ ctx }) => {
|
||||
// Anyone can create an experiment
|
||||
requireNothing(ctx);
|
||||
create: protectedProcedure
|
||||
.input(z.object({ organizationId: z.string() }))
|
||||
.mutation(async ({ input, ctx }) => {
|
||||
await requireCanModifyOrganization(input.organizationId, ctx);
|
||||
|
||||
const numDatasets = await prisma.dataset.count({
|
||||
where: {
|
||||
organization: {
|
||||
organizationUsers: {
|
||||
some: { userId: ctx.session.user.id },
|
||||
},
|
||||
},
|
||||
organizationId: input.organizationId,
|
||||
},
|
||||
});
|
||||
|
||||
return await prisma.dataset.create({
|
||||
data: {
|
||||
name: `Dataset ${numDatasets + 1}`,
|
||||
organizationId: (await userOrg(ctx.session.user.id)).id,
|
||||
organizationId: input.organizationId,
|
||||
},
|
||||
});
|
||||
}),
|
||||
|
||||
@@ -8,11 +8,10 @@ import { generateNewCell } from "~/server/utils/generateNewCell";
|
||||
import {
|
||||
canModifyExperiment,
|
||||
requireCanModifyExperiment,
|
||||
requireCanModifyOrganization,
|
||||
requireCanViewExperiment,
|
||||
requireCanViewOrganization,
|
||||
requireNothing,
|
||||
} from "~/utils/accessControl";
|
||||
import userOrg from "~/server/utils/userOrg";
|
||||
import generateTypes from "~/modelProviders/generateTypes";
|
||||
import { promptConstructorVersion } from "~/promptConstructor/version";
|
||||
|
||||
@@ -47,7 +46,7 @@ export const experimentsRouter = createTRPCRouter({
|
||||
list: protectedProcedure
|
||||
.input(z.object({ organizationId: z.string() }))
|
||||
.query(async ({ input, ctx }) => {
|
||||
await requireCanViewOrganization(input.organizationId, ctx)
|
||||
await requireCanViewOrganization(input.organizationId, ctx);
|
||||
|
||||
const experiments = await prisma.experiment.findMany({
|
||||
where: {
|
||||
@@ -90,6 +89,9 @@ export const experimentsRouter = createTRPCRouter({
|
||||
await requireCanViewExperiment(input.id, ctx);
|
||||
const experiment = await prisma.experiment.findFirstOrThrow({
|
||||
where: { id: input.id },
|
||||
include: {
|
||||
organization: true,
|
||||
},
|
||||
});
|
||||
|
||||
const canModify = ctx.session?.user.id
|
||||
@@ -105,8 +107,11 @@ export const experimentsRouter = createTRPCRouter({
|
||||
};
|
||||
}),
|
||||
|
||||
fork: protectedProcedure.input(z.object({ id: z.string() })).mutation(async ({ input, ctx }) => {
|
||||
fork: protectedProcedure
|
||||
.input(z.object({ id: z.string(), organizationId: z.string() }))
|
||||
.mutation(async ({ input, ctx }) => {
|
||||
await requireCanViewExperiment(input.id, ctx);
|
||||
await requireCanModifyOrganization(input.organizationId, ctx);
|
||||
|
||||
const [
|
||||
existingExp,
|
||||
@@ -259,7 +264,7 @@ export const experimentsRouter = createTRPCRouter({
|
||||
id: newExperimentId,
|
||||
sortIndex: maxSortIndex + 1,
|
||||
label: `${existingExp.label} (forked)`,
|
||||
organizationId: (await userOrg(ctx.session.user.id)).id,
|
||||
organizationId: input.organizationId,
|
||||
},
|
||||
}),
|
||||
prisma.promptVariant.createMany({
|
||||
@@ -288,11 +293,10 @@ export const experimentsRouter = createTRPCRouter({
|
||||
return newExperimentId;
|
||||
}),
|
||||
|
||||
create: protectedProcedure.input(z.object({})).mutation(async ({ ctx }) => {
|
||||
// Anyone can create an experiment
|
||||
requireNothing(ctx);
|
||||
|
||||
const organizationId = (await userOrg(ctx.session.user.id)).id;
|
||||
create: protectedProcedure
|
||||
.input(z.object({ organizationId: z.string() }))
|
||||
.mutation(async ({ input, ctx }) => {
|
||||
await requireCanModifyOrganization(input.organizationId, ctx);
|
||||
|
||||
const maxSortIndex =
|
||||
(
|
||||
@@ -300,7 +304,7 @@ export const experimentsRouter = createTRPCRouter({
|
||||
_max: {
|
||||
sortIndex: true,
|
||||
},
|
||||
where: { organizationId },
|
||||
where: { organizationId: input.organizationId },
|
||||
})
|
||||
)._max?.sortIndex ?? 0;
|
||||
|
||||
@@ -308,7 +312,7 @@ export const experimentsRouter = createTRPCRouter({
|
||||
data: {
|
||||
sortIndex: maxSortIndex + 1,
|
||||
label: `Experiment ${maxSortIndex + 1}`,
|
||||
organizationId,
|
||||
organizationId: input.organizationId,
|
||||
},
|
||||
});
|
||||
|
||||
|
||||
Reference in New Issue
Block a user