# What Kam stores, writes, reads, and proves

Review the State add-on beside AgentCore: storage authority, accepted writes, exact reads, reconciliation, recovery and their qualification limits.

Status: Implemented in source. Prelaunch; not a live service guarantee.
Describes the History contract implemented in source. Nothing here is live-qualified, and no deployment is offered from this page.

Reviewed: 2026-10-14.
Backend source: e16b81b4a637acec91f3aed8a71cf5b0f42f0c19.
Native toolkit: merged in PR #176, reviewed at e16b81b4a637acec91f3aed8a71cf5b0f42f0c19.
HTML: /docs/engineering-review

## In short

Review the State layer your AgentCore application would rely on: what Kam stores, what a write commits, what an exact read proves and where recovery stops. Keep DynamoDB authority, Rust semantics, runtime execution and application decisions distinct.

**Available today:** The reviewed source implements History and bounded State contracts. Package receipts are local evidence, not live AgentCore or production qualification.

> Review what the State add-on proves before wiring it into an AgentCore application.

## Review the State layer beside AgentCore

- **Storage authority** — DynamoDB holds authoritative Kam data; Rust defines admitted State changes.
- **Exact read evidence** — Keep revision, fixed membership, scope and work limits together.
- **Runtime responsibility** — AgentCore execution and application decisions are outside a State read.
- **Recovery evidence** — Inspect accepted results and unfinished processing without assuming external success.
- **Release qualification** — Match the exact artifacts; local tests do not establish live production access.

## What is stored

1. **Outcome revisions** — Immutable (id, revision) records your application declares: subject, type, occurrence time, success or failure, category, and source references. Kam does not store your system of record, model prompts, or agent transcripts.

2. **Day membership** — Ordered references naming which exact revisions belong to one scope and UTC day, published as generations.

3. **Durable work records** — Work owed to the projection worker, committed with each accepted revision (a transactional outbox).

4. **Checkpoints and projections** — Saved fold state and applied sequence, plus the trajectory comparisons derived from them.

5. **Delivery obligations and receipts** — Only when optional AgentCore delivery is enabled (default off): one obligation per eligible generation, with separate publication and verification receipts.

