@deepstrike/wasm 0.2.77 → 0.2.78

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (62) hide show
  1. package/dist/agent.d.ts +6 -2
  2. package/dist/agent.js +59 -19
  3. package/dist/index.d.ts +7 -9
  4. package/dist/index.js +3 -5
  5. package/dist/memory/attestation.d.ts +38 -0
  6. package/dist/memory/attestation.js +43 -0
  7. package/dist/memory/authority.d.ts +2 -0
  8. package/dist/memory/authority.js +3 -1
  9. package/dist/memory/candidate-sink.d.ts +66 -0
  10. package/dist/memory/candidate-sink.js +82 -0
  11. package/dist/memory/durable.d.ts +4 -2
  12. package/dist/memory/durable.js +2 -0
  13. package/dist/memory/index.d.ts +9 -1
  14. package/dist/memory/index.js +5 -0
  15. package/dist/memory/lifecycle.d.ts +82 -0
  16. package/dist/memory/lifecycle.js +46 -0
  17. package/dist/memory/recall-projection.d.ts +5 -0
  18. package/dist/memory/recall-projection.js +18 -0
  19. package/dist/memory/runtime-policy.d.ts +15 -0
  20. package/dist/memory/runtime-policy.js +26 -0
  21. package/dist/memory/writer.d.ts +22 -0
  22. package/dist/memory/writer.js +41 -0
  23. package/dist/providers/anthropic-compaction.d.ts +84 -0
  24. package/dist/providers/anthropic-compaction.js +222 -0
  25. package/dist/providers/anthropic.d.ts +41 -1
  26. package/dist/providers/anthropic.js +187 -18
  27. package/dist/providers/base.js +11 -1
  28. package/dist/runtime/canonical-kernel-step.d.ts +1 -2
  29. package/dist/runtime/canonical-kernel-step.js +74 -8
  30. package/dist/runtime/execution-plane.js +1 -1
  31. package/dist/runtime/index.d.ts +0 -2
  32. package/dist/runtime/index.js +0 -1
  33. package/dist/runtime/kernel-event-log.d.ts +8 -0
  34. package/dist/runtime/kernel-event-log.js +61 -1
  35. package/dist/runtime/kernel-step.d.ts +13 -2
  36. package/dist/runtime/os-snapshot.js +1 -0
  37. package/dist/runtime/runner.d.ts +40 -25
  38. package/dist/runtime/runner.js +196 -240
  39. package/dist/runtime/session-event-registry.generated.d.ts +212 -0
  40. package/dist/runtime/session-event-registry.generated.js +112 -0
  41. package/dist/runtime/session-log.d.ts +69 -16
  42. package/dist/runtime/session-log.js +10 -58
  43. package/dist/runtime/session-repair.d.ts +0 -3
  44. package/dist/runtime/session-repair.js +0 -3
  45. package/dist/runtime/sub-agent-orchestrator.d.ts +2 -0
  46. package/dist/runtime/sub-agent-orchestrator.js +2 -0
  47. package/dist/runtime/types/agent.d.ts +9 -52
  48. package/dist/runtime/types/agent.js +8 -45
  49. package/dist/types.d.ts +10 -5
  50. package/package.json +3 -3
  51. package/dist/memory/extraction.d.ts +0 -4
  52. package/dist/memory/extraction.js +0 -48
  53. package/dist/runtime/context.d.ts +0 -28
  54. package/dist/runtime/context.js +0 -16
  55. package/dist/runtime/evolution.d.ts +0 -189
  56. package/dist/runtime/evolution.js +0 -25
  57. package/dist/runtime/reducers.d.ts +0 -15
  58. package/dist/runtime/reducers.js +0 -57
  59. package/dist/runtime/verifiable-report.d.ts +0 -59
  60. package/dist/runtime/verifiable-report.js +0 -64
  61. package/dist/runtime/workflow-control-flow.d.ts +0 -21
  62. package/dist/runtime/workflow-control-flow.js +0 -83
package/dist/agent.d.ts CHANGED
@@ -145,7 +145,6 @@ export interface AgentRunResult {
145
145
  evidence?: {
146
146
  route?: unknown;
147
147
  measurement?: unknown;
148
- contextBinding?: unknown;
149
148
  };
150
149
  }
