import { env } from "cloudflare:workers";
import { all, first } from "./db";
import type { DeliveryRecord, StoredDelivery } from "./webhook-log-do";
function log(repoId: string) {
return env.WEBHOOK_LOG.get(env.WEBHOOK_LOG.idFromName(repoId));
}
export function recordWebhookDelivery(repoId: string, delivery: StoredDelivery): Promise<void> {
return log(repoId).record(repoId, delivery);
}
/**
* Newest deliveries for a repo (or one hook). Rows written to D1 before the log moved to the per-repo
* object are merged in until the 30-day retention sweep removes them.
*/
export async function listWebhookDeliveries(
repoId: string,
hookId: string | null,
limit: number,
): Promise<DeliveryRecord[]> {
const [current, legacy] = await Promise.all([
log(repoId).list(hookId, limit),
all<DeliveryRecord>(
`SELECT d.id, d.webhook_id, d.event, d.status_code, d.error, d.duration_ms, d.attempt, d.created_at
FROM webhook_deliveries d JOIN webhooks w ON w.id = d.webhook_id
WHERE w.repo_id = ?1 AND (?2 IS NULL OR d.webhook_id = ?2) ORDER BY d.created_at DESC LIMIT ?3`,
repoId,
hookId,
limit,
),
]);
return [...current, ...legacy].sort((left, right) => right.created_at - left.created_at).slice(0, limit);
}
/** A delivery with its stored request body, only if it belongs to one of the repo's current hooks. */
export async function findWebhookDelivery(
repoId: string,
deliveryId: string,
hookId: string | null,