UNPKG

agentfootprint

Version:

The explainable agent framework — backtrack a wrong answer to the exact context that caused it (evidence, not guesses). Built on footprintjs.

153 lines • 11 kB
/** * agentfootprint/observe — observability recorders. * * Pattern: Observer (GoF) — pluggable, fire-and-forget event listeners * for the agent's typed event stream. * Role: Outer ring (Hexagonal). Attach via `runner.attachScopeRecorder()`; * the runner emits events, recorders accumulate state. * * Three tiers (progressive disclosure): * * Tier 1 — context + stream (the core) * • ContextRecorder — every slot composition * • StreamRecorder — token-level LLM streaming * * Tier 2 — composition + agent (structural nav) * • CompositionRecorder — Sequence/Parallel/Conditional/Loop entries * • AgentRecorder — agent-loop iterations, tool calls * • BoundaryRecorder — domain-tagged subflow entry/exit * • FlowchartRecorder — StepGraph projection (Lens-friendly) * * Tier 3 — domain dashboards (attach on demand) * • CostRecorder — token/USD spend * • EvalRecorder — eval scores from `runner.emit('eval.*', ...)` * • MemoryRecorder — memory injections + writes * • EmbeddingRecorder — embedding cost, index-time vs query-time * • PermissionRecorder — permission decisions + denials * • SkillRecorder — skill activations * • LoggingRecorder — structured log lines per event * • StatusRecorder — chat-bubble first-person status * * Domain-flavored consumers (Lens, Grafana, Datadog) compose Tier 1+2 * directly; Tier 3 dashboards are opt-in. */ // Tier 1 — context + stream export { ContextRecorder } from './recorders/core/ContextRecorder.js'; export { streamRecorder } from './recorders/core/StreamRecorder.js'; // Tier 2 — composition + agent export { compositionRecorder, } from './recorders/core/CompositionRecorder.js'; export { agentRecorder } from './recorders/core/AgentRecorder.js'; export { boundaryRecorder, BoundaryRecorder, } from './recorders/observability/BoundaryRecorder.js'; export { RunStepRecorder, runStepRecorder, } from './recorders/observability/RunStepRecorder.js'; export { attachFlowchart, buildStepGraph, buildStepGraphFromEvents, } from './recorders/observability/FlowchartRecorder.js'; // recordRun — save a run so a viewer can show it later. THE producer for // `{ snapshot, events, structure }`: the timeline, the state, and the chart, // which is the shape the UIs consume (lens's `observeRecording`) and the one // every integration used to assemble by hand, each missing a different piece. export { recordRun, } from './recorders/observability/recordRun.js'; // A recording with every repeated value written ONCE — what to store or send // when the run is long: plain JSON repeats the history once per place that // saw it (K²·R), packed it grows with K·R. `unpackRecording` reads both // shapes, so a reader that calls it reads every recording ever minted — and // expands a packed one only when the plain recording it stands for is within // `maxBytes` (default `DEFAULT_UNPACK_MAX_BYTES`). export { packRecording, unpackRecording, isPackedRecording, PACKED_RECORDING_FORMAT, DEFAULT_UNPACK_MAX_BYTES, PackedRecordingError, PackedRecordingTooLargeError, } from './recorders/observability/recordingPack.js'; // Runtime selected-policy evidence: typed subscription only, with one bounded // capture owner. recordRun can own its lifecycle and snapshot bundle. export { trustBoundaryRecorder, } from './trust-boundaries/index.js'; // accountForAnswer — "Explain this answer": one answer's recording (plus what // the app declared) in, a typed account out — facts, each with who vouches for // it and where it lives in the record, and fixed sentences from a closed, // versioned template table. Pure and read-time: no clock, network or model. // See src/answer-account/README.md. // `answerAccountPointerKey(pointer)` is the key of the `shown` map the hosting // op `{ op: 'answer-account', ref }` returns beside the account. export { accountForAnswer, answerAccountPointerKey, } from './answer-account/index.js'; // assessAnswer — the answer's STANDING, folded from the run's committed record: // known · consistent with the record · not sure (with the reasons) · ask · not // assessed. Never read from how sure the model sounds, never "known" from // silence, never from events. The account's "How sure" row renders the same // fold. ONE public type; its family (a reason, a witness, a check that ran) by // indexed access. See src/core/agent/assessment/README.md. export { assessAnswer } from './core/agent/assessment/assess.js'; // The recording ENVELOPE — the versioned contract that makes a recording // archivable. `recordRun` freezes a run; this states which run it is, how much // of it this is, who produced it and under what privacy policy, so a saved run // can be filed, attached to a bug report, or read by an analysis tool without // every consumer inventing its own wrapper. Every field is derived from the // run's own events or stated by the caller — never guessed. export { buildRecordingEnvelope, persistRecording, FULL_PRIVACY_POLICY_ID, RECORDING_ENVELOPE_FORMAT, IndeterminateRunFactError, UnsupportedPrivacyModeError, } from './recorders/observability/recordingEnvelope.js'; // The reference sink: one archived run per JSON file, written atomically // (tmp + rename) so a crash never leaves a half-parsed archive. The file name // derives from the run id, which makes it a key — hence the asserted safe // charset and `UnsafeRecordingIdError` rather than a hopeful `${runId}.json`. export { fileRecordingSink, recordingFileName, UnsafeRecordingIdError, } from './recorders/observability/fileRecordingSink.js'; // exportBugReport — a bug report IS the evidence. `describeBugReport` measures // the run first (selectable units, sizes, the redacted keys by NAME) so a human // can consent to exactly what leaves; `exportBugReport` bundles the units they // kept as named files plus a real (stored) zip. `githubBugReporter` — in this // same door, from the providers barrel — files that bundle. // // The evidence in that zip is a RecordingEnvelope (bundle layout 2), built by // the same `buildRecordingEnvelope` above rather than a second wrapper — so the // producer facts are stamped once. `BugReportRunFacts` is the pair the envelope // cannot derive; without it the bundle still ships, as the bare recording, with // the manifest naming the fact that was missing. export { describeBugReport, exportBugReport, } from './bug-report/index.js'; // What a recording keeps of a vector: `{ dims, norm }`, not the bytes (8.20.0). // Applied by BoundaryRecorder and recordRun unless `recordEmbeddings: true`; // exported so consumers that render or post-process recordings can apply or // recognise the same projection. export { summarizeEmbeddings, summarizeVector, } from './recorders/observability/embeddingSummary.js'; // Offline replay: freeze a live run model into a UI-free, JSON-lossless Trace // (redaction applied at the serialize boundary). agentfootprint-lens's <Replay> // rehydrates it. See docs/design/local-observability-and-pii.md. export { serializeTrace, redactContent, traceToStepGraph, } from './recorders/observability/trace.js'; // localObservability — Tier-3 retain: live onLive(graph) + offline // getTrace()/onRecorded. NOT a Lens recorder — to render a run in Lens, use // `recordRun` above and lens's `observeRecording`. export { attachLocalObservability, } from './recorders/observability/localObservability.js'; export { liveStateRecorder, LiveStateRecorder, LiveLLMTracker, LiveToolTracker, LiveAgentTurnTracker, } from './recorders/observability/LiveStateRecorder.js'; // Tier 3 — domain dashboards export { costRecorder } from './recorders/core/CostRecorder.js'; export { toolsRecorder } from './recorders/core/ToolsRecorder.js'; export { contextEvaluatedRecorder, } from './recorders/core/ContextEvaluatedRecorder.js'; export { evalRecorder } from './recorders/core/EvalRecorder.js'; export { memoryRecorder } from './recorders/core/MemoryRecorder.js'; export { embeddingRecorder, } from './recorders/core/EmbeddingRecorder.js'; export { permissionRecorder, } from './recorders/core/PermissionRecorder.js'; export { skillRecorder } from './recorders/core/SkillRecorder.js'; // Provider-decorator telemetry (fallback.triggered / error.retried / // error.recovered / error.circuit_changed). Attached automatically by // Agent / LLMCall / Parallel; // exported so consumers running the public message-api charts on a bare // FlowChartExecutor can wire the bridge themselves. export { resilienceRecorder, } from './recorders/core/ResilienceRecorder.js'; export { attachLogging, LoggingDomains, } from './recorders/observability/LoggingRecorder.js'; export { attachStatus, } from './recorders/observability/StatusRecorder.js'; // Tool→tool DATA-FLOW graph, derived by value provenance from the tool emit // stream (see finding 2: causalChain can't see LLM-mediated tool dependencies). export { toolLineageRecorder, } from './recorders/observability/ToolLineageRecorder.js'; // AgentThinkingUI Trace (run → the "watch it think" beat list, collected during // traversal). Lets any agentfootprint run drive AgentThinkingUI / domain views. export { agentThinkingTrace, } from './recorders/observability/AgentThinkingTraceRecorder.js'; // Emit primitive — used by every Tier-3 source-domain. export { typedEmit } from './recorders/core/typedEmit.js'; // ── Diagnosis tools ──────────────────────────────────────────── // influence-core, trace-toolpack, context-bisect and tool-lint live in // `src/debug.ts`. 8.0.0 folded their import path INTO this one, and 9.0.0 // removed the separate `agentfootprint/debug` subpath, so this re-export is // how they reach the door. Watching a healthy run and performing the autopsy // on a broken one come through the same door on purpose. export * from './debug.js'; // Tool-choice margin recorder (RFC-002 tier 2, C4–C6) — per LLM call, // ranks the OFFERED catalog against the choice context (user message + // latest assistant reasoning) via influence-core scoreMargin; embeds // LAZILY on first read; flags narrow margins + proxy disagreements. export { buildChoiceContext, toolChoiceRecorder, } from './recorders/observability/ToolChoiceRecorder.js'; export { routeRecorder, formatRouteHop, } from './recorders/observability/RouteRecorder.js'; // context-ledger — which context pieces EARNED their tokens? Post-run // bookkeeping (offers/uses/outcomes from the commit log) feeding the gating // seams. See src/context-ledger/README.md. export { contextLedger, ledgerToolGate, ledgerEntryScorer, ledgerGated, } from './context-ledger/index.js'; //# sourceMappingURL=observe.js.map