Skip to content
Open
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,13 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
diagnostic compatibility exports out of the package root into explicit
`legacy`, `storage`, `advanced`, and `diagnostics` subpaths. The package root
now rejects those nouns through the v19 public API boundary audit.
- Locked the package root to the v19 facade allowlist so support ports,
infrastructure adapters, memory helpers, cancellation utilities, sync
internals, and canonical serialization helpers stay behind explicit subpaths.
- Aligned `CheckpointStorePort` with the schema:5 checkpoint envelope tree. The
CBOR adapter now owns the named checkpoint artifact encoding for runtime
checkpoint creation and loading instead of exposing a stale single
`state.cbor` result.
- Added visible-state scope helpers to the `diagnostics` subpath so
materialized-state inspection has an explicit non-legacy import path.
- Deprecated the entire graph-first legacy API. `legacy` remains migration-only
Expand Down
76 changes: 2 additions & 74 deletions docs/topics/reference.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,100 +30,31 @@ public API export, CLI command, package entrypoint, or public error class.

First-use product API: `openWarp`, `intent`, `reading`, timelines, and receipts.

### Export modules

| Module | Kind | Source |
| --- | --- | --- |
| `./src/domain/memory/index.ts` | export * | `index.ts#L55` |

### Value exports

Source: `index.ts`. Count: 73.
Source: `index.ts`. Count: 13.

```text
AlfredOperationPolicyAdapter @ index.ts#L68
AuditError @ index.ts#L71
BunHttpAdapter @ index.ts#L102
canonicalEmissionJson @ index.ts#L118
canonicalObservationJson @ index.ts#L124
CasContentEncryptionPolicy @ index.ts#L62
checkAborted @ index.ts#L104
ChunkEffectSink @ index.ts#L134
ConsoleEffectSink @ index.ts#L133
ConsoleLogger @ index.ts#L96
ContinuumArtifactAuthorityError @ index.ts#L72
createDeliveryObservation @ index.ts#L123
createEffectEmission @ index.ts#L117
createExternalizationPolicy @ index.ts#L127
createTickReceipt @ index.ts#L108
createTimeoutSignal @ index.ts#L104
CryptoPort @ index.ts#L98
DELIVERY_MODES @ index.ts#L119
DELIVERY_OUTCOMES @ index.ts#L120
DenoHttpAdapter @ index.ts#L103
DraftTimeline @ index.ts#L19
EffectPipeline @ index.ts#L115
EffectSinkPort @ index.ts#L113
EncryptionError @ index.ts#L73
ForkError @ index.ts#L74
HealthCheckService @ index.ts#L93
HealthStatus @ index.ts#L93
HttpServerPort @ index.ts#L99
IndexError @ index.ts#L75
INSPECT_LENS @ index.ts#L130
intent @ index.ts#L22
Intent @ index.ts#L23
JoinReceipt @ index.ts#L24
JoinResult @ index.ts#L25
LIVE_LENS @ index.ts#L128
LoggerPort @ index.ts#L94
LogLevel @ index.ts#L96
MemoryBudgetError @ index.ts#L76
MultiplexSink @ index.ts#L114
NodeCryptoAdapter @ index.ts#L100
NoOpEffectSink @ index.ts#L132
NoOpLogger @ index.ts#L95
NoopOperationPolicyAdapter @ index.ts#L69
openWarp @ index.ts#L18
OperationAbortedError @ index.ts#L77
OperationPolicyExhaustedError @ index.ts#L78
OperationPolicyPort @ index.ts#L57
OperationPolicyTimeoutError @ index.ts#L79
PatchError @ index.ts#L80
QueryError @ index.ts#L81
reading @ index.ts#L26
Reading @ index.ts#L27
ReadingResult @ index.ts#L28
ReadReceipt @ index.ts#L29
REPLAY_LENS @ index.ts#L129
SchemaUnsupportedError @ index.ts#L82
ShardCorruptionError @ index.ts#L83
ShardLoadError @ index.ts#L84
ShardValidationError @ index.ts#L85
StorageError @ index.ts#L86
StrandError @ index.ts#L87
SyncError @ index.ts#L88
SyncSecret @ index.ts#L105
TICK_RECEIPT_OP_TYPES @ index.ts#L110
TICK_RECEIPT_RESULT_TYPES @ index.ts#L111
tickReceiptCanonicalJson @ index.ts#L109
Timeline @ index.ts#L21
TraversalError @ index.ts#L89
Warp @ index.ts#L20
WebCryptoAdapter @ index.ts#L101
WormholeError @ index.ts#L90
WriteReceipt @ index.ts#L30
WriterError @ index.ts#L97
```

