import type { IsoTime, NodeIdDTO, NodeStatusDTO, TerminalReasonDTO } from './common.js'; import type { DeclinedResultDTO } from './reports.js'; export type OutcomeKindDTO = 'result' | 'failure'; /** The terminal outcome fields carried by a node-list row. */ export interface NodeOutcomeSummaryDTO { kind: OutcomeKindDTO; reason: TerminalReasonDTO; settled_at: IsoTime; } /** Bounded diagnostics recorded for a failed node outcome. */ export interface NodeOutcomeDetailV1 { schema: 'crtr.node-outcome-detail/v1'; message?: string; fault_kind?: 'rate-limit' | 'overloaded' | 'connection' | 'auth' | 'protocol' | 'context-overflow' | 'other' | 'wedged' | 'model-not-found'; error_class?: 'rate_limit' | 'overloaded' | 'connection' | 'auth' | 'protocol' | 'context_overflow' | 'wedged' | 'model_not_found' | 'unknown'; respawn_failures?: number; deadline?: { deadline_at: string; elapsed_ms: number; }; /** Present only for reason `declined`: what the node gave `crtr push result --decline`. */ declined?: DeclinedResultDTO; truncated?: true; } interface NodeOutcomeBaseDTO { node_id: NodeIdDTO; revision: number; settled_at: IsoTime; /** Canonical final report basename; set for kind='result' and for a declined structured result (kind='failure', reason='declined'); else null. */ final_report: string | null; /** Absolute path of the canonical final report; null whenever `final_report` is. */ final_report_path: string | null; /** Parsed context/result.json when the node ran under --output-schema; else null. */ structured_result: unknown | null; /** Bounded diagnostics; null for kind='result'. */ detail: NodeOutcomeDetailV1 | null; } /** A settled outcome. Narrowing on `kind` then `reason` makes a declined * structured result (`failure`/`declined`) a case a consumer must handle: * only that case can carry `declined`; every other outcome has it null. A * declined outcome latched before the decline block was recorded on the row * (or reconstructed by the outcome-column backfill from `terminal_reason` * alone) carries null there — the decline happened, its reason/code/retryable * triple was never stored. */ export type NodeOutcomeDTO = (NodeOutcomeBaseDTO & { kind: 'result'; reason: TerminalReasonDTO; declined: null; }) | (NodeOutcomeBaseDTO & { kind: 'failure'; reason: 'declined'; declined: DeclinedResultDTO | null; }) | (NodeOutcomeBaseDTO & { kind: 'failure'; reason: Exclude; declined: null; }); export interface NodeOutcomeResponseDTO { node_id: NodeIdDTO; state: 'pending' | 'settled'; outcome: NodeOutcomeDTO | null; node_status: NodeStatusDTO; deadline_at: IsoTime | null; } export interface RegisterOutcomeDeliveryRequest { /** A name declared in the humanActions map of scope config. */ action: string; /** Opaque, frozen at registration, echoed verbatim in the document. */ payload?: unknown; } export type OutcomeDeliveryStateDTO = 'armed' | 'pending' | 'running' | 'accepted' | 'permanent_failed'; export interface OutcomeDeliveryDTO { node_id: NodeIdDTO; state: OutcomeDeliveryStateDTO; action: string; attempt: number; /** ISO-8601 time of the next retry, or null before the row is scheduled. */ next_attempt_at: IsoTime | null; accepted_at: IsoTime | null; permanent_failed_at: IsoTime | null; last_failure: { kind: string; exit_code?: number; signal?: string; message?: string; } | null; created_at: IsoTime; updated_at: IsoTime; } export {};