import { z } from 'zod';
const cleanupPayloadSchema = z.object({
    platform: z.enum(['gitlab', 'github']),
    projectPath: z.string().min(1),
    mrNumber: z.number().int().positive(),
});
function buildLockKey(identity) {
    return `${identity.platform}:${identity.projectPath}:${identity.mrNumber}`;
}
export const worktreeOverviewRoutes = async (fastify, opts) => {
    const { worktreeGateway, presenter, schedulerControls, logger, detectDegradedWorktrees, forceCleanupLock, removeWorktreeForCleanup, } = opts;
    fastify.get('/api/worktrees', async (_request, reply) => {
        if (schedulerControls === null) {
            reply.code(503);
            return { error: 'scheduler-unavailable' };
        }
        const worktrees = await worktreeGateway.list();
        const healthReports = detectDegradedWorktrees ? await detectDegradedWorktrees(worktrees) : [];
        const viewModel = await presenter.present({
            worktrees,
            lastSweep: schedulerControls.getLastSweep(),
            nextSweepAt: schedulerControls.getNextSweepEta(),
            healthReports,
        });
        return viewModel;
    });
    fastify.post('/api/worktrees/sweep', async (_request, reply) => {
        if (schedulerControls === null) {
            reply.code(503);
            return { error: 'scheduler-unavailable' };
        }
        const result = await schedulerControls.runSweepNow();
        if (result.status === 'conflict') {
            reply.code(409);
            return { error: 'sweep-in-progress', startedAt: result.startedAt.toISOString() };
        }
        if (result.status === 'error') {
            logger.error({ reason: result.reason }, 'Manual worktree sweep failed');
            reply.code(500);
            return { error: 'sweep-failed' };
        }
        return {
            ranAt: result.summary.ranAt.toISOString(),
            removed: result.summary.removed,
            failures: result.summary.failures,
            scanned: result.summary.scanned,
        };
    });
    fastify.post('/api/worktrees/cleanup', async (request, reply) => {
        if (forceCleanupLock === undefined || removeWorktreeForCleanup === undefined) {
            reply.code(503);
            return { error: 'cleanup-unavailable' };
        }
        const parsed = cleanupPayloadSchema.safeParse(request.body);
        if (!parsed.success) {
            reply.code(400);
            return { error: 'invalid-payload' };
        }
        const identity = {
            platform: parsed.data.platform,
            projectPath: parsed.data.projectPath,
            mrNumber: parsed.data.mrNumber,
        };
        const lockKey = buildLockKey(identity);
        if (!forceCleanupLock.tryAcquire(lockKey)) {
            reply.code(409);
            return { error: 'cleanup-in-progress' };
        }
        try {
            const result = await removeWorktreeForCleanup(identity);
            if (result.status === 'failed') {
                logger.warn({ identity, warning: result.warning }, 'Force cleanup failed');
                reply.code(500);
                return { error: 'cleanup-failed', warning: result.warning };
            }
            logger.info({ identity, outcome: result.status }, 'Force cleanup completed');
            return { status: 'removed' };
        }
        catch (error) {
            const warning = error instanceof Error ? error.message : String(error);
            logger.warn({ identity, warning }, 'Force cleanup threw');
            reply.code(500);
            return { error: 'cleanup-failed', warning };
        }
        finally {
            forceCleanupLock.release(lockKey);
        }
    });
};
//# sourceMappingURL=worktreeOverview.routes.js.map