export interface SpoolEvent { eventId: string; type: 'verdict'; decision: 'allow' | 'block' | 'approval' | 'warn' | 'mask'; toolName?: string; operation?: string; reason?: string; ruleId?: string; category?: string; categoryId?: string; itemId?: string; severity?: 'critical' | 'high' | 'medium' | 'low'; source?: 'builtin' | 'custom' | 'taint' | 'backend'; evidence?: string; explanation?: string; policyHash?: string; /** True when this decision was enforced locally while the backend was unreachable. */ offlineEnforced?: boolean; /** * Wall time the developer actually waited for this verdict, in ms — measured * from the moment the hook process started to the moment the decision was * spooled. Passive: computed from timestamps already taken on the hot path * (see markVerdictTiming), never an extra probe, timer, or process. */ latencyMs?: number; /** Which path produced the verdict (see VerdictPath). */ verdictPath?: VerdictPath; occurredAt: string; } /** * How a verdict was produced — the difference between a healthy machine and a * degraded one: * - `ipc` resident daemon answered the thin client (the fast path) * - `local` full local evaluation in the hook process (daemon down/busy) * - `gateway` resident MCP gateway decided in-process (its own fast path) * - `fail_open` the hook crashed and allowed by contract */ export type VerdictPath = 'ipc' | 'local' | 'fail_open' | 'gateway'; /** * Compact JSON of the command/path/query/args the agent attempted. The console * Details column renders this as labeled Command / Query / URL / File / Args * rows. Truncated to 500 chars so it survives backend sanitize(). * * Known keys are preferred. Other primitive args (action, selector, prompt, …) * are included so MCP tools that are not a shell/file still show what ran. */ export declare function evidenceFromToolArgs(toolArgs: Record | undefined): string | undefined; interface VerdictTiming { startedAt: number; path: VerdictPath; /** Tool args for this evaluation — stamps `evidence` onto every spooled event. */ toolArgs?: Record; } /** Run one hook evaluation with timing attached to everything it spools. */ export declare function markVerdictTiming(timing: VerdictTiming, fn: () => T): T; /** * Re-label the current evaluation (e.g. it ended in the fail-open handler). * Keeps the original start time so latency still covers the full wait. */ export declare function setVerdictPath(path: VerdictPath): void; /** Attach the current tool call's args so every spool in this evaluation carries the command. */ export declare function setVerdictToolArgs(toolArgs: Record): void; /** * Restart the current evaluation's clock. Used by the MCP gateway right after * the downstream tool returns: everything spooled from then on (response * scanning, masking, bookkeeping) must report OUR overhead, not the tool's own * runtime — a 30s build tool is not a 30s FullCourtDefense stall. */ export declare function restartVerdictTiming(): void; /** Append one decision to the spool. Never throws (telemetry must not break the hook). */ export declare function spoolEvent(event: Omit & Partial>): void; export interface FlushInput { apiUrl: string; shieldId: string; shieldKey?: string; /** Include a heartbeat in this flush (drives device liveness). */ heartbeat?: boolean; agentVersion?: string; /** Whether protection points still look intact (tamper signal). */ integrityOk?: boolean; /** Machine-readable reasons for partial protection, never prompt/tool content. */ integrityReasons?: string[]; integrityCheckedAt?: string; /** Set only by the resident process; distinguishes daemon liveness from hook flushes. */ daemon?: boolean; /** Windows Claude Desktop chat guard liveness (advisory prompt protection). */ desktopChatGuard?: boolean; /** EDR/AV products detected on this machine (Windows service probe). */ securityAgents?: string[]; /** Could powershell.exe/pwsh.exe be spawned at all? (from real DPAPI work, never a dedicated spawn) */ powershellSpawnOk?: boolean; /** Did the DPAPI-protected shield key actually decrypt? */ powershellDecryptOk?: boolean; /** PowerShell language mode (FullLanguage/ConstrainedLanguage/…) — captured on decrypt failures and self-tests. */ powershellLanguageMode?: string; /** Which source supplied the shield key on the last resolution (codes only — see config.ts ShieldKeySource). */ shieldKeySource?: string; /** Recent coded distress signals from the on-disk ledger (see distress.ts). */ distress?: Array<{ code: string; component: string; detail?: string; firstAt: string; lastAt: string; count: number; }>; /** Post-mortem of a previous daemon that died without a clean shutdown. */ lastCrash?: { version?: string; startedAt?: string; lastAliveAt?: string; detectedAt: string; detectedBy: 'daemon' | 'watchdog'; }; timeoutMs?: number; } /** Drain the spool to the backend in one batch (+ optional heartbeat). Returns accepted count. */ export declare function flushSpool(input: FlushInput): Promise<{ accepted: number; deduped: number; } | null>; /** * Opportunistically spawn a DETACHED flusher so the hot path (hook) never blocks * on network I/O. Throttled via a marker file. `immediate` bypasses the throttle * (used for critical blocks). The child reads creds from ~/.fullcourtdefense.yml. */ export declare function triggerFlush(immediate?: boolean): void; export {};