[Glossary: outcome revision](/docs/concepts#outcome-revision)

## The write path

1. **1. Authenticate and authorize** — API Gateway verifies the Cognito access token; the handler re-checks issuer, client and scope, takes the principal from sub, and authorizes the requested tenant. A tenant ID in the request is not permission.

2. **2. Admit** — Rust validates identity, revision, occurrence time against the working window, and budgets. A correction must be exactly the next revision and cannot move the occurrence time.

3. **3. Commit atomically** — One DynamoDB TransactWriteItems call commits the revision, its day membership, and the work record, guarded by version conditions. Identical resubmission returns duplicate with the original acceptedSequence; a different payload for the same revision is rejected.

4. **4. Wake and fold** — A best-effort wakeup starts the worker. If it fails, the committed work record is redriven. The worker folds accepted revisions in sequence order.

5. **5. Publish** — A separate transaction commits the checkpoint, the new generation, and any eligible delivery obligation. Acceptance and publication are two transactions, not one.

[Glossary: acceptance transaction](/docs/concepts#acceptance-transaction)

[Glossary: transactional outbox](/docs/concepts#outbox)

## The read path, and what each read proves

1. **trajectory()** — Proves the projection as of appliedSequence, alongside acceptedSequence. If they differ, accepted work is not yet folded.

2. **allIds()** — Proves membership: these exact revision references belong to this generation, through acceptedThroughSequence. It does not assert that every real-world event was reported (externalCompleteness: not_asserted).

3. **byIds() in generation mode** — Proves each named revision is retained and matches its content hash, in caller order, and that it belongs to the generation. Missing, expired and unresolved positions stay explicit.

4. **byIds() in direct mode** — Proves a known (id, revision) is retained. It makes no membership claim and never falls back to the latest revision.

5. **What no read proves** — That an agent consumed the record, that the external fact is true, or who authored it. A content hash is integrity, not a signature.

## Where consistency and concurrency apply

Ordering is per scope: each tenant, subject and type has its own contiguous acceptedSequence and no global commit counter. Concurrent writers use optimistic concurrency; a stale version is rejected, not merged.

Each storage read is strongly consistent. A read that spans pages is made consistent by pinning a generation and passing its cursor back with it; if the service would have to switch generations, the read fails instead.

Kam makes no linearizability, serializability, or cross-scope isolation claim, and projections are asynchronous relative to acceptance.

[Glossary: conditional write](/docs/concepts#conditional-write)

[Glossary: generation](/docs/concepts#generation)

[Glossary: strongly consistent read](/docs/concepts#consistent-read)

## How recovery works

Work is persisted before anything relies on a wakeup, so a lost message delays processing instead of losing it. Processing is at-least-once and idempotent; Kam does not claim exactly-once execution.

Ambiguous external responses stay UNKNOWN until reconciled, and lifecycle epochs stop old jobs from acting with new authority. Owner export, export-bound deletion and a restore fence are implemented in source; live restore and erasure drills are not qualified. There is no arbitrary point-in-time recovery.

[Recovery and authority](/docs/reliability)

## Retention and deletion

New outcomes are admitted for today plus the previous 364 UTC dates. Retained evidence carries its own deadline of up to 730 days. Reads report a revision past its deadline as expired immediately; DynamoDB TTL removes the item later, typically within a few days, so expiry is not proof of physical deletion.

[Glossary: logical expiry](/docs/concepts#logical-expiry)

[Retention guide](/docs/retention)

## Who is responsible for what

1. **Your application** — Business meaning of success and failure, stable IDs, idempotency of external effects, and the agent runtime.

2. **Kam** — Admission rules, per-scope ordering, immutable revisions, generations, projections, and receipts, with the limits stated above.

3. **Identity and access** — Cognito authenticates the principal. The History API decides which workspaces that principal can read. Neither the browser nor this website grants access.

4. **Deployment** — Kam is designed for deployment on AWS. No live hosted service or Marketplace listing is offered today; an evaluation needs an isolated deployment and an explicit review of identity, permissions, retries, corrections, and exit.

## What remains unqualified

Every capability below is shown at the highest level its recorded evidence supports. No capability is live-qualified, pilot-only, or production-authorized.

1. **History — Locally qualified** — Package qualification is not a live deployment.

2. **Identity & membership — Locally qualified** — Covered by the same package qualification as History.

3. **Views & current State — Source-implemented** — Reviewed View and reconciliation source; no live-qualified or publicly offered hosted State service is established.

4. **State queries & Components — Source-implemented** — SDK 0.40.0 has a passed offline artifact receipt; the source claim is limited to supported bounded operations, not arbitrary payload queries or live service qualification.

5. **Metrics, materialize & watch — Planned · not available** — Design preview only.

6. **Turn Lifecycle — Locally qualified** — Merged native toolkit; reference-only local frames.

7. **Versioned Context manifests — Source-implemented** — Exact capture, ordered manifests and bounded assembly exist in source. Automatic ranking, managed runtime wiring and live model-consumption proof are not established.

8. **Operational durability — Source-implemented** — History and reconciliation progress are durable in source; no named checkpoint API.

9. **Profiler & developer toolkit — Locally qualified** — Merged; Linux x64 only; no public distribution.

10. **Optional AgentCore delivery — Locally qualified** — Default off; simulated AWS transports only.

11. **Export, deletion & restore fence — Source-implemented** — Live erasure and restore drills are qualification gates.

[What has been tested](/docs/qualification)

## Quickstart: record, retry, correct, read both revisions

Every call below exists in SDK 0.40.0. Obtain the reviewed private package through an evaluation; the package-name import assumes that artifact has already been supplied. An authorized endpoint, principal and tenant binding are separate prerequisites. No public npm release or self-serve endpoint is offered.

The duplicate assertion checks the same retained revision and acceptance sequence. It does not deduplicate an external model or tool action.

### Assert an exact retry, then read both revisions

```javascript
// Private SDK 0.40.0. Not published to npm. Methods checked against the pinned typings.
// Run in Node 22 with the supplied evaluation package and an authorized endpoint, tenant and token.
import assert from 'node:assert/strict';
import { createKamClient } from '@kam-ai/agentcore-history-sdk';
const kam = createKamClient({
  baseUrl: process.env.KAM_API_URL,
  tenantId: process.env.KAM_TENANT_ID,
  accessToken: () => process.env.KAM_ACCESS_TOKEN,
});
const checks = kam.scope({ subjectId: 'checkout', type: 'deployment' });

// 1. Record revision 1, then resend the identical payload while its evidence is retained.
const original = { id: 'deploy-0412', occurredAt: '2026-10-06T17:00:00.000Z', status: 'success' };
const first = await checks.outcome(original);
const retry = await checks.outcome(original);
assert.equal(retry.status, 'duplicate');
assert.equal(retry.acceptedSequence, first.acceptedSequence);
assert.equal(retry.revision, first.revision); // No new accepted revision.

// 2. Correct it: the next revision, same id and occurredAt. Revision 1 is kept while retained.
const second = await checks.outcome({ id: 'deploy-0412', revision: 2, occurredAt: '2026-10-06T17:00:00.000Z', status: 'failure' });
console.log(first.acceptedSequence, second.acceptedSequence); // per-scope order

// 3. Read both exact revisions. Direct mode makes no day-membership claim.
const exact = await checks.byIds({ refs: [{ id: 'deploy-0412', revision: 1 }, { id: 'deploy-0412', revision: 2 }] });
for (const record of exact.records) console.log(record.ref.revision, record.status);
```
