import { run } from "../db";
const DELIVERY_RETENTION_MS = 30 * 24 * 60 * 60_000;
const PRUNE_BATCH = 500;
/** Integrations whose repo or org no longer exists hold live credentials for nothing; remove them. */
async function pruneOrphanedIntegrations(): Promise<void> {
await run(
`DELETE FROM integrations WHERE id IN (
SELECT id FROM integrations WHERE scope_type = 'repo' AND scope_id NOT IN (SELECT id FROM repos) LIMIT ?)`,
PRUNE_BATCH,
);
await run(
`DELETE FROM integrations WHERE id IN (
SELECT id FROM integrations WHERE scope_type = 'org' AND scope_id NOT IN (SELECT id FROM accounts) LIMIT ?)`,
PRUNE_BATCH,
);
}
/** Integration delivery logs (inbound and outbound) are kept for 30 days, pruned in batches. */
async function pruneDeliveryLogs(now: number): Promise<void> {
const cutoff = now - DELIVERY_RETENTION_MS;
await run(
"DELETE FROM integration_deliveries WHERE id IN (SELECT id FROM integration_deliveries WHERE created_at < ? LIMIT ?)",
cutoff,
PRUNE_BATCH,
);
}
/** Legacy webhook deliveries live in their repository's RepoState, whose alarm expires them (housekeeping.ts). */
export const WEBHOOK_DELIVERY_RETENTION_MS = DELIVERY_RETENTION_MS;
/** Cron tail: orphaned integrations (INT-A25) and unbounded delivery logs (INT-A27). */
export async function pruneIntegrationLeftovers(now: number): Promise<void> {
await pruneOrphanedIntegrations();
await pruneDeliveryLogs(now);
}