{"version":3,"file":"integration.d.ts","sourceRoot":"","sources":["../../../src/core/reliability/integration.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAEH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,+BAA+B,CAAC;AAG/D,OAAO,EAAE,KAAK,mBAAmB,EAAE,KAAK,mBAAmB,EAA0B,MAAM,uBAAuB,CAAC;AACnH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAC3D,OAAO,KAAK,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAElE,wBAAgB,yBAAyB,CAAC,KAAK,EAAE,SAAS,SAAS,EAAE,GAAG,mBAAmB,CAyB1F;AAED,MAAM,WAAW,0BAA0B;IAC1C,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,sDAAsD;IACtD,cAAc,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACnC,6DAA6D;IAC7D,QAAQ,CAAC,EAAE,OAAO,CAAC;CACnB;AAED;;;;GAIG;AACH,wBAAgB,yBAAyB,CAAC,OAAO,GAAE,0BAA+B,GAAG,mBAAmB,CAqCvG;AAED,MAAM,WAAW,sBAAsB;IACtC,sEAAsE;IACtE,cAAc,CAAC,CAAC,QAAQ,EAAE,eAAe,GAAG,IAAI,CAAC;IACjD,gFAAgF;IAChF,UAAU,CAAC,IAAI,IAAI,CAAC;CACpB;AAED;;;;;;GAMG;AACH,qBAAa,wBAAwB;IAEnC,QAAQ,CAAC,OAAO,EAAE,cAAc;IAChC,OAAO,CAAC,QAAQ,CAAC,MAAM;IACvB,OAAO,CAAC,QAAQ,CAAC,MAAM;IAHxB,YACU,OAAO,EAAE,cAAc,EACf,MAAM,EAAE,mBAAmB,EAC3B,MAAM,EAAE,mBAAmB,EACzC;IAEJ,4EAA0E;IACpE,cAAc,CAAC,QAAQ,EAAE,cAAc,GAAG,OAAO,CAAC;QAAE,KAAK,EAAE,OAAO,CAAC;QAAC,MAAM,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,CAuB3F;IAED,0EAAwE;IACxE,aAAa,CAAC,QAAQ,EAAE,cAAc,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,CAWhF;IAED,kFAAgF;IAChF,UAAU,IAAI,UAAU,CAAC,cAAc,CAAC,uBAAuB,CAAC,CAAC,CAEhE;CACD","sourcesContent":["/**\n * Reliability Session Bridge — adapters that connect the Reliability Kernel to\n * a live agent session's tool hooks.\n *\n * The bridge is provider-independent and side-effect free until attached. It\n * provides:\n *\n *   - createToolSchemaValidator(): adapts real AgentTool[] to the kernel's\n *     ToolSchemaValidator (schema enforcement via validateToolArguments).\n *   - createActionPolicyAdapter(): adapts a workspace root + forbidden-action\n *     set to the kernel's ActionPolicyAdapter (boundary + denylist checks).\n *   - ReliabilitySessionBridge: wraps beforeToolCall/afterToolCall/agentEnd so\n *     a session gains action validation, evidence recording, and a completion\n *     gate without a separate agent implementation.\n */\n\nimport type { AgentTool } from \"@apholdings/jensen-agent-core\";\nimport { validateToolArguments } from \"@apholdings/jensen-ai\";\nimport { decodeAction } from \"./action-decoder.js\";\nimport { type ActionPolicyAdapter, type ToolSchemaValidator, validateToolCallAction } from \"./action-validator.js\";\nimport type { MissionRuntime } from \"./mission-runtime.js\";\nimport type { MissionEvidence, ToolCallAction } from \"./types.js\";\n\nexport function createToolSchemaValidator(tools: readonly AgentTool[]): ToolSchemaValidator {\n\treturn {\n\t\texists(name: string): boolean {\n\t\t\treturn tools.some((t) => t.name === name);\n\t\t},\n\t\tvalidateArgs(name: string, args: Record<string, unknown>) {\n\t\t\tconst tool = tools.find((t) => t.name === name);\n\t\t\tif (!tool) {\n\t\t\t\treturn { ok: false as const, message: `Tool ${name} not found` };\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tconst normalized = validateToolArguments(tool, {\n\t\t\t\t\tname,\n\t\t\t\t\targuments: args as Record<string, unknown>,\n\t\t\t\t\ttoolCallId: `validate_${name}`,\n\t\t\t\t} as never) as Record<string, unknown>;\n\t\t\t\treturn { ok: true as const, normalized };\n\t\t\t} catch (error) {\n\t\t\t\treturn {\n\t\t\t\t\tok: false as const,\n\t\t\t\t\tmessage: error instanceof Error ? error.message : String(error),\n\t\t\t\t};\n\t\t\t}\n\t\t},\n\t};\n}\n\nexport interface ActionPolicyAdapterOptions {\n\tworkspaceRoot?: string;\n\t/** Tool names that are forbidden for this mission. */\n\tforbiddenTools?: readonly string[];\n\t/** When true, tools that write the workspace are blocked. */\n\treadOnly?: boolean;\n}\n\n/**\n * Lexical boundary/denylist policy. The full realpath boundary is enforced by\n * the tool executor itself; this adapter rejects obviously-escaping absolute\n * paths and `..` segments deterministically before execution.\n */\nexport function createActionPolicyAdapter(options: ActionPolicyAdapterOptions = {}): ActionPolicyAdapter {\n\tconst forbidden = new Set(options.forbiddenTools ?? []);\n\tconst root = options.workspaceRoot;\n\n\tconst pathArg = (action: ToolCallAction): string | undefined => {\n\t\tconst args = action.arguments;\n\t\tconst candidate = args?.path ?? args?.file ?? args?.filePath ?? args?.target;\n\t\treturn typeof candidate === \"string\" ? candidate : undefined;\n\t};\n\n\treturn {\n\t\tforbiddenReason(action): string | undefined {\n\t\t\tif (forbidden.has(action.tool)) {\n\t\t\t\treturn `tool '${action.tool}' is forbidden for this mission`;\n\t\t\t}\n\t\t\treturn undefined;\n\t\t},\n\t\tboundaryViolationReason(action): string | undefined {\n\t\t\tif (!root) return undefined;\n\t\t\tconst p = pathArg(action);\n\t\t\tif (!p) return undefined;\n\t\t\tif (p.includes(\"\\u0000\")) return \"path contains NUL byte\";\n\t\t\tconst segments = p.split(/[\\\\/]+/);\n\t\t\tif (segments.includes(\"..\")) return \"path contains a parent-directory segment\";\n\t\t\tif (p.startsWith(\"/\") || /^[A-Za-z]:/.test(p)) {\n\t\t\t\treturn \"absolute paths are not allowed within the mission boundary\";\n\t\t\t}\n\t\t\treturn undefined;\n\t\t},\n\t\tpermissionViolationReason(action): string | undefined {\n\t\t\tif (!options.readOnly) return undefined;\n\t\t\tconst mutating =\n\t\t\t\taction.tool === \"edit\" || action.tool === \"write\" || action.tool === \"bash\" || action.tool === \"powershell\";\n\t\t\tif (mutating) return \"read-only mission cannot run mutating tools\";\n\t\t\treturn undefined;\n\t\t},\n\t};\n}\n\nexport interface ReliabilityBridgeHooks {\n\t/** Called with observed tool evidence after a validated execution. */\n\tonToolExecuted?(evidence: MissionEvidence): void;\n\t/** Called when the agent ends a turn (implicit or explicit final candidate). */\n\tonAgentEnd?(): void;\n}\n\n/**\n * Bridge between a live agent session and the Reliability Kernel.\n *\n * beforeToolCall decodes + validates the model's raw tool call and blocks\n * invalid actions. afterToolCall records observed evidence. agentEnd proposes a\n * final candidate and runs the completion gate.\n */\nexport class ReliabilitySessionBridge {\n\tconstructor(\n\t\treadonly runtime: MissionRuntime,\n\t\tprivate readonly schema: ToolSchemaValidator,\n\t\tprivate readonly policy: ActionPolicyAdapter,\n\t) {}\n\n\t/** beforeToolCall handler — block invalid tool calls before execution. */\n\tasync beforeToolCall(toolCall: ToolCallAction): Promise<{ block: boolean; reason?: string }> {\n\t\tconst decoded = decodeAction({\n\t\t\ttype: \"tool_call\",\n\t\t\ttool: toolCall.tool,\n\t\t\ttoolCallId: toolCall.toolCallId,\n\t\t\targuments: toolCall.arguments,\n\t\t});\n\t\tif (!decoded.ok) {\n\t\t\treturn { block: true, reason: decoded.failure.message };\n\t\t}\n\t\tconst action = decoded.action;\n\t\tif (action.type !== \"tool_call\") {\n\t\t\treturn { block: true, reason: `expected tool_call, got ${action.type}` };\n\t\t}\n\t\tconst result = validateToolCallAction(action, { schema: this.schema, policy: this.policy });\n\t\tif (!result.ok) {\n\t\t\tthis.runtime.recorder.record(\"action_validation_failure\", {\n\t\t\t\ttool: action.tool,\n\t\t\t\tcategory: result.failure.category,\n\t\t\t});\n\t\t\treturn { block: true, reason: result.failure.message };\n\t\t}\n\t\treturn { block: false };\n\t}\n\n\t/** afterToolCall handler — record observed tool outcome as evidence. */\n\tafterToolCall(toolCall: ToolCallAction, isError: boolean, summary?: string): void {\n\t\tthis.runtime.recordToolEvidence({\n\t\t\tid: `tool_${toolCall.toolCallId}`,\n\t\t\ttype: \"tool_result\",\n\t\t\tsource: \"runtime\",\n\t\t\tsummary: summary ?? `${toolCall.tool} ${isError ? \"failed\" : \"executed\"}`,\n\t\t\tsuccess: !isError,\n\t\t\ttimestamp: new Date().toISOString(),\n\t\t\tdata: { tool: toolCall.tool },\n\t\t});\n\t\tthis.runtime.recorder.record(isError ? \"tool_failed\" : \"tool_executed\", { tool: toolCall.tool });\n\t}\n\n\t/** agentEnd handler — propose a final candidate and run the completion gate. */\n\tonAgentEnd(): ReturnType<MissionRuntime[\"proposeFinalCandidate\"]> {\n\t\treturn this.runtime.proposeFinalCandidate();\n\t}\n}\n"]}