### Type exports

Source: `index.ts`. Count: 32.
Source: `index.ts`. Count: 26.

```text
CasContentEncryptionDiagnostics @ index.ts#L64
CasContentEncryptionScheme @ index.ts#L65
CasResolvedVaultKeyOptions @ index.ts#L66
EdgeIntentFields @ index.ts#L33
EdgePropertyIntentFields @ index.ts#L34
IntentBuilders @ index.ts#L40
Expand All @@ -138,8 +69,6 @@ JoinResultOptions @ index.ts#L42
NodeIntentFields @ index.ts#L37
NodeReadingFields @ index.ts#L45
OpenWarpOptions @ index.ts#L31
OperationPolicyExecuteOptions @ index.ts#L59
OperationRetryDecision @ index.ts#L60
PropertyIntentFields @ index.ts#L38
PropertyReadingFields @ index.ts#L46
ReadingBuilders @ index.ts#L50
Expand All @@ -150,7 +79,6 @@ ReadingValue @ index.ts#L51
ReadReceiptOptions @ index.ts#L52
ReadReceiptOutcome @ index.ts#L52
ReceiptOutcome @ index.ts#L53
SyncRateLimitConfig @ index.ts#L106
WarpStorage @ index.ts#L31
WriteReceiptOptions @ index.ts#L53
```
Expand Down
81 changes: 0 additions & 81 deletions index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -51,84 +51,3 @@ export type { ReadingBuilders } from './src/domain/api/ReadingBuilders.ts';
export type { ReadingResultOptions, ReadingValue } from './src/domain/api/ReadingResult.ts';
export type { ReadReceiptOptions, ReadReceiptOutcome } from './src/domain/api/ReadReceipt.ts';
export type { ReceiptOutcome, WriteReceiptOptions } from './src/domain/api/WriteReceipt.ts';

export * from './src/domain/memory/index.ts';

export { default as OperationPolicyPort } from './src/ports/OperationPolicyPort.ts';
export type {
OperationPolicyExecuteOptions,
OperationRetryDecision,
} from './src/ports/OperationPolicyPort.ts';
export { default as CasContentEncryptionPolicy } from './src/infrastructure/adapters/CasContentEncryptionPolicy.ts';
export type {
CasContentEncryptionDiagnostics,
CasContentEncryptionScheme,
CasResolvedVaultKeyOptions,
} from './src/infrastructure/adapters/CasContentEncryptionPolicy.ts';
export { default as AlfredOperationPolicyAdapter } from './src/infrastructure/adapters/AlfredOperationPolicyAdapter.ts';
export { default as NoopOperationPolicyAdapter } from './src/infrastructure/adapters/NoopOperationPolicyAdapter.ts';
export {
AuditError,
ContinuumArtifactAuthorityError,
EncryptionError,
ForkError,
IndexError,
MemoryBudgetError,
OperationAbortedError,
OperationPolicyExhaustedError,
OperationPolicyTimeoutError,
PatchError,
QueryError,
SchemaUnsupportedError,
ShardCorruptionError,
ShardLoadError,
ShardValidationError,
StorageError,
StrandError,
SyncError,
TraversalError,
WormholeError,
} from './src/domain/errors/index.ts';

