/** * Observation Resolver — PRI-446 (migrated from the plugin adapter) * * Unified source-kind resolution from RawObservation. * * Pure data mapping — no I/O, no plugin imports, no side effects. This module * replaces the scattered resolveSourceKindFrom* helpers that previously lived in * the plugin-side raw-observation-adapter.ts. The plugin file now re-exports * these symbols so existing callers and source-string characterization tests * keep working unchanged. * * Field precedence (highest to lowest): * 1. isManualEntry → owner_reported * 2. isGateBlock → rulehost_block * 3. isSubagentError → subagent_error * 4. isRateLimit → rate_limit / provider_failure * 5. toolName === 'pain' / 'skill:pain' → agent_on_owner_request / owner_reported * 6. isGfiTriggered → gfi_threshold * 7. failureSource → tool_failure / dispatch_error * 8. detectionSource → llm_paralysis / semantic / empathy_inferred / unknown * 9. Fallback → unknown * * ERR checklist: * - ERR-001: Source kind resolved from runtime values, no `as` casts. * - ERR-002: Every path returns a valid SourceKind (fallback to 'unknown'). * - EP-01: Runtime values validated before use. */ import type { SourceKind } from './types.js'; /** * Raw observation from a source adapter. * * This is the input to resolveSourceKind. It contains all possible * context fields that different sources may provide. The resolver * reads only the fields it needs based on the observation source. */ export interface RawObservation { /** When the observation was made (ISO timestamp) */ readonly observedAt: string; /** Workspace identifier */ readonly workspaceId?: string; /** Session identifier */ readonly sessionId?: string; /** Trace identifier for correlation */ readonly traceId?: string; /** Tool name (for after_tool_call hook) */ readonly toolName?: string; /** Failure source classification */ readonly failureSource?: 'tool_failure' | 'dispatch_error'; /** Whether the tool call exited with non-zero code */ readonly nonZeroExit?: boolean; /** Whether the tool call timed out */ readonly timedOut?: boolean; /** Whether the tool does not exist */ readonly toolNotFound?: boolean; /** Detection source identifier */ readonly detectionSource?: string; /** Whether GFI threshold was crossed */ readonly isGfiTriggered?: boolean; /** Whether the failure was a rate limit (429) */ readonly isRateLimit?: boolean; /** Whether this observation came from a gate block */ readonly isGateBlock?: boolean; /** Whether this was a manual CLI entry */ readonly isManualEntry?: boolean; /** Provenance: how trustworthy and context-bound is the observation */ readonly provenance?: 'host_context_bound' | 'owner_reported_no_host_trace' | 'automatic_hook'; /** Whether this observation came from a subagent error */ readonly isSubagentError?: boolean; /** * Raw payload from the source. * * This is always `unknown` (ERR-005). Source adapters validate only * enough to identify the source and capture bounded context. */ readonly payload?: unknown; } /** * Resolve SourceKind from a unified RawObservation. * * This function replaces the scattered resolveSourceKindFrom* functions * and provides a single entry point for source-kind classification. * * Field precedence is explicitly defined in the function body to ensure * deterministic behavior and make the logic easy to understand and test. */ export declare function resolveSourceKind(observation: RawObservation): SourceKind; /** * Build a RawObservation for a tool failure context. * * This replaces classifyToolFailureSource and the inline classification * in after-tool-call-helpers. All tool error → dispatch/tool_failure * classification is centralized here. */ export declare function buildToolFailureObservation(options: { toolName: string | undefined; error: unknown; exitCode?: number; provenance?: RawObservation['provenance']; }): RawObservation; /** * Build a RawObservation for an LLM detection context. */ export declare function buildLlmDetectionObservation(options: { detectionSource: string; isGfiTriggered: boolean; }): RawObservation; /** * Build a RawObservation for an empathy/GFI-triggered context (PRI-454). * * Used by prompt.ts paths 2 and 3 (GFI threshold crossing + empathy keyword match). * When isGfiTriggered=true, resolveSourceKind returns 'gfi_threshold' (evidence_only). * When isGfiTriggered=false, resolveSourceKind returns 'empathy_inferred' (owner_confirm). */ export declare function buildEmpathyObservation(options: { detectionSource: string; isGfiTriggered: boolean; sessionId?: string; }): RawObservation; /** * Build a RawObservation for a manual pain entry (PRI-454). * * Used by pain.ts path 5 (manual /pd-pain command). * resolveSourceKind returns 'owner_reported' (triage: admit). */ export declare function buildManualPainObservation(options: { sessionId?: string; }): RawObservation; //# sourceMappingURL=observation-resolver.d.ts.map