Spaces:
Sleeping
Sleeping
| import { z } from "zod"; | |
| import { protectedProcedure, router } from "../_core/trpc"; | |
| import { uploadCodeReference, getUserCodeReferences } from "../db"; | |
| import { storagePut, storageGet } from "../storage"; | |
| export const filesRouter = router({ | |
| upload: protectedProcedure | |
| .input( | |
| z.object({ | |
| filename: z.string().min(1), | |
| category: z.enum(["library", "exploit", "payload", "example", "utility"]), | |
| description: z.string().optional(), | |
| content: z.string(), | |
| tags: z.array(z.string()).optional(), | |
| }) | |
| ) | |
| .mutation(async ({ ctx, input }) => { | |
| try { | |
| // Upload to S3 | |
| const s3Key = `code-refs/${ctx.user.id}/${Date.now()}-${input.filename}`; | |
| const { url: s3Url } = await storagePut(s3Key, input.content, "text/plain"); | |
| // Save to database | |
| const result = await uploadCodeReference(ctx.user.id, { | |
| filename: input.filename, | |
| category: input.category, | |
| description: input.description, | |
| content: input.content.substring(0, 10000), // Store first 10k chars | |
| s3Key, | |
| s3Url, | |
| mimeType: "text/plain", | |
| fileSize: input.content.length, | |
| tags: input.tags, | |
| }); | |
| return { success: true, s3Url, fileId: (result as any).insertId }; | |
| } catch (error) { | |
| console.error("File upload error:", error); | |
| throw new Error("Failed to upload file"); | |
| } | |
| }), | |
| list: protectedProcedure | |
| .input(z.object({ category: z.string().optional() }).optional()) | |
| .query(async ({ ctx, input }) => { | |
| return await getUserCodeReferences(ctx.user.id, input?.category); | |
| }), | |
| getDownloadUrl: protectedProcedure | |
| .input(z.object({ s3Key: z.string() })) | |
| .query(async ({ input }) => { | |
| try { | |
| const { url } = await storageGet(input.s3Key); | |
| return { url }; | |
| } catch (error) { | |
| throw new Error("Failed to get download URL"); | |
| } | |
| }), | |
| }); | |