import { NextResponse } from 'next/server'
import { timingSafeEqual } from 'node:crypto'
import { db } from '@/lib/db'

// Called by the home-server wrapper script to report progress. The script
// authenticates with a shared secret over HTTPS — this is single-user infra,
// not a public webhook, so a static token is sufficient.

const STATUS_SET = new Set(['RUNNING', 'SUCCEEDED', 'FAILED'])

export async function POST(
  req: Request,
  { params }: { params: Promise<{ id: string }> },
) {
  if (!isAuthorized(req)) {
    return new NextResponse('Unauthorized', { status: 401 })
  }

  const { id } = await params
  if (!/^[0-9a-f-]{36}$/i.test(id)) {
    return new NextResponse('Bad id', { status: 400 })
  }

  let body: { status?: string; errorMessage?: string; logTail?: string }
  try {
    body = await req.json()
  } catch {
    return new NextResponse('Bad JSON', { status: 400 })
  }

  const status = body.status?.toUpperCase()
  if (!status || !STATUS_SET.has(status)) {
    return new NextResponse('Bad status', { status: 400 })
  }

  const now = new Date()
  const data: Record<string, unknown> = { status }
  if (status === 'RUNNING') data.runningAt = now
  if (status === 'SUCCEEDED' || status === 'FAILED') data.finishedAt = now
  if (typeof body.errorMessage === 'string') data.errorMessage = body.errorMessage.slice(0, 1000)
  if (typeof body.logTail === 'string') data.logTail = body.logTail.slice(0, 8000)

  try {
    await db.aIReviewSession.update({ where: { id }, data })
  } catch {
    return new NextResponse('Session not found', { status: 404 })
  }

  return NextResponse.json({ ok: true })
}

function isAuthorized(req: Request): boolean {
  const expected = process.env.IDENTIFY_CALLBACK_SECRET
  if (!expected) return false
  const header = req.headers.get('authorization') || ''
  const m = header.match(/^Bearer\s+(.+)$/i)
  if (!m) return false
  const provided = m[1]
  const a = Buffer.from(provided)
  const b = Buffer.from(expected)
  if (a.length !== b.length) return false
  return timingSafeEqual(a, b)
}
