import { hasPermissions } from "#shared/auth.util"; import useDatabase from '~/composables/useDatabase'; import { explorerContentTable } from '~/db/schema'; import { project, type ProjectItem } from '~/schemas/project'; import { parsePath } from "#shared/general.utils"; import { eq, getTableColumns } from "drizzle-orm"; export default defineEventHandler(async (e) => { const { user } = await getUserSession(e); if(!user || !hasPermissions(user.permissions, ['admin', 'editor'])) { throw createError({ statusCode: 401, statusText: 'Unauthorized' }); } const body = await readValidatedBody(e, project.safeParse); if(!body.success) { throw body.error; } const items = buildOrder(body.data.items); const db = useDatabase(); const { content, ...cols } = getTableColumns(explorerContentTable); const full = db.select(cols).from(explorerContentTable).all(); for(let i = full.length - 1; i >= 0; i--) { if(items.find(e => (e.path === '' ? [e.parent, parsePath(e.name === '' ? e.title : e.name)].filter(e => !!e).join('/') : e.path) === full[i].path)) full.splice(i, 1); } db.transaction((tx) => { for(let i = 0; i < items.length; i++) { const item = items[i]; tx.insert(explorerContentTable).values({ path: item.path, owner: user.id, title: item.title, type: item.type, navigable: item.navigable, private: item.private, order: item.order, content: null, }).onConflictDoUpdate({ set: { path: [item.parent, parsePath(item.name === '' ? item.title : item.name)].filter(e => !!e).join('/'), title: item.title, type: item.type, navigable: item.navigable, private: item.private, order: item.order, }, target: explorerContentTable.path, }).run(); } for(let i = 0; i < full.length; i++) { tx.delete(explorerContentTable).where(eq(explorerContentTable.path, full[i].path)).run(); } }); }); function buildOrder(items: ProjectItem[]): ProjectItem[] { items.forEach((e, i) => { e.order = i; if(e.children) e.children = buildOrder(e.children); }); return items.flatMap(e => [e, ...(e.children ?? [])]); }