import { apiFetch, type ApiSettings, type DeltaDeletedItem } from "@govoplan/core-webui"; export type AuditAdminItem = { id: string; scope: "tenant" | "system"; tenant_id?: string | null; actor_email?: string | null; action: string; object_type?: string | null; object_id?: string | null; details: Record; created_at: string; }; export type AuditSortBy = "time" | "actor" | "action" | "object" | "tenant"; export type AuditQueryOptions = { tenantId?: string | null; allTenants?: boolean; scope?: "tenant" | "system"; limit?: number; offset?: number; page?: number; pageSize?: number; cursor?: string | null; sortBy?: AuditSortBy; sortDirection?: "asc" | "desc"; filters?: Partial>; }; export type AuditAdminListResponse = { items: AuditAdminItem[]; total: number; page: number; page_size: number; pages: number; cursor?: string | null; next_cursor?: string | null; }; export type AuditAdminDeltaResponse = AuditAdminListResponse & { deleted: DeltaDeletedItem[]; watermark?: string | null; has_more: boolean; full: boolean; }; export type EvidenceBundleExportRequest = { scope: "tenant" | "system" | "all"; tenant_id?: string | null; record_ids?: string[]; max_records?: number; sign?: boolean; }; export type EvidenceBundleResponse = { id: string; scope: "tenant" | "system" | "all"; tenant_id?: string | null; status: "pending" | "ready" | "failed"; bundle_sha256?: string | null; record_count: number; reference_count: number; generated_at?: string | null; download_url?: string | null; }; export type EvidenceBundleDownloadResponse = { bundle: Record; }; function auditQuery(options: AuditQueryOptions & { since?: string | null } = {}): string { const params = new URLSearchParams(); if (options.tenantId) params.set("tenant_id", options.tenantId); if (options.allTenants) params.set("all_tenants", "true"); if (options.scope) params.set("scope", options.scope); if (options.limit) params.set("limit", String(options.limit)); if (options.offset) params.set("offset", String(options.offset)); if (options.page) params.set("page", String(options.page)); if (options.pageSize) params.set("page_size", String(options.pageSize)); if (options.cursor) params.set("cursor", options.cursor); if (options.sortBy) params.set("sort_by", options.sortBy); if (options.sortDirection) params.set("sort_direction", options.sortDirection); if (options.since) params.set("since", options.since); for (const [column, value] of Object.entries(options.filters ?? {})) { if (value?.trim()) params.set(`filter_${column}`, value); } const suffix = params.toString(); return suffix ? `?${suffix}` : ""; } export function fetchAdminAudit(settings: ApiSettings, options: AuditQueryOptions = {}): Promise { return apiFetch(settings, `/api/v1/admin/audit${auditQuery(options)}`); } export function fetchAdminAuditDelta(settings: ApiSettings, options: AuditQueryOptions & { since?: string | null } = {}): Promise { return apiFetch(settings, `/api/v1/admin/audit/delta${auditQuery(options)}`); } export function exportAuditEvidenceBundle( settings: ApiSettings, payload: EvidenceBundleExportRequest ): Promise { return apiFetch(settings, "/api/v1/admin/audit/evidence-bundles", { method: "POST", body: JSON.stringify(payload) }); } export function downloadAuditEvidenceBundle( settings: ApiSettings, bundleId: string ): Promise { return apiFetch(settings, `/api/v1/admin/audit/evidence-bundles/${bundleId}/download`); }