151
150
  export interface MemoryInput {
@@ -226,8 +225,13 @@ export declare class Agent {
226
225
  workflow(spec: WorkflowSpec, options?: {
227
226
  sessionId?: string;
228
227
  }): Promise<WorkflowOutcome>;
228
+ /** M4 · the runner a facade memory call goes through, so `remember`/`recall` take the same
229
+ * kernel admission, memory runtime policy, candidate routing, recall lifecycle and session
230
+ * audit as every other memory path. A `DurableMemory` is routed on its own store; any other
231
+ * `Memory` facade is adapted to one. */
232
+ private memoryRunner;
229
233
  remember(input: MemoryInput, sessionId?: string): Promise<MemoryRecord>;
230
- recall(query: string, options?: RecallOptions, _sessionId?: string): Promise<MemoryRecall[]>;
234
+ recall(query: string, options?: RecallOptions, sessionId?: string): Promise<MemoryRecall[]>;
231
235
  delegate(request: {
232
236
  target: AgentRef;
233
237
  goal: string;
package/dist/agent.js CHANGED
@@ -2,7 +2,7 @@ import { RuntimeRunner } from "./runtime/runner.js";
2
2
  import { LocalExecutionPlane } from "./runtime/execution-plane.js";
3
3
  import { InMemorySessionLog } from "./runtime/session-log.js";
4
4
  import { extractJsonValue, validateAgainstSchema } from "./runtime/output-schema.js";
5
- import { checkMemoryWrite } from "./memory/authority.js";
5
+ import { DurableMemory } from "./memory/durable.js";
6
6
  function statusOf(reason) {
7
7
  if (["completed", "success", "done"].includes(reason))
8
8
  return "completed";
@@ -158,31 +158,54 @@ export class Agent {
158
158
  resume(sessionId, options = {}) { return this.session(sessionId).resume(options); }
159
159
  interrupt(reason = "user", sessionId) { sessionId ? this.session(sessionId).interrupt(reason) : [...this.sessions.values()].forEach(s => s.interrupt(reason)); }
160
160
  workflow(spec, options = {}) { return this.session(options.sessionId).workflow(spec); }
161
- async remember(input, sessionId) {
162
- if (!this.memory || typeof this.memory.put !== "function")
161
+ /** M4 · the runner a facade memory call goes through, so `remember`/`recall` take the same
162
+ * kernel admission, memory runtime policy, candidate routing, recall lifecycle and session
163
+ * audit as every other memory path. A `DurableMemory` is routed on its own store; any other
164
+ * `Memory` facade is adapted to one. */
165
+ memoryRunner() {
166
+ const memory = this.memory;
167
+ if (!memory || typeof memory.put !== "function" || typeof memory.search !== "function") {
163
168
  throw new Error(`agent "${this.name}" memory is not runtime-bound`);
169
+ }
170
+ const facade = memory;
171
+ const scope = facade.scope ?? { tenant_id: "default", namespace: facade.namespace ?? this.name };
172
+ const durable = memory instanceof DurableMemory ? memory : undefined;
173
+ const binding = this.runtimeBinding;
174
+ const provider = binding?.provider ?? (typeof this.model === "string" ? binding?.providerFor?.(this.model) : undefined);
175
+ const runner = new RuntimeRunner({
176
+ ...(binding?.runtimeOptions ?? {}),
177
+ provider: provider ?? memoryOnlyProvider(this.name),
178
+ executionPlane: new LocalExecutionPlane(),
179
+ sessionLog: this.sessionLog,
180
+ maxTokens: 32_000,
181
+ agentId: durable?.agentId ?? this.name,
182
+ memoryScope: scope,
183
+ memoryStore: durable?.store ?? facadeStore(facade),
184
+ });
185
+ return { runner, scope };
186
+ }
187
+ async remember(input, sessionId) {
188
+ const { runner, scope } = this.memoryRunner();
164
189
  const now = Date.now();
190
+ const session = sessionId ?? `memory-${crypto.randomUUID()}`;
165
191
  const record = {
166
- record_id: crypto.randomUUID(), scope: this.memory.scope
167
- ?? { tenant_id: "default", namespace: this.memory.namespace ?? this.name },
192
+ record_id: crypto.randomUUID(), scope,
168
193
  name: input.name, kind: input.kind ?? "reference", content: input.content,
169
194
  description: input.description ?? input.name,
170
- provenance: { author: "host", trust: "user_asserted", evidence_refs: [], session_id: sessionId ?? `memory-${crypto.randomUUID()}` },
195
+ provenance: { author: "host", trust: "user_asserted", evidence_refs: [], session_id: session },
171
196
  created_at: now, updated_at: now, recall_count: 0, confidence: input.confidence ?? 1,
172
197
  links: [], pinned: input.pinned ?? false, ...(input.ttlDays === undefined ? {} : { ttl_days: input.ttlDays }),
173
198
  };
174
- // §22.13 · the kernel's write rule, not a copy of it, decides whether this record may be stored.
175
- const refusal = await checkMemoryWrite(undefined, record.name, record.content);
176
- if (refusal)
177
- throw new Error(`agent "${this.name}" memory write denied: ${refusal}`);
178
- await this.memory.put(record);
199
+ if (!await runner.writeMemory(record, session))
200
+ throw new Error(`agent "${this.name}" memory write denied`);
179
201
  return record;
180
202
  }
181
- async recall(query, options = {}, _sessionId) {
182
- if (!this.memory || typeof this.memory.search !== "function")
183
- throw new Error(`agent "${this.name}" memory is not runtime-bound`);
184
- const records = await this.memory.search(query, { topK: options.topK ?? 8, kinds: options.kinds, minScore: options.minScore });
185
- return records.map(record => ({ record, score: 1, why: "memory facade search" }));
203
+ async recall(query, options = {}, sessionId) {
204
+ const { runner, scope } = this.memoryRunner();
205
+ return runner.queryMemory({
206
+ scope, query, top_k: options.topK ?? 8, kinds: options.kinds ?? [],
207
+ ...(options.minScore === undefined ? {} : { min_score: options.minScore }),
208
+ }, sessionId ?? `memory-${crypto.randomUUID()}`);
186
209
  }
187
210
  async delegate(request) {
188
211
  const targetName = typeof request.target === "string" ? request.target : request.target.name;
@@ -231,12 +254,10 @@ export class Agent {
231
254
  result.usage = { inputTokens: attempt.usage.inputTokens, outputTokens: attempt.usage.outputTokens, totalTokens: attempt.usage.inputTokens + attempt.usage.outputTokens };
232
255
  }
233
256
  const measured = [...entries].reverse().find(e => e.event.kind === "prompt_measured")?.event;
234
- const prepared = [...entries].reverse().find(e => e.event.kind === "context_prepared")?.event;
235
- if ((started?.kind === "run_started" && started.route) || (attempt?.kind === "provider_attempt" && attempt.route) || measured || prepared) {
257
+ if ((started?.kind === "run_started" && started.route) || (attempt?.kind === "provider_attempt" && attempt.route) || measured) {
236
258
  result.evidence = {
237
259
  ...((attempt?.kind === "provider_attempt" ? attempt.route : started?.kind === "run_started" ? started.route : undefined) ? { route: attempt?.kind === "provider_attempt" ? attempt.route : started.route } : {}),
238
260
  ...(measured?.kind === "prompt_measured" ? { measurement: measured.measurement } : {}),
239
- ...(prepared?.kind === "context_prepared" ? { contextBinding: prepared.preparation.binding } : {}),
240
261
  };
241
262
  }
242
263
  if (this.outputSchema) {
@@ -247,3 +268,22 @@ export class Agent {
247
268
  return result;
248
269
  }
249
270
  }
271
+ /** The provider a memory-only runner carries: `remember`/`recall` never call the model. */
272
+ function memoryOnlyProvider(agent) {
273
+ const refuse = () => { throw new Error(`agent "${agent}" has no runtime provider binding`); };
274
+ return { complete: async () => refuse(), stream: () => refuse() };
275
+ }
276
+ /** A `Memory` facade as the store the runner writes through. The facade reports records only,
277
+ * so a recall from it carries no retrieval score. */
278
+ function facadeStore(memory) {
279
+ return {
280
+ put: (_agentId, record) => memory.put(record),
281
+ get: (_agentId, recordId) => memory.get(recordId),
282
+ delete: (_agentId, recordId) => memory.delete(recordId),
283
+ search: async (_agentId, query) => (await memory.search(query.query, {
284
+ topK: query.top_k, kinds: query.kinds,
285
+ ...(query.min_score === undefined ? {} : { minScore: query.min_score }),
286
+ })).map(record => ({ record, score: 1, why: "memory facade search" })),
287
+ saveSession: async () => { },
288
+ };
289
+ }
package/dist/index.d.ts CHANGED
@@ -5,19 +5,17 @@ export { CANONICAL_CONTENT_PARTS_PREFIX, encodeCanonicalContentParts, decodeCano
5
5
  export type { ReplayProviderOpts, Criterion, Verdict, VerdictDetail, JudgeArgs, } from "./runtime/index.js";
6
6
  export type { NativeOsProfile, OsProfileId, MemoryPolicy, MemoryWriteRateLimit, ResourceQuota, RuntimeOptions, PromptBudget, SchedulerPolicy, SignalPolicy, SessionEvent, SessionEventKind, SessionLog, RunContext, ExecutionPlane, KernelEventCategory, KernelPrimitive, } from "./runtime/index.js";
7
7
  export { primitiveForCategory, primitiveForKind } from "./runtime/index.js";
8
- export { VERIFIABLE_REPORT_SCHEMA, VERIFIABLE_FORK_SCHEMA, assertVerifiableReportSchema, createVerifiableRuntimeAdapter, createNativeVerifiableRuntimeAdapter, VerifiableOperation, } from "./runtime/verifiable-report.js";
9
- export type { VerifiableCommand, CheckVerdict, VerifiableForkManifest, ForkPlan, VerifiableEvidence, VerifyOptions, ReplayOptions, VerifiableRuntimeAdapter, VerifiableReport, VerifiableOperationJson, } from "./runtime/verifiable-report.js";
10
8
  export { FilteredExecutionPlane } from "./runtime/filtered-plane.js";
11
9
  export { SubAgentOrchestrator, defaultSubAgentOrchestrator, spawnStandalone } from "./runtime/sub-agent-orchestrator.js";
12
10
  export type { SubAgentRunContext } from "./runtime/sub-agent-orchestrator.js";
13
11
  export type { AgentCapabilityFilter, AgentIdentity, AgentIsolation, AgentRunSpec, AgentProcessChangedObservation, ContextInheritance, KernelAgentRole, LoopResult, MilestoneCheckResult, MilestoneContract, MilestonePhase, MilestonePolicy, SubAgentResult, TerminationReason, WorkflowSpec, WorkflowNodeSpec, SchedulingFactors, WorkflowDependencyPolicy, WorkflowNodeStatus, WorkflowNodeOutcome, WorkflowOutcome, WorkflowTaskSpec, WorkflowSpawnInfo, } from "./runtime/types/agent.js";
14
12
  export { workflowSpecToKernel, workflowNodeSpecToKernel, submitWorkflowNodesTool, startWorkflowTool, fanoutSynthesize, generateAndFilter, genEval, verifyRules } from "./runtime/types/agent.js";
15
- export { loopInstruction, classifyInstruction, judgeGoal, extractClassifyBranch, extractJudgeWinner, } from "./runtime/workflow-control-flow.js";
16
13
  export { Agent } from "./agent.js";
17
14
  export { McpExecutionPlane } from "./runtime/mcp-transport.js";
18
15
  export type { McpConnection, McpConnectionFactory, McpCredentialVault, McpServerConfig } from "./runtime/mcp-transport.js";
19
16
  export type { AgentMemory, AgentOptions, AgentRunResult, AgentRunOptions, AgentToolDefinition, AgentRef, Guardrail, Handoff, Knowledge, KnowledgeSourceRef, MCPServer, McpTransport, MemoryReference, ModelRef, ModelRequirement, Skill, MemoryInput, RecallOptions, DelegationResult, AgentRuntimeBinding, AgentSession, } from "./agent.js";
20
17
  export { AnthropicProvider } from "./providers/anthropic.js";
18
+ export type { AnthropicCompaction, AnthropicContextEditing, AnthropicOnDemandCompaction, AnthropicProviderOptions, AnthropicThresholdCompaction, } from "./providers/anthropic.js";
21
19
  export { OpenAIProvider, qwen, deepseek, minimax, kimi } from "./providers/openai.js";
22
20
  export type { OpenAIProviderOptions, BackendProviderOptions } from "./providers/openai.js";
23
21
  export { ProviderError, classifyProviderError } from "./providers/provider-error.js";
@@ -35,11 +33,8 @@ export type { InMemoryMemoryStoreOptions } from "./memory/in-memory-store.js";
35
33
  export { memoryRetentionScore } from "./memory/retention.js";
36
34
  export { rankMemories } from "./memory/ranking.js";
37
35
  export type { RankableMemory, RankedMemory, RankOptions } from "./memory/ranking.js";
38
- export { extractSessionMemories, parseExtractedMemories } from "./memory/extraction.js";
39
36
  export type { MemoryStore, Memory, MemorySearchOptions, SessionStore, SessionData, SessionMessage, MemoryRecord, MemoryRecall, MemoryRecallLifecycle, MemoryQuery, MemoryScope, MemoryProvenance, MemoryKind, MemoryAuthor, MemoryTrustLevel, } from "./memory/index.js";
40
37
  export type { KnowledgeSource } from "./knowledge/index.js";
41
- export { createEvolutionRuntimeAdapter, createNativeEvolutionRuntimeAdapter, EvolutionRuntime } from "./runtime/evolution.js";
42
- export type { ActivationBinding, ArtifactKind, ArtifactManifest, ArtifactRef, ArtifactSet, ArtifactVersion, ContextEntryRef, ContextEntrySource, ContextExecutionInput, ContextPlan, ContextPlanAction, ContextPreparationRequest, ContextSelection, ContextState, EvaluationContextBinding, EvaluationFact, EvaluationGate, EvaluationMetric, EvaluationRun, EvolutionBundle, EvolutionProposal, EvolutionReport, EvolutionVerdict, PromotionDecision, PromotionOutcome, EvolutionStore, } from "./runtime/evolution.js";
43
38
  export { AttemptLoop, RuntimeAttemptBody, VerdictFnJudge, LlmEvalJudge, HybridJudge, continueSession, freshWithFeedback, freshWithDigest, } from "./harness/index.js";
44
39
  export type { AttemptBody, AttemptBodyContext, AttemptBodyEvent, AttemptBodyTerminal, AttemptJudge, AttemptLoopEvent, AttemptLoopOptions, AttemptOutcome, AttemptOutcomeKind, AttemptProgressEvent, AttemptRequest, CarryPolicy, JudgeContext, JudgeResult, PreparedAttempt, StopPolicy, VerdictFn, } from "./harness/index.js";
45
40
  export { ScheduledPrompt } from "./signals/index.js";
@@ -57,6 +52,9 @@ export type { PermissionDecision } from "./safety/index.js";
57
52
  export type { ModelMessage, ToolCall, ToolExecutionResult, ToolSchema, RenderedContext, ProviderRunState, StreamEvent, TextDelta, ThinkingDelta, ToolCallEvent, ToolResultEvent, ToolAuditFailedEvent, DoneEvent, ErrorEvent, PermissionRequestEvent, PermissionResolvedEvent, PermissionResponse, EntropySample, EntropySampleEvent, EntropyAlertEvent, EntropyWatchOptions, LLMProvider, CacheBreakpointStrategy, ProviderWireEvidence, ProviderTransportTelemetry, } from "./types.js";
58
53
  export { DurableContentError, decodeDurableContent, decodeDurableToolResult, encodeDurableContent, encodeDurableToolResult, toolOutputBlocksToDurable, durableBlocksToToolOutput } from "./runtime/durable-content.js";
59
54
  export type { DurableContent, DurableContentBlock, DurableSource, DurableToolResult } from "./runtime/durable-content.js";
60
- export { createContextPreparationAdapter, createNativeContextPreparationAdapter } from "./runtime/context.js";
61
- export type { ContextPrepareJson, ContextVerifyJson, ContextPrepared, ContextProviderPreparationRequest } from "./runtime/context.js";
62
- export type { PreparedProviderRequest } from "./types.js";
55
+ export type { NativeContextTiers, PreparedProviderRequest } from "./types.js";
56
+ export { InMemoryMemoryCandidateSink, memoryCandidateDuplicateReason, memoryCandidateId, memoryCandidatePayloadDigest } from "./memory/candidate-sink.js";
57
+ export { memoryFetchRecall } from "./memory/recall-projection.js";
58
+ export type { MemoryCandidate, MemoryCandidateReceipt, MemoryCandidateSink, MemoryCandidateSource } from "./memory/candidate-sink.js";
59
+ export { resolveMemoryRuntimePolicy } from "./memory/runtime-policy.js";
60
+ export type { MemoryRuntimePolicy, MemoryRetrievalPolicy, MemoryWritePolicy, ResolvedMemoryRuntimePolicy } from "./memory/runtime-policy.js";
package/dist/index.js CHANGED
@@ -4,11 +4,9 @@ export { DriverKernelJournal, InMemoryJournalDriver, InMemoryKernelJournal, Jour
4
4
  // ── content-parts-v1 registered encoding (F14/B5; byte-pinned by sdk-conformance) ──
5
5
  export { CANONICAL_CONTENT_PARTS_PREFIX, encodeCanonicalContentParts, decodeCanonicalContentParts, } from "./runtime/kernel-step.js";
6
6
  export { primitiveForCategory, primitiveForKind } from "./runtime/index.js";
7
- export { VERIFIABLE_REPORT_SCHEMA, VERIFIABLE_FORK_SCHEMA, assertVerifiableReportSchema, createVerifiableRuntimeAdapter, createNativeVerifiableRuntimeAdapter, VerifiableOperation, } from "./runtime/verifiable-report.js";
8
7
  export { FilteredExecutionPlane } from "./runtime/filtered-plane.js";
9
8
  export { SubAgentOrchestrator, defaultSubAgentOrchestrator, spawnStandalone } from "./runtime/sub-agent-orchestrator.js";
10
9
  export { workflowSpecToKernel, workflowNodeSpecToKernel, submitWorkflowNodesTool, startWorkflowTool, fanoutSynthesize, generateAndFilter, genEval, verifyRules } from "./runtime/types/agent.js";
11
- export { loopInstruction, classifyInstruction, judgeGoal, extractClassifyBranch, extractJudgeWinner, } from "./runtime/workflow-control-flow.js";
12
10
  export { Agent } from "./agent.js";
13
11
  export { McpExecutionPlane } from "./runtime/mcp-transport.js";
14
12
  export { AnthropicProvider } from "./providers/anthropic.js";
@@ -22,8 +20,6 @@ export { DurableMemory } from "./memory/durable.js";
22
20
  export { InMemoryMemoryStore } from "./memory/in-memory-store.js";
23
21
  export { memoryRetentionScore } from "./memory/retention.js";
24
22
  export { rankMemories } from "./memory/ranking.js";
25
- export { extractSessionMemories, parseExtractedMemories } from "./memory/extraction.js";
26
- export { createEvolutionRuntimeAdapter, createNativeEvolutionRuntimeAdapter, EvolutionRuntime } from "./runtime/evolution.js";
27
23
  export { AttemptLoop, RuntimeAttemptBody, VerdictFnJudge, LlmEvalJudge, HybridJudge, continueSession, freshWithFeedback, freshWithDigest, } from "./harness/index.js";
28
24
  export { ScheduledPrompt } from "./signals/index.js";
29
25
  export { PermissionManager, PermissionMode } from "./safety/index.js";
@@ -32,4 +28,6 @@ export { FULL_FOOTPRINT_USAGE_ACCOUNTING_POLICY, providerAttemptToRecord, tryNor
32
28
  export { decodeCanonicalStopReason, normalizeProviderStopReason } from "./providers/stop-reason.js";
33
29
  export { ContentPolicyError, contentDispositionFor, requireContentDisposition } from "./providers/content-policy.js";
34
30
  export { DurableContentError, decodeDurableContent, decodeDurableToolResult, encodeDurableContent, encodeDurableToolResult, toolOutputBlocksToDurable, durableBlocksToToolOutput } from "./runtime/durable-content.js";
35
- export { createContextPreparationAdapter, createNativeContextPreparationAdapter } from "./runtime/context.js";
31
+ export { InMemoryMemoryCandidateSink, memoryCandidateDuplicateReason, memoryCandidateId, memoryCandidatePayloadDigest } from "./memory/candidate-sink.js";
32
+ export { memoryFetchRecall } from "./memory/recall-projection.js";
33
+ export { resolveMemoryRuntimePolicy } from "./memory/runtime-policy.js";
@@ -0,0 +1,38 @@
1
+ import { type MemoryCandidate, type MemoryCandidateSource } from "./candidate-sink.js";
2
+ export interface MemoryCandidateAttestation {
3
+ issuer: string;
4
+ key_id: string;
5
+ agent_id: string;
6
+ tenant_id: string;
7
+ namespace: string;
8
+ candidate_id: string;
9
+ source: MemoryCandidateSource;
10
+ payload_digest: string;
11
+ issued_at: number;
12
+ expires_at: number;
13
+ policy_version: string;
14
+ signature: string;
15
+ }
16
+ export type MemoryCandidateVerification = {
17
+ valid: true;
18
+ verified_at?: number;
19
+ } | {
20
+ valid: false;
21
+ reason_code: string;
22
+ };
23
+ export interface MemoryCandidateSourceVerifier {
24
+ verify(agentId: string, candidate: MemoryCandidate): MemoryCandidateVerification | Promise<MemoryCandidateVerification>;
25
+ }
26
+ /** Browser-safe verifier seam. Signature verification stays host-injected in WASM. */
27
+ export declare class HostMemoryCandidateSourceVerifier implements MemoryCandidateSourceVerifier {
28
+ private readonly verifyFn;
29
+ constructor(verifyFn: (agentId: string, candidate: MemoryCandidate) => MemoryCandidateVerification | Promise<MemoryCandidateVerification>);
30
+ verify(agentId: string, candidate: MemoryCandidate): MemoryCandidateVerification | Promise<MemoryCandidateVerification>;
31
+ }
32
+ /** The kernel's provenance rule, then the host's verifier: only the host may claim
33
+ * `host_verified`, that claim must carry an attestation, and any attestation supplied is verified. */
34
+ export declare function verifyMemoryCandidateSource(agentId: string, candidate: MemoryCandidate, verifier?: MemoryCandidateSourceVerifier): Promise<MemoryCandidateVerification>;
35
+ export declare function admitMemoryCandidate(agentId: string, candidate: MemoryCandidate, verifier?: MemoryCandidateSourceVerifier): Promise<MemoryCandidateVerification>;
36
+ export declare function memoryCandidateAttestationCanonicalPayload(attestation: Omit<MemoryCandidateAttestation, "signature">): Promise<string>;
37
+ export declare function memoryCandidateAttestationDigest(attestation: MemoryCandidateAttestation): Promise<string>;
38
+ export declare function memoryCandidateAttestationMatches(candidate: MemoryCandidate, attestation: MemoryCandidateAttestation): Promise<boolean>;
@@ -0,0 +1,43 @@
1
+ import { askMemoryAuthority } from "./authority.js";
2
+ import { memoryCandidatePayloadDigest } from "./candidate-sink.js";
3
+ /** Browser-safe verifier seam. Signature verification stays host-injected in WASM. */
4
+ export class HostMemoryCandidateSourceVerifier {
5
+ verifyFn;
6
+ constructor(verifyFn) {
7
+ this.verifyFn = verifyFn;
8
+ }
9
+ verify(agentId, candidate) { return this.verifyFn(agentId, candidate); }
10
+ }
11
+ /** Timestamps the kernel can read: non-negative safe integers. */
12
+ function wireTimestamps(attestation) {
13
+ return [attestation.issued_at, attestation.expires_at].every(value => Number.isSafeInteger(value) && value >= 0);
14
+ }
15
+ /** The kernel's provenance rule, then the host's verifier: only the host may claim
16
+ * `host_verified`, that claim must carry an attestation, and any attestation supplied is verified. */
17
+ export async function verifyMemoryCandidateSource(agentId, candidate, verifier) {
18
+ // Asked with no verifier, the kernel admits a candidate that needs none, refuses a bad claim, and
19
+ // answers `attestation_verifier_unconfigured` for one whose attestation the host must judge.
20
+ if (candidate.attestation && !wireTimestamps(candidate.attestation)) {
21
+ return verifier ? verifier.verify(agentId, candidate) : { valid: false, reason_code: "attestation_verifier_unconfigured" };
22
+ }
23
+ const answer = await askMemoryAuthority({ op: "verify_source", agent_id: agentId, candidate });
24
+ if (answer.valid === true)
25
+ return { valid: true };
26
+ if (answer.reason_code === "attestation_verifier_unconfigured" && verifier)
27
+ return verifier.verify(agentId, candidate);
28
+ return { valid: false, reason_code: String(answer.reason_code) };
29
+ }
30
+ export async function admitMemoryCandidate(agentId, candidate, verifier) {
31
+ return verifyMemoryCandidateSource(agentId, candidate, verifier);
32
+ }
33
+ export async function memoryCandidateAttestationCanonicalPayload(attestation) {
34
+ return String((await askMemoryAuthority({ op: "attestation", attestation })).canonical_payload);
35
+ }
36
+ export async function memoryCandidateAttestationDigest(attestation) {
37
+ return String((await askMemoryAuthority({ op: "attestation", attestation })).digest);
38
+ }
39
+ export async function memoryCandidateAttestationMatches(candidate, attestation) {
40
+ return attestation.candidate_id === candidate.candidate_id &&
41
+ attestation.source === candidate.source &&
42
+ attestation.payload_digest === await memoryCandidatePayloadDigest(candidate.record);
43
+ }
@@ -21,6 +21,8 @@ export interface MemoryPromotion {
21
21
  record_id: string;
22
22
  recall_count: number;
23
23
  }
24
+ /** One stateless question to the kernel's memory authority. */
25
+ export declare function askMemoryAuthority(request: Record<string, unknown>): Promise<Record<string, unknown>>;
24
26
  /** Would the kernel admit this write? Resolves to the refusal reason, or `undefined` when admitted. */
25
27
  export declare function checkMemoryWrite(policy: KernelMemoryPolicyWire | undefined, name: string, content: string): Promise<string | undefined>;
26
28
  /** Derive one recall's lifecycle from the counts the store reported it held. */
@@ -1,8 +1,10 @@
1
1
  import { getKernel } from "../runtime/kernel.js";
2
- async function ask(request) {
2
+ /** One stateless question to the kernel's memory authority. */
3
+ export async function askMemoryAuthority(request) {
3
4
  const kernel = await getKernel();
4
5
  return JSON.parse(kernel.memoryAuthorityJson(JSON.stringify(request)));
5
6
  }
7
+ const ask = askMemoryAuthority;
6
8
  /** Would the kernel admit this write? Resolves to the refusal reason, or `undefined` when admitted. */
7
9
  export async function checkMemoryWrite(policy, name, content) {
8
10
  const answer = await ask({
@@ -0,0 +1,66 @@
1
+ import type { MemoryRecord } from "./index.js";
2
+ import { type MemoryCandidateAttestation, type MemoryCandidateSourceVerifier } from "./attestation.js";
3
+ /** Which write path produced the candidate. `child_request` is the kernel's PersistMemory effect;
4
+ * `model_proposal` is the model's own `propose_memory` call. */
5
+ export type MemoryCandidateSource = "child_request" | "model_proposal";
6
+ export interface MemoryCandidate {
7
+ /** Deterministic for the write that produced it (see {@link memoryCandidateId}): a retry of the
8
+ * same write carries the same id, so the sink can answer it from what it already holds. */
9
+ candidate_id: string;
10
+ source: MemoryCandidateSource;
11
+ record: MemoryRecord;
12
+ attestation?: MemoryCandidateAttestation;
13
+ }
14
+ export type MemoryCandidateReceipt = {
15
+ status: "pending";
16
+ candidate_id: string;
17
+ receipt_id: string;
18
+ } | {
19
+ status: "accepted";
20
+ candidate_id: string;
21
+ receipt_id: string;
22
+ record_ref: string;
23
+ digest: string;
24
+ } | {
25
+ status: "rejected";
26
+ candidate_id: string;
27
+ receipt_id: string;
28
+ reason_code: string;
29
+ };
30
+ /**
31
+ * The host's candidate store. Contract (spec §2.3):
32
+ *
33
+ * - The sink mints `receipt_id`; it is the stable name of its answer.
34
+ * - Identity is scoped by agentId; source and review metadata are part of conflict detection.
35
+ * - The same `candidate_id` with the same payload returns the original receipt and stores nothing
36
+ * new, so a write whose acknowledgement was lost can be redelivered safely.
37
+ * - The same `candidate_id` with a different payload is rejected with
38
+ * `reason_code = "candidate_conflict"` and does not overwrite what is held.
39
+ * - Throwing means no answer was obtained; the caller may redeliver the same candidate.
40
+ */
41
+ export interface MemoryCandidateSink {
42
+ submit(agentId: string, candidate: MemoryCandidate): Promise<MemoryCandidateReceipt>;
43
+ }
44
+ /** A candidate id from the write's canonical identity — never random, so a retry repeats it.
45
+ * The kernel mints it, so every SDK hands the same write the same id. */
46
+ export declare function memoryCandidateId(parts: readonly string[]): Promise<string>;
47
+ /** The kernel's digest of the part of a record a candidate is judged by. Store ids, timestamps and
48
+ * recall counters are excluded: a retry of the same write may mint them afresh without changing
49
+ * what is being proposed. */
50
+ export declare function memoryCandidatePayloadDigest(record: MemoryRecord): Promise<string>;
51
+ /** Why a sink refuses a candidate whose payload it already holds for the agent under another id:
52
+ * the proposal is still in review, or already remembered. A rejected one does not count, so a
53
+ * proposal the host turned down may be made again. Each write path mints its own ids, so this is
54
+ * what keeps a model proposal and a child request for the same fact from both reaching review. */
55
+ export declare function memoryCandidateDuplicateReason(held: MemoryCandidateReceipt["status"] | undefined): string | undefined;
56
+ /** In-process sink: every candidate is held as `pending`. For tests and local development. */
57
+ export declare class InMemoryMemoryCandidateSink implements MemoryCandidateSink {
58
+ private readonly sourceVerifier?;
59
+ private readonly held;
60
+ private nextReceipt;
61
+ constructor(sourceVerifier?: MemoryCandidateSourceVerifier | undefined);
62
+ submit(agentId: string, candidate: MemoryCandidate): Promise<MemoryCandidateReceipt>;
63
+ /** Candidates held for `agentId`, in submission order. */
64
+ candidates(agentId?: string): MemoryCandidate[];
65
+ private mintReceiptId;
66
+ }
@@ -0,0 +1,82 @@
1
+ // Memory candidate hand-off (contract M2). A write path whose `memoryRuntimePolicy` value is
2
+ // `"candidate_sink"` does not put the record in the memory store: it hands the record to the
3
+ // host's sink as a candidate, and the sink answers whether it is pending review, accepted, or
4
+ // rejected. Only an accepted candidate is a remembered record.
5
+ import { askMemoryAuthority } from "./authority.js";
6
+ import { admitMemoryCandidate } from "./attestation.js";
7
+ /** A candidate id from the write's canonical identity — never random, so a retry repeats it.
8
+ * The kernel mints it, so every SDK hands the same write the same id. */
9
+ export async function memoryCandidateId(parts) {
10
+ return String((await askMemoryAuthority({ op: "candidate_id", parts })).candidate_id);
11
+ }
12
+ /** The kernel's digest of the part of a record a candidate is judged by. Store ids, timestamps and
13
+ * recall counters are excluded: a retry of the same write may mint them afresh without changing
14
+ * what is being proposed. */
15
+ export async function memoryCandidatePayloadDigest(record) {
16
+ return String((await askMemoryAuthority({ op: "candidate_payload_digest", record })).payload_digest);
17
+ }
18
+ /** Why a sink refuses a candidate whose payload it already holds for the agent under another id:
19
+ * the proposal is still in review, or already remembered. A rejected one does not count, so a
20
+ * proposal the host turned down may be made again. Each write path mints its own ids, so this is
21
+ * what keeps a model proposal and a child request for the same fact from both reaching review. */
22
+ export function memoryCandidateDuplicateReason(held) {
23
+ if (held === "pending")
24
+ return "already_pending_review";
25
+ if (held === "accepted")
26
+ return "already_remembered";
27
+ return undefined;
28
+ }
29
+ /** In-process sink: every candidate is held as `pending`. For tests and local development. */
30
+ export class InMemoryMemoryCandidateSink {
31
+ sourceVerifier;
32
+ held = new Map();
33
+ nextReceipt = 1;
34
+ constructor(sourceVerifier) {
35
+ this.sourceVerifier = sourceVerifier;
36
+ }
37
+ async submit(agentId, candidate) {
38
+ const payloadDigest = await memoryCandidatePayloadDigest(candidate.record);
39
+ const key = JSON.stringify([agentId, candidate.candidate_id]);
40
+ const existing = this.held.get(key);
41
+ if (existing) {
42
+ if (existing.payloadDigest === payloadDigest && existing.candidate.source === candidate.source)
43
+ return structuredClone(existing.receipt);
44
+ return {
45
+ status: "rejected",
46
+ candidate_id: candidate.candidate_id,
47
+ receipt_id: this.mintReceiptId(),
48
+ reason_code: "candidate_conflict",
49
+ };
50
+ }
51
+ const verification = await admitMemoryCandidate(agentId, candidate, this.sourceVerifier);
52
+ if (!verification.valid) {
53
+ return {
54
+ status: "rejected",
55
+ candidate_id: candidate.candidate_id,
56
+ receipt_id: this.mintReceiptId(),
57
+ reason_code: verification.reason_code,
58
+ };
59
+ }
60
+ const duplicate = memoryCandidateDuplicateReason([...this.held.values()]
61
+ .find(held => held.agentId === agentId && held.payloadDigest === payloadDigest)?.receipt.status);
62
+ if (duplicate) {
63
+ return { status: "rejected", candidate_id: candidate.candidate_id, receipt_id: this.mintReceiptId(), reason_code: duplicate };
64
+ }
65
+ const receipt = {
66
+ status: "pending",
67
+ candidate_id: candidate.candidate_id,
68
+ receipt_id: this.mintReceiptId(),
69
+ };
70
+ this.held.set(key, { agentId, candidate: structuredClone(candidate), payloadDigest, receipt });
71
+ return structuredClone(receipt);
72
+ }
73
+ /** Candidates held for `agentId`, in submission order. */
74
+ candidates(agentId) {
75
+ return [...this.held.values()]
76
+ .filter(held => agentId === undefined || held.agentId === agentId)
77
+ .map(held => structuredClone(held.candidate));
78
+ }
79
+ mintReceiptId() {
80
+ return `receipt:${this.nextReceipt++}`;
81
+ }
82
+ }
@@ -1,10 +1,12 @@
1
1
  import type { Memory, MemoryRecord, MemoryScope, MemorySearchOptions, MemoryStore } from "./index.js";
2
2
  /** Binds host storage to the public durable Memory contract for one agent and namespace. */
3
3
  export declare class DurableMemory implements Memory {
4
- private readonly store;
5
- private readonly agentId;
4
+ readonly store: MemoryStore;
5
+ readonly agentId: string;
6
6
  readonly namespace: string;
7
7
  readonly scope: MemoryScope;
8
+ /** `store` and `agentId` are the binding a runner uses to route this memory's writes and
9
+ * recalls through the kernel funnel (M4). */
8
10
  constructor(store: MemoryStore, agentId: string, scope: MemoryScope);
9
11
  search(query: string, options?: MemorySearchOptions): Promise<MemoryRecord[]>;
10
12
  get(recordId: string): Promise<MemoryRecord | null>;
@@ -4,6 +4,8 @@ export class DurableMemory {
4
4
  agentId;
5
5
  namespace;
6
6
  scope;
7
+ /** `store` and `agentId` are the binding a runner uses to route this memory's writes and
8
+ * recalls through the kernel funnel (M4). */
7
9
  constructor(store, agentId, scope) {
8
10
  this.store = store;
9
11
  this.agentId = agentId;
@@ -1,3 +1,4 @@
1
+ export * from "./lifecycle.js";
1
2
  export declare class WorkingMemory {
2
3
  private store;
3
4
  set(key: string, value: unknown): void;
@@ -90,7 +91,7 @@ export interface MemoryStore {
90
91
  get(agentId: string, recordId: string): Promise<MemoryRecord | null>;
91
92
  delete(agentId: string, recordId: string): Promise<void>;
92
93
  search(agentId: string, query: MemoryQuery): Promise<MemoryRecall[]>;
93
- /** Persist a completed session before the runner's one extraction pass. */
94
+ /** Persist a completed session's transcript. */
94
95
  saveSession(data: SessionData): Promise<void>;
95
96
  /** M3: mirror the kernel's journaled recall lifecycle into the durable store. Optional. */
96
97
  recordRecall?(agentId: string, recalls: MemoryRecallLifecycle[]): Promise<void>;
@@ -101,3 +102,10 @@ export interface SessionStore {
101
102
  loadSession(sessionId: string): Promise<SessionData | undefined>;
102
103
  saveSession(data: SessionData): Promise<void>;
103
104
  }
105
+ export { InMemoryMemoryCandidateSink, memoryCandidateDuplicateReason, memoryCandidateId, memoryCandidatePayloadDigest } from "./candidate-sink.js";
106
+ export { HostMemoryCandidateSourceVerifier, admitMemoryCandidate, verifyMemoryCandidateSource, memoryCandidateAttestationCanonicalPayload, memoryCandidateAttestationDigest, memoryCandidateAttestationMatches } from "./attestation.js";
107
+ export type { MemoryCandidateAttestation, MemoryCandidateSourceVerifier, MemoryCandidateVerification } from "./attestation.js";
108
+ export { memoryFetchRecall } from "./recall-projection.js";
109
+ export type { MemoryCandidate, MemoryCandidateReceipt, MemoryCandidateSink, MemoryCandidateSource } from "./candidate-sink.js";
110
+ export { resolveMemoryRuntimePolicy } from "./runtime-policy.js";
111
+ export type { MemoryRuntimePolicy, MemoryRetrievalPolicy, MemoryWritePolicy, ResolvedMemoryRuntimePolicy } from "./runtime-policy.js";
@@ -1,3 +1,4 @@
1
+ export * from "./lifecycle.js";
1
2
  export class WorkingMemory {
2
3
  store = new Map();
3
4
  set(key, value) { this.store.set(key, value); }
@@ -6,3 +7,7 @@ export class WorkingMemory {
6
7
  clear() { this.store.clear(); }
7
8
  has(key) { return this.store.has(key); }
8
9
  }
10
+ export { InMemoryMemoryCandidateSink, memoryCandidateDuplicateReason, memoryCandidateId, memoryCandidatePayloadDigest } from "./candidate-sink.js";
11
+ export { HostMemoryCandidateSourceVerifier, admitMemoryCandidate, verifyMemoryCandidateSource, memoryCandidateAttestationCanonicalPayload, memoryCandidateAttestationDigest, memoryCandidateAttestationMatches } from "./attestation.js";
12
+ export { memoryFetchRecall } from "./recall-projection.js";
13
+ export { resolveMemoryRuntimePolicy } from "./runtime-policy.js";
@@ -0,0 +1,82 @@
1
+ import type { MemoryRecord, MemoryScope } from "./index.js";
2
+ export interface MemoryLease {
3
+ lease_id: string;
4
+ agent_id: string;
5
+ scope: MemoryScope;
6
+ issued_at: number;
7
+ expires_at: number;
8
+ max_writes: number;
9
+ writes_used: number;
10
+ revoked_at?: number;
11
+ }
12
+ export type MemoryLeaseRejection = "lease_missing" | "lease_scope_mismatch" | "lease_expired" | "lease_revoked" | "memory_write_budget_exhausted";
13
+ export interface MemoryWriteBudget {
14
+ max_writes: number;
15
+ writes_used?: number;
16
+ }
17
+ export type MemoryLifecycleEventType = "lease_issued" | "lease_renewed" | "lease_write_consumed" | "lease_revoked" | "deletion_requested" | "deletion_applied" | "deletion_noop";
18
+ export interface MemoryLifecycleEvent {
19
+ event_id: string;
20
+ sequence: number;
21
+ type: MemoryLifecycleEventType;
22
+ agent_id: string;
23
+ lease_id: string;
24
+ scope: MemoryScope;
25
+ operation_id?: string;
26
+ occurred_at: number;
27
+ payload: Record<string, unknown>;
28
+ }
29
+ export interface MemoryDeletionReceipt {
30
+ deletion_id: string;
31
+ agent_id: string;
32
+ scope: MemoryScope;
33
+ record_id: string;
34
+ prior_digest?: string;
35
+ status: "applied" | "noop";
36
+ event_sequence: number;
37
+ }
38
+ export type MemoryLifecycleWriteResult = {
39
+ valid: true;
40
+ lease: MemoryLease;
41
+ event_id: string;
42
+ } | {
43
+ valid: false;
44
+ reason_code: MemoryLeaseRejection;
45
+ };
46
+ export interface MemoryLifecycleController {
47
+ issueLease(lease: MemoryLease): MemoryLease;
48
+ getLease(agentId: string, scope: MemoryScope): MemoryLease | undefined;
49
+ renewLease(agentId: string, leaseId: string, expiresAt: number, renewedAt: number): MemoryLease;
50
+ consumeWrite(agentId: string, scope: MemoryScope, operationId: string, nowMs: number): MemoryLifecycleWriteResult;
51
+ revokeLease(agentId: string, leaseId: string, revokedAt: number): MemoryLease;
52
+ deleteRecord(agentId: string, scope: MemoryScope, recordId: string, deletionId: string, priorDigest?: string): MemoryDeletionReceipt;
53
+ events(): MemoryLifecycleEvent[];
54
+ }
55
+ export declare function memoryRecordExpired(record: Pick<MemoryRecord, "updated_at" | "ttl_days">, nowMs: number): boolean;
56
+ export declare function verifyMemoryLease(lease: MemoryLease | undefined, agentId: string, scope: MemoryScope, nowMs: number, budget?: MemoryWriteBudget): {
57
+ valid: true;
58
+ } | {
59
+ valid: false;
60
+ reason_code: MemoryLeaseRejection;
61
+ };
62
+ export declare function consumeMemoryLeaseWrite(lease: MemoryLease): MemoryLease;
63
+ export declare function revokeMemoryLease(lease: MemoryLease, revokedAt: number): MemoryLease;
64
+ export declare function scopeMatchesMemoryDeletion(record: MemoryRecord, scope: {
65
+ tenant_id?: string;
66
+ namespace?: string;
67
+ }): boolean;
68
+ export declare class InMemoryMemoryLifecycleController implements MemoryLifecycleController {
69
+ private leases;
70
+ private consumed;
71
+ private deletedRecords;
72
+ private journal;
73
+ issueLease(lease: MemoryLease): MemoryLease;
74
+ getLease(agentId: string, scope: MemoryScope): MemoryLease | undefined;
75
+ renewLease(agentId: string, leaseId: string, expiresAt: number, renewedAt: number): MemoryLease;
76
+ consumeWrite(agentId: string, scope: MemoryScope, operationId: string, nowMs: number): MemoryLifecycleWriteResult;
77
+ revokeLease(agentId: string, leaseId: string, revokedAt: number): MemoryLease;
78
+ deleteRecord(agentId: string, scope: MemoryScope, recordId: string, deletionId: string, priorDigest?: string): MemoryDeletionReceipt;
79
+ events(): MemoryLifecycleEvent[];
80
+ private require;
81
+ private append;
82
+ }