import { NextRequest, NextResponse } from "next/server"; import { eq } from "drizzle-orm"; import { db } from "@/lib/db"; import { imageArchiveTask } from "@/lib/db/schema"; // The SHA-256 URL is a capability, like the provider's signed image URL. It must be // readable by image nodes and reference-image providers without a session cookie. export async function GET(request: NextRequest, { params }: { params: Promise<{ key: string }> }) { const { key } = await params; if (!/^[a-f0-9]{64}$/.test(key)) return new NextResponse(null, { status: 404 }); const configured = process.env.NEXT_PUBLIC_APP_URL || process.env.AUTH_URL || process.env.NEXTAUTH_URL; const origin = configured ? new URL(configured).origin : `http://localhost:${process.env.PORT || "3000"}`; const sourceUrl = `${origin}/api/generated-image-preview/${key}`; const [task] = await db .select({ targetUrl: imageArchiveTask.targetUrl, metadata: imageArchiveTask.metadata }) .from(imageArchiveTask) .where(eq(imageArchiveTask.sourceUrl, sourceUrl)) .limit(1); if (task?.targetUrl) return NextResponse.redirect(task.targetUrl, 307); const inline = (task?.metadata as { inlineSource?: string } | null)?.inlineSource; const match = inline?.match(/^data:(image\/[a-z0-9.+-]+);base64,([a-z0-9+/=]+)$/i); if (!match) return new NextResponse(null, { status: 404 }); return new NextResponse(Buffer.from(match[2], "base64"), { headers: { "Content-Type": match[1], "Cache-Control": "private, no-store", "X-Content-Type-Options": "nosniff", "Content-Security-Policy": "default-src 'none'; sandbox", }, }); }