import { NextResponse } from "next/server"; import { prisma } from "@/lib/db"; import { getActiveAccountId } from "@/lib/account-context"; import { enqueueJob, findActiveJob } from "@/lib/jobs/runner"; import { scheduleBackgroundJob } from "@/lib/jobs/schedule"; import { runScanForAllActiveTopics } from "@/lib/services/scan"; export const maxDuration = 300; export async function POST(request: Request) { try { const body = await request.json().catch(() => ({})); const accountId = await getActiveAccountId(); const { topicId, useTags, selectedTags } = body as { topicId?: string; useTags?: boolean; selectedTags?: string[]; }; if (topicId) { const topic = await prisma.topic.findUnique({ where: { id: topicId } }); if (!topic || (accountId && topic.accountId !== accountId)) { return NextResponse.json({ error: "找不到主題" }, { status: 404 }); } const existing = await findActiveJob(topicId, "scan"); if (existing) { return NextResponse.json({ jobId: existing.id, status: existing.status, message: "已有海巡任務在背景執行中", }); } const job = await enqueueJob({ type: "scan", topicId, label: `${topic.label} · 標籤海巡`, payload: { topicId, useTags, selectedTags }, }); scheduleBackgroundJob(job.id); return NextResponse.json({ jobId: job.id, status: "pending", message: "已於背景執行,可自由切換頁面", }); } const scans = await runScanForAllActiveTopics(accountId); return NextResponse.json({ scans }); } catch (error) { const message = error instanceof Error ? error.message : "海巡失敗"; return NextResponse.json({ error: message }, { status: 500 }); } }