export { default as HealthCheckService, HealthStatus } from './src/domain/services/HealthCheckService.ts';
export { default as LoggerPort } from './src/ports/LoggerPort.ts';
export { default as NoOpLogger } from './src/infrastructure/adapters/NoOpLogger.ts';
export { default as ConsoleLogger, LogLevel } from './src/infrastructure/adapters/ConsoleLogger.ts';
export { default as WriterError } from './src/domain/errors/WriterError.ts';
export { default as CryptoPort } from './src/ports/CryptoPort.ts';
export { default as HttpServerPort } from './src/ports/HttpServerPort.ts';
export { default as NodeCryptoAdapter } from './src/infrastructure/adapters/NodeCryptoAdapter.ts';
export { default as WebCryptoAdapter } from './src/infrastructure/adapters/WebCryptoAdapter.ts';
export { default as BunHttpAdapter } from './src/infrastructure/adapters/BunHttpAdapter.ts';
export { default as DenoHttpAdapter } from './src/infrastructure/adapters/DenoHttpAdapter.ts';
export { checkAborted, createTimeoutSignal } from './src/domain/utils/cancellation.ts';
export { default as SyncSecret } from './src/domain/services/sync/SyncSecret.ts';
export type { SyncRateLimitConfig } from './src/domain/services/sync/SyncRateLimiter.ts';
export {
createTickReceipt,
canonicalJson as tickReceiptCanonicalJson,
OP_TYPES as TICK_RECEIPT_OP_TYPES,
RESULT_TYPES as TICK_RECEIPT_RESULT_TYPES,
} from './src/domain/types/TickReceipt.ts';
export { default as EffectSinkPort } from './src/ports/EffectSinkPort.ts';
export { MultiplexSink } from './src/domain/services/MultiplexSink.ts';
export { EffectPipeline } from './src/domain/services/EffectPipeline.ts';
export {
createEffectEmission,
canonicalEmissionJson,
DELIVERY_MODES,
DELIVERY_OUTCOMES,
} from './src/domain/types/EffectEmission.ts';
export {
createDeliveryObservation,
canonicalObservationJson,
} from './src/domain/types/DeliveryObservation.ts';
export {
createExternalizationPolicy,
LIVE_LENS,
REPLAY_LENS,
INSPECT_LENS,
} from './src/domain/types/ExternalizationPolicy.ts';
export { NoOpEffectSink } from './src/infrastructure/adapters/NoOpEffectSink.ts';
export { ConsoleEffectSink } from './src/infrastructure/adapters/ConsoleEffectSink.ts';
export { ChunkEffectSink } from './src/infrastructure/adapters/ChunkEffectSink.ts';
66 changes: 44 additions & 22 deletions src/domain/services/state/checkpointCreate.ts
Original file line number Diff line number Diff line change
Expand Up @@ -118,11 +118,17 @@ export async function createCheckpointEnvelope({
}

// 3–6. Serialize and write current state envelope, frontier, appliedVV.
// The previous CheckpointStorePort path wrote a single state.cbor blob;
// current checkpoints keep the option for API compatibility but publish the
// runtime checkpoint through named envelope artifacts.
// Runtime callers route artifact encoding through CheckpointStorePort so the
// domain path no longer needs to know the concrete checkpoint blob layout.
// codecOpt is still needed for envelope/provenance serialization.
const codecOpt = codec !== undefined && codec !== null ? { codec } : {};
let nodeAliveOid: string;
let edgeAliveOid: string;
let propOid: string;
let observedFrontierOid: string;
let edgeBirthEventOid: string;
let frontierBlobOid: string;
let appliedVVBlobOid: string;
let stateHash: string;
let provenanceIndexBlobOid: string | null = null;

Expand All @@ -133,25 +139,41 @@ export async function createCheckpointEnvelope({
stateHash = await computeStateHash(checkpointState, { ...codecOpt, crypto: crypto as CryptoPort });
}

void checkpointStore;

// Current checkpoints publish separate envelope artifacts so the Git tree names
// each read basis member.
const stateEnvelope = serializeCheckpointStateEnvelope(checkpointState, codecOpt);
const nodeAliveOid = await persistence.writeBlob(stateEnvelope.nodeAlive);
const edgeAliveOid = await persistence.writeBlob(stateEnvelope.edgeAlive);
const propOid = await persistence.writeBlob(stateEnvelope.prop);
const observedFrontierOid = await persistence.writeBlob(stateEnvelope.observedFrontier);
const edgeBirthEventOid = await persistence.writeBlob(stateEnvelope.edgeBirthEvent);

const frontierBuffer = serializeFrontier(frontier, codecOpt);
const appliedVVBuffer = serializeAppliedVV(appliedVV, codecOpt);
const frontierBlobOid = await persistence.writeBlob(frontierBuffer);
const appliedVVBlobOid = await persistence.writeBlob(appliedVVBuffer);

if (provenanceIndex) {
const provenanceIndexBuffer = provenanceIndex.serialize(codecOpt);
provenanceIndexBlobOid = await persistence.writeBlob(provenanceIndexBuffer);
if (checkpointStore !== undefined && checkpointStore !== null) {
const checkpointWrite = await checkpointStore.writeCheckpoint({
state: checkpointState,
frontier,
appliedVV,
stateHash,
...(provenanceIndex !== undefined ? { provenanceIndex } : {}),
});
nodeAliveOid = checkpointWrite.nodeAliveBlobOid;
edgeAliveOid = checkpointWrite.edgeAliveBlobOid;
propOid = checkpointWrite.propBlobOid;
observedFrontierOid = checkpointWrite.observedFrontierBlobOid;
edgeBirthEventOid = checkpointWrite.edgeBirthEventBlobOid;
frontierBlobOid = checkpointWrite.frontierBlobOid;
appliedVVBlobOid = checkpointWrite.appliedVVBlobOid;
provenanceIndexBlobOid = checkpointWrite.provenanceIndexBlobOid;
} else {
// Current checkpoints publish separate envelope artifacts so the Git tree names
// each read basis member.
const stateEnvelope = serializeCheckpointStateEnvelope(checkpointState, codecOpt);
nodeAliveOid = await persistence.writeBlob(stateEnvelope.nodeAlive);
edgeAliveOid = await persistence.writeBlob(stateEnvelope.edgeAlive);
propOid = await persistence.writeBlob(stateEnvelope.prop);
observedFrontierOid = await persistence.writeBlob(stateEnvelope.observedFrontier);
edgeBirthEventOid = await persistence.writeBlob(stateEnvelope.edgeBirthEvent);

const frontierBuffer = serializeFrontier(frontier, codecOpt);
const appliedVVBuffer = serializeAppliedVV(appliedVV, codecOpt);
frontierBlobOid = await persistence.writeBlob(frontierBuffer);
appliedVVBlobOid = await persistence.writeBlob(appliedVVBuffer);

if (provenanceIndex) {
const provenanceIndexBuffer = provenanceIndex.serialize(codecOpt);
provenanceIndexBlobOid = await persistence.writeBlob(provenanceIndexBuffer);
}
}

// 6c. Collect content storage OIDs from state properties for GC anchoring.
Expand Down
19 changes: 18 additions & 1 deletion src/domain/services/state/checkpointLoad.ts
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,6 @@ export async function loadCheckpoint(

// Build codec option object once for exactOptionalPropertyTypes compliance
const loadCodecOpt = codec !== undefined && codec !== null ? { codec } : {};
void checkpointStore;

// 3. Read tree entries via the indexOid from the message (points to the tree)
const rawTreeOids = await persistence.readTreeOids(decoded.indexOid);
Expand All @@ -104,6 +103,24 @@ export async function loadCheckpoint(
partitionedTree.indexShardOids,
);

if (checkpointStore !== undefined && checkpointStore !== null) {
const checkpoint = await checkpointStore.readCheckpoint(treeOids);
const result: LoadedCheckpoint = {
state: checkpoint.state,
frontier: checkpoint.frontier,
stateHash: decoded.stateHash,
schema: decoded.schema,
appliedVV: checkpoint.appliedVV,
indexShardOids: Object.keys(indexShardOids).length > 0
? indexShardOids
: checkpoint.indexShardOids,
};
if (checkpoint.provenanceIndex !== null && checkpoint.provenanceIndex !== undefined) {
result.provenanceIndex = checkpoint.provenanceIndex;
}
return result;
}

// Current path: read each envelope blob individually.
const frontierOid = treeOids['frontier.cbor'];
if (frontierOid === undefined) {
Expand Down
Loading
Loading