Squashed commit of the following:
commit 33c0ad7d14a85f22c57f943dab58610c13d2ac07
Author: Nicholas Koben Kao <[email protected]>
Date: Tue Jan 30 21:56:00 2024 -0800
revert custom form change
commit d2905ad045ad7856156e3647a81d642999352de7
Merge: 654423d e3a1d24
Author: Nicholas Koben Kao <[email protected]>
Date: Tue Jan 30 20:50:06 2024 -0800
merge schema
commit 654423d597e019a5ebf1ab6568c9942fcb9181c5
Author: Nicholas Koben Kao <[email protected]>
Date: Tue Jan 30 20:49:34 2024 -0800
merge confl.ict
commit 641724c11346319674fbb329e8e29b362117c242
Author: Nicholas Koben Kao <[email protected]>
Date: Tue Jan 30 20:47:34 2024 -0800
model reload on create
commit eb4dfe8e3f39a0a98eab0fcf1affe7096c12f33b
Author: Nicholas Koben Kao <[email protected]>
Date: Tue Jan 30 17:00:03 2024 -0800
delete models
commit 0bea9583fada102396c4e08fe6da971c94d404df
Author: Nicholas Koben Kao <[email protected]>
Date: Tue Jan 30 14:35:15 2024 -0800
deploy volume uploader to have timeouts only be modal related
This commit is contained in:
@@ -353,4 +353,4 @@
|
||||
"breakpoints": true
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,6 +7,13 @@ import { Checkbox } from "@/components/ui/checkbox";
|
||||
import { InsertModal } from "./InsertModal";
|
||||
import { Input } from "@/components/ui/input";
|
||||
import { ScrollArea } from "@/components/ui/scroll-area";
|
||||
import {
|
||||
DropdownMenu,
|
||||
DropdownMenuContent,
|
||||
DropdownMenuItem,
|
||||
DropdownMenuLabel,
|
||||
DropdownMenuTrigger,
|
||||
} from "@/components/ui/dropdown-menu";
|
||||
import {
|
||||
Table,
|
||||
TableBody,
|
||||
@@ -30,9 +37,9 @@ import {
|
||||
getSortedRowModel,
|
||||
useReactTable,
|
||||
} from "@tanstack/react-table";
|
||||
import { ArrowUpDown } from "lucide-react";
|
||||
import { ArrowUpDown, MoreHorizontal } from "lucide-react";
|
||||
import * as React from "react";
|
||||
import { addModel } from "@/server/curdModel";
|
||||
import { addModel, deleteModel } from "@/server/curdModel";
|
||||
import { downloadUrlModelSchema } from "@/server/addCivitaiModelSchema";
|
||||
import { modelEnumType } from "@/db/schema";
|
||||
|
||||
@@ -192,10 +199,16 @@ export const columns: ColumnDef<ModelItemList>[] = [
|
||||
lora: "green",
|
||||
embedding: "violet",
|
||||
vae: "teal",
|
||||
clip: "default",
|
||||
clip_vision: "default",
|
||||
configs: "default",
|
||||
controlnet: "default",
|
||||
upscale_models: "default",
|
||||
ipadapter: "default",
|
||||
};
|
||||
|
||||
function getBadgeColor(modelType: modelEnumType) {
|
||||
return model_type_map[modelType] || "default";
|
||||
return model_type_map[modelType]
|
||||
}
|
||||
|
||||
const color = getBadgeColor(row.original.model_type);
|
||||
@@ -225,35 +238,35 @@ export const columns: ColumnDef<ModelItemList>[] = [
|
||||
),
|
||||
},
|
||||
// TODO: deletion and editing for future sprint
|
||||
// {
|
||||
// id: "actions",
|
||||
// enableHiding: false,
|
||||
// cell: ({ row }) => {
|
||||
// const checkpoint = row.original;
|
||||
//
|
||||
// return (
|
||||
// <DropdownMenu>
|
||||
// <DropdownMenuTrigger asChild>
|
||||
// <Button variant="ghost" className="h-8 w-8 p-0">
|
||||
// <span className="sr-only">Open menu</span>
|
||||
// <MoreHorizontal className="h-4 w-4" />
|
||||
// </Button>
|
||||
// </DropdownMenuTrigger>
|
||||
// <DropdownMenuContent align="end">
|
||||
// <DropdownMenuLabel>Actions</DropdownMenuLabel>
|
||||
// <DropdownMenuItem
|
||||
// className="text-destructive"
|
||||
// onClick={() => {
|
||||
// deleteWorkflow(checkpoint.id);
|
||||
// }}
|
||||
// >
|
||||
// Delete Workflow
|
||||
// </DropdownMenuItem>
|
||||
// </DropdownMenuContent>
|
||||
// </DropdownMenu>
|
||||
// );
|
||||
// },
|
||||
// },
|
||||
{
|
||||
id: "actions",
|
||||
enableHiding: false,
|
||||
cell: ({ row }) => {
|
||||
const model = row.original;
|
||||
|
||||
return (
|
||||
<DropdownMenu>
|
||||
<DropdownMenuTrigger asChild>
|
||||
<Button variant="ghost" className="h-8 w-8 p-0">
|
||||
<span className="sr-only">Open menu</span>
|
||||
<MoreHorizontal className="h-4 w-4" />
|
||||
</Button>
|
||||
</DropdownMenuTrigger>
|
||||
<DropdownMenuContent align="end">
|
||||
<DropdownMenuLabel>Actions</DropdownMenuLabel>
|
||||
<DropdownMenuItem
|
||||
className="text-destructive"
|
||||
onClick={() => {
|
||||
deleteModel(model.id);
|
||||
}}
|
||||
>
|
||||
Delete Model
|
||||
</DropdownMenuItem>
|
||||
</DropdownMenuContent>
|
||||
</DropdownMenu>
|
||||
);
|
||||
},
|
||||
},
|
||||
];
|
||||
|
||||
export function ModelList({ data }: { data: ModelItemList[] }) {
|
||||
|
||||
+19
-6
@@ -7,10 +7,10 @@ import {
|
||||
jsonb,
|
||||
pgEnum,
|
||||
pgSchema,
|
||||
real,
|
||||
text,
|
||||
timestamp,
|
||||
uuid,
|
||||
real,
|
||||
} from "drizzle-orm/pg-core";
|
||||
import { createInsertSchema, createSelectSchema } from "drizzle-zod";
|
||||
import { TypeOf, z } from "zod";
|
||||
@@ -150,8 +150,9 @@ export const workflowRunsTable = dbSchema.table("workflow_runs", {
|
||||
onDelete: "set null",
|
||||
},
|
||||
),
|
||||
workflow_inputs:
|
||||
jsonb("workflow_inputs").$type<Record<string, string | number>>(),
|
||||
workflow_inputs: jsonb("workflow_inputs").$type<
|
||||
Record<string, string | number>
|
||||
>(),
|
||||
workflow_id: uuid("workflow_id")
|
||||
.notNull()
|
||||
.references(() => workflowTable.id, {
|
||||
@@ -298,8 +299,9 @@ export const deploymentsTable = dbSchema.table("deployments", {
|
||||
.references(() => machinesTable.id),
|
||||
share_slug: text("share_slug").unique(),
|
||||
description: text("description"),
|
||||
showcase_media:
|
||||
jsonb("showcase_media").$type<z.infer<typeof showcaseMedia>>(),
|
||||
showcase_media: jsonb("showcase_media").$type<
|
||||
z.infer<typeof showcaseMedia>
|
||||
>(),
|
||||
environment: deploymentEnvironment("environment").notNull(),
|
||||
created_at: timestamp("created_at").defaultNow().notNull(),
|
||||
updated_at: timestamp("updated_at").defaultNow().notNull(),
|
||||
@@ -389,7 +391,18 @@ export const modelUploadType = pgEnum("model_upload_type", [
|
||||
]);
|
||||
|
||||
// https://www.answeroverflow.com/m/1125106227387584552
|
||||
export const modelTypes = ["checkpoint", "lora", "embedding", "vae"] as const;
|
||||
export const modelTypes = [
|
||||
"checkpoint",
|
||||
"lora",
|
||||
"embedding",
|
||||
"vae",
|
||||
"clip",
|
||||
"clip_vision",
|
||||
"configs",
|
||||
"controlnet",
|
||||
"upscale_models",
|
||||
"ipadapter",
|
||||
] as const;
|
||||
export const modelType = pgEnum("model_type", modelTypes);
|
||||
export type modelEnumType = (typeof modelTypes)[number];
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@ import {
|
||||
import { withServerPromise } from "./withServerPromise";
|
||||
import { db } from "@/db/db";
|
||||
import type { z } from "zod";
|
||||
import { revalidatePath } from "next/cache";
|
||||
import { headers } from "next/headers";
|
||||
import { downloadUrlModelSchema } from "./addCivitaiModelSchema";
|
||||
import { and, eq, isNull } from "drizzle-orm";
|
||||
@@ -210,6 +211,47 @@ export const addModelDownloadUrl = withServerPromise(
|
||||
},
|
||||
);
|
||||
|
||||
export const deleteModel = withServerPromise(
|
||||
async (modelId: string) => {
|
||||
const model = await db.query.modelTable.findFirst({
|
||||
where: eq(modelTable.id, modelId),
|
||||
});
|
||||
|
||||
// If the model does not exist, throw an error or return a message
|
||||
if (!model) {
|
||||
throw new Error("Model not found");
|
||||
// Or return { error: "Model not found" }; if you prefer to handle it without throwing
|
||||
}
|
||||
|
||||
const volumes = await retrieveModelVolumes();
|
||||
if (
|
||||
model.status === "success" && !!model.folder_path && !!model.model_name
|
||||
) {
|
||||
const result = await fetch(
|
||||
`${process.env.MODAL_BUILDER_URL!}/delete-volume-model`,
|
||||
{
|
||||
method: "POST",
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
body: JSON.stringify({
|
||||
volume_name: volumes[0].volume_name,
|
||||
path: model.folder_path,
|
||||
file_name: model.model_name,
|
||||
}),
|
||||
},
|
||||
);
|
||||
if (!result.ok) {
|
||||
const error_log = await result.text();
|
||||
throw new Error(`Error: ${result.statusText} ${error_log}`);
|
||||
}
|
||||
}
|
||||
await db.delete(modelTable).where(eq(modelTable.id, modelId));
|
||||
revalidatePath("/storage");
|
||||
return { message: "Model Deleted" };
|
||||
},
|
||||
);
|
||||
|
||||
export const getCivitaiModelRes = async (civitaiUrl: string) => {
|
||||
const { url, modelVersionId } = getUrl(civitaiUrl);
|
||||
const civitaiModelRes = await fetch(url)
|
||||
@@ -301,8 +343,8 @@ export const addCivitaiModel = withServerPromise(
|
||||
model_name: selectedModelVersion.files[0].name,
|
||||
civitai_id: civitaiModelRes.id.toString(),
|
||||
civitai_version_id: selectedModelVersionId,
|
||||
civitai_url: data.url, // TODO: need to confirm
|
||||
civitai_download_url: selectedModelVersion.files[0].downloadUrl,
|
||||
civitai_url: data.url,
|
||||
civitai_download_url: selectedModelVersion.files[0].downloadUrl, // there is an issue when a model hoster might put multiple different types of files i.e. their training data.
|
||||
civitai_model_response: civitaiModelRes,
|
||||
user_volume_id: volumes[0].id,
|
||||
model_type,
|
||||
@@ -312,6 +354,7 @@ export const addCivitaiModel = withServerPromise(
|
||||
const b = a[0];
|
||||
|
||||
await uploadModel(data, b, volumes[0]);
|
||||
revalidatePath("/storage");
|
||||
},
|
||||
);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user