@microdelta/history 0.1.0 → 0.3.0

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 (44) hide show
  1. package/README.md +15 -3
  2. package/dist/api/history.alpha.d.ts +2 -2
  3. package/dist/api/history.root.raw.alpha.d.ts +380 -21
  4. package/dist/api/history.root.raw.beta.d.ts +40 -2
  5. package/dist/api/history.root.raw.public.d.ts +40 -2
  6. package/dist/api/history.root.raw.untrimmed.d.ts +380 -21
  7. package/dist/api/history.shared.alpha.d.ts +376 -19
  8. package/dist/api/history.shared.beta.d.ts +36 -0
  9. package/dist/api/history.shared.public.d.ts +36 -0
  10. package/dist/api/history.shared.untrimmed.d.ts +376 -19
  11. package/dist/api/history.untrimmed.d.ts +2 -2
  12. package/dist/src/durable/contracts.d.ts +292 -17
  13. package/dist/src/durable/contracts.d.ts.map +1 -1
  14. package/dist/src/durable/errors.d.ts +44 -3
  15. package/dist/src/durable/errors.d.ts.map +1 -1
  16. package/dist/src/durable/errors.js +43 -7
  17. package/dist/src/durable/errors.js.map +1 -1
  18. package/dist/src/durable/index.d.ts.map +1 -1
  19. package/dist/src/durable/index.js +299 -111
  20. package/dist/src/durable/index.js.map +1 -1
  21. package/dist/src/durable/journal.d.ts +53 -0
  22. package/dist/src/durable/journal.d.ts.map +1 -0
  23. package/dist/src/durable/journal.js +174 -0
  24. package/dist/src/durable/journal.js.map +1 -0
  25. package/dist/src/durable/records.d.ts +40 -0
  26. package/dist/src/durable/records.d.ts.map +1 -0
  27. package/dist/src/durable/records.js +74 -0
  28. package/dist/src/durable/records.js.map +1 -0
  29. package/dist/src/durable/schema.d.ts +14 -3
  30. package/dist/src/durable/schema.d.ts.map +1 -1
  31. package/dist/src/durable/schema.js +99 -21
  32. package/dist/src/durable/schema.js.map +1 -1
  33. package/dist/src/durable/selected-index.d.ts.map +1 -1
  34. package/dist/src/durable/selected-index.js +19 -5
  35. package/dist/src/durable/selected-index.js.map +1 -1
  36. package/dist/src/durable/sqlite-boundary.d.ts +11 -0
  37. package/dist/src/durable/sqlite-boundary.d.ts.map +1 -0
  38. package/dist/src/durable/sqlite-boundary.js +79 -0
  39. package/dist/src/durable/sqlite-boundary.js.map +1 -0
  40. package/dist/src/index.d.ts +7 -5
  41. package/dist/src/index.d.ts.map +1 -1
  42. package/dist/src/index.js +5 -3
  43. package/dist/src/index.js.map +1 -1
  44. package/package.json +3 -3
@@ -106,6 +106,21 @@ export declare interface GenerationRow {
106
106
  /** Retained lifecycle states interpreted by repository and claim, not by storage. @public */
107
107
  export declare type GenerationState = 'claimed' | 'current' | 'superseded' | 'abandoned';
108
108
 
109
+ /**
110
+ * A History-owned SQLite operation exhausted Machine's bounded busy wait.
111
+ * The exact host failure is retained as `cause`, so callers can distinguish
112
+ * contention from corruption or a stale writer without losing host detail.
113
+ * History wraps only failures raised at its SQLite capability boundary, never
114
+ * an application callback that happened to throw a Machine busy error.
115
+ * @alpha
116
+ */
117
+ export declare class HistoryBusyError extends Error {
118
+ /** The exact Machine failure that History received. */
119
+ readonly cause: SqliteBusyError;
120
+ /** Create History's boundary failure while retaining the original host error. */
121
+ constructor(message: string, cause: SqliteBusyError);
122
+ }
123
+
109
124
  /**
110
125
  * The injected clock failed to produce a nonnegative safe-integer epoch
111
126
  * millisecond reading, so the time-dependent operation was refused unchanged.
@@ -156,6 +171,8 @@ export declare interface IAcceptanceRecord {
156
171
  readonly acceptanceId: number;
157
172
  /** The accepted exact result. */
158
173
  readonly reference: ICompletedResultReference;
174
+ /** The environment namespace whose verification recorded this acceptance. */
175
+ readonly environment: string;
159
176
  /** The writer fence under which the acceptance was recorded. */
160
177
  readonly fence: number;
161
178
  /** Resolution's acceptance evidence, decoded and frozen. */
@@ -176,8 +193,22 @@ export declare interface IAcceptanceRequest {
176
193
  readonly reference: ICompletedResultReference;
177
194
  /** Resolution's versioned acceptance evidence. */
178
195
  readonly evidence: IVersionedRecord;
179
- /** Exact completed results the current verification followed. */
196
+ /**
197
+ * Exact completed results the current verification followed. Each must be
198
+ * admissible in the accepting environment: published there, or named by a
199
+ * promotion into it.
200
+ */
180
201
  readonly dependencies: readonly ICompletedResultReference[];
202
+ /**
203
+ * The environment, within the result's analysis, whose current verification
204
+ * accepted the result. It is always explicit and never inferred from the
205
+ * reference: the caller names its own run environment. It may be the
206
+ * environment that published the result, or another environment into which
207
+ * a recorded promotion admits the result. The acceptance then belongs to
208
+ * that environment's namespace alone and never satisfies a lookup in any
209
+ * other environment.
210
+ */
211
+ readonly environment: string;
181
212
  }
182
213
 
183
214
  /** @alpha A path segment whose kind follows the container's operation semantics. */
@@ -369,6 +400,17 @@ export declare type Identity = {
369
400
  * larger fence. A host reading that is not a nonnegative safe integer fails
370
401
  * the operation without any change. This is a local single-file policy, not a
371
402
  * distributed-time or liveness guarantee.
403
+ *
404
+ * Storage contention: every mutation, including acquisition, is one IMMEDIATE
405
+ * SQLite transaction. When another connection, possibly in another process,
406
+ * holds SQLite's write lock past the host's bounded busy wait, nothing
407
+ * changes. Acquisition and renewal, the lease operations a waiter repeats,
408
+ * report it as their `contended` outcome ({@link IWriterContention}), so
409
+ * contention is never mistaken for ownership or staleness (PUB-005). Any other
410
+ * History-owned SQLite operation, including opening and reads, fails with
411
+ * `HistoryBusyError` whose cause is the exact Machine `SqliteBusyError`.
412
+ * Callback-thrown failures retain their identity and do not become contention
413
+ * outcomes. Whether to try again is always the caller's policy, never History's.
372
414
  * @alpha
373
415
  */
374
416
  export declare interface IDurableHistory {
@@ -376,11 +418,20 @@ export declare interface IDurableHistory {
376
418
  readonly logicalStore: string;
377
419
  /** Exact selected reads over completed results, answered from their generated index. */
378
420
  readonly reader: ICompletedResultReader & ICompletedNavigationReader;
379
- /** Acquire the single logical writer, or report the observed unexpired holder. */
421
+ /**
422
+ * Acquire the single logical writer, or report the observed unexpired
423
+ * holder, or report storage contention with the recorded writer. Any other
424
+ * failure, such as damaged storage or an unusable clock, is thrown.
425
+ */
380
426
  acquireWriter(request: IWriterAcquisitionRequest): IWriterAcquisition;
381
- /** Extend a still-valid lease; a stale or expired lease is rejected. */
382
- renewWriter(lease: IWriterLease, leaseMilliseconds: number): IWriterLease;
383
- /** End a still-valid lease without resetting the fence. */
427
+ /**
428
+ * Extend a still-valid lease, or report storage contention, which leaves the
429
+ * lease as it was. A stale or expired lease is rejected with
430
+ * `StaleWriterError`. Only the expiry changes: the durable fence is left as
431
+ * it is, never rewritten from the presented lease.
432
+ */
433
+ renewWriter(lease: IWriterLease, leaseMilliseconds: number): IWriterRenewal;
434
+ /** End a still-valid lease; the durable fence is left as it is, so the next grant still advances it. */
384
435
  releaseWriter(lease: IWriterLease): void;
385
436
  /** Inspect the recorded holder, if any, without granting authority. */
386
437
  currentWriter(): IWriterLease | undefined;
@@ -403,9 +454,17 @@ export declare interface IDurableHistory {
403
454
  abandonAttempt(lease: IWriterLease, request: IAbandonRequest): IAttemptRecord;
404
455
  /** Report what durably happened to one identified execution, read-only. */
405
456
  recoverAttempt(request: IAttemptRequest): IRecoveryOutcome;
406
- /** Completed results for one scoped subject and version, latest publication first. */
457
+ /**
458
+ * Completed results admissible for one scoped subject and version, latest
459
+ * publication first: those published in the subject's environment and those
460
+ * a recorded promotion admits into it. A promoted result keeps its own exact
461
+ * reference and envelope scope; nothing from any other environment appears.
462
+ */
407
463
  findCandidates(subject: IVersionedSubject): readonly ICompletedEnvelope[];
408
- /** The scoped subject's latest publication, if any; never rewound by acceptance. */
464
+ /**
465
+ * The scoped subject's latest publication in its own environment, if any;
466
+ * never rewound by acceptance and never moved by a promotion.
467
+ */
409
468
  readCurrent(subject: IScopedSubject): ICompletedResultReference | undefined;
410
469
  /** Read one exact result's metadata without loading its payload. */
411
470
  readEnvelope(reference: ICompletedResultReference): ICompletedEnvelope;
@@ -413,8 +472,25 @@ export declare interface IDurableHistory {
413
472
  verifyResult(reference: ICompletedResultReference): IResultVerification;
414
473
  /** Record a current acceptance of an existing result without touching it or the current pointer. */
415
474
  recordAcceptance(lease: IWriterLease, request: IAcceptanceRequest): IAcceptanceRecord;
416
- /** Acceptance records naming one exact result, in record order. */
417
- readAcceptances(reference: ICompletedResultReference): readonly IAcceptanceRecord[];
475
+ /**
476
+ * Acceptance records naming one exact result that were recorded in the
477
+ * named environment, in record order. The environment is always explicit:
478
+ * the publishing environment, or one a promotion admits the result into.
479
+ */
480
+ readAcceptances(reference: ICompletedResultReference, environment: string): readonly IAcceptanceRecord[];
481
+ /**
482
+ * In one commit, record a promotion that admits exact results of other
483
+ * environments into the target environment. Nothing already recorded changes.
484
+ */
485
+ promoteResults(lease: IWriterLease, request: IPromotionRequest): IPromotionRecord;
486
+ /** Promotion records into one environment, in record order. */
487
+ readPromotions(query: IPromotionQuery): readonly IPromotionRecord[];
488
+ /**
489
+ * Open Run Supervision's operation journal over this store, bound to the
490
+ * declared record formats and versions. The port shares this authority's
491
+ * connection, writer lease and lifetime.
492
+ */
493
+ openJournal(declaration: IJournalDeclaration): IOperationJournal;
418
494
  /** Release the SQLite file; later calls fail. */
419
495
  close(): void;
420
496
  }
@@ -443,7 +519,10 @@ export declare interface IDurableHistoryOptions {
443
519
  * The analysis and environment that scope every subject, attempt and result
444
520
  * within one logical store. The same subject text in another analysis or
445
521
  * environment is a different scoped subject (RES-001/002). Both are complete
446
- * opaque non-empty strings compared by exact equality.
522
+ * opaque non-empty strings compared by exact equality. An environment is a
523
+ * namespace within one store (RUN-017): a trial and a production run of the
524
+ * same analysis use different environments of the same file, selected per
525
+ * call rather than process-wide.
447
526
  * @alpha
448
527
  */
449
528
  export declare interface IHistoryScope {
@@ -453,14 +532,198 @@ export declare interface IHistoryScope {
453
532
  readonly environment: string;
454
533
  }
455
534
 
535
+ /**
536
+ * Locates one journal record: its environment namespace, owner-named
537
+ * collection and owner-defined key. The record's identity is exactly this
538
+ * address; its format tag may change between revisions only by
539
+ * compare-and-set.
540
+ * @alpha
541
+ */
542
+ export declare interface IJournalAddress extends IHistoryScope {
543
+ /** The owner-named non-empty collection, such as Supervision's operations. */
544
+ readonly collection: string;
545
+ /** The owner-defined non-empty key, unique within the namespace and collection. */
546
+ readonly key: string;
547
+ }
548
+
549
+ /**
550
+ * One atomic journal commit in one environment namespace: every write lands
551
+ * in the same transaction, or none does.
552
+ * @alpha
553
+ */
554
+ export declare interface IJournalCommit extends IHistoryScope {
555
+ /** At least one write, each collection and key pair at most once. */
556
+ readonly writes: readonly IJournalWrite[];
557
+ }
558
+
559
+ /**
560
+ * The formats a journal port is bound to. A stored record of an undeclared
561
+ * format or version is refused rather than returned or overwritten, so a
562
+ * caller never acts on, or clobbers, a record it does not understand.
563
+ * @alpha
564
+ */
565
+ export declare interface IJournalDeclaration {
566
+ /** At least one declared format, each format named once. */
567
+ readonly formats: readonly IJournalFormat[];
568
+ }
569
+
570
+ /**
571
+ * One owner-defined journal record format and the exact format versions a
572
+ * journal port can read and write. A format is only a record's version tag:
573
+ * it never identifies a record or its collection. History compares the tag
574
+ * and versions for exact equality and never interprets the content.
575
+ * @alpha
576
+ */
577
+ export declare interface IJournalFormat {
578
+ /** The owner-defined non-empty format identity. */
579
+ readonly format: string;
580
+ /** The positive safe-integer versions of that format this port understands. */
581
+ readonly versions: readonly number[];
582
+ }
583
+
584
+ /**
585
+ * Selects every record of one collection in one environment namespace.
586
+ * @alpha
587
+ */
588
+ export declare interface IJournalQuery extends IHistoryScope {
589
+ /** The owner-named collection to list. */
590
+ readonly collection: string;
591
+ }
592
+
593
+ /**
594
+ * One immutable revision of a journal record. Revisions of an address start
595
+ * at 1 and increase by one per committed write; earlier revisions are retained
596
+ * and never rewritten.
597
+ * @alpha
598
+ */
599
+ export declare interface IJournalRecord extends IHistoryScope {
600
+ /** The owner-named collection. */
601
+ readonly collection: string;
602
+ /** The owner-defined key. */
603
+ readonly key: string;
604
+ /** This revision's number within its address, starting at 1. */
605
+ readonly revision: number;
606
+ /** Store-wide never-reused journal write identity, increasing in commit order. */
607
+ readonly sequence: number;
608
+ /** The writer fence under which this revision was committed. */
609
+ readonly fence: number;
610
+ /** The owner-defined record, decoded and frozen, with this revision's version tag. */
611
+ readonly record: IVersionedRecord;
612
+ }
613
+
614
+ /**
615
+ * One compare-and-set write of a journal commit. The expected revision is the
616
+ * revision the caller last read at this address; `0` asserts that the key has
617
+ * never been written in the collection, under any format. The record's
618
+ * format and version are its version tag and must be declared by the port.
619
+ * @alpha
620
+ */
621
+ export declare interface IJournalWrite {
622
+ /** The owner-named non-empty collection. */
623
+ readonly collection: string;
624
+ /** The owner-defined non-empty key. */
625
+ readonly key: string;
626
+ /** The current revision the write replaces, or `0` for a new key. */
627
+ readonly expectedRevision: number;
628
+ /** The new owner-defined record. */
629
+ readonly record: IVersionedRecord;
630
+ }
631
+
456
632
  /** A patch attempted to modify an immutable address or managed CAS version. @public */
457
633
  export declare class InvalidStorePatchError extends Error {
458
634
  /** Identify a structurally forbidden patch before any columns are changed. @public */
459
635
  constructor(message?: string);
460
636
  }
461
637
 
462
- /** @alpha A supported JavaScript observation operation with its own fact meaning. */
463
- export declare type IOperation = 'value' | 'own' | 'membership' | 'length' | 'keys';
638
+ /**
639
+ * A supported observation operation with its own fact meaning. `container-kind`
640
+ * answers record, array or scalar without consuming any container member or
641
+ * scalar content; ordinary scalar reads still retain their literal values.
642
+ * @alpha
643
+ */
644
+ export declare type IOperation = 'value' | 'own' | 'membership' | 'length' | 'keys' | 'container-kind';
645
+
646
+ /**
647
+ * Run Supervision's operation journal, stored by History (RUN-011/012). It
648
+ * keeps owner-defined operation and deferral records, such as an intent
649
+ * committed before a send or a "not before" deferral, atomically and under
650
+ * writer fencing, without interpreting them: History owns only namespacing,
651
+ * collections, revisions, fencing and the declared-version check. A commit
652
+ * needs the current writer lease and checks holder, fence and unexpired lease
653
+ * in the same transaction as its compare-and-set checks and writes; reads
654
+ * need no lease and never see an uncommitted write.
655
+ * @alpha
656
+ */
657
+ export declare interface IOperationJournal {
658
+ /** The frozen formats and versions this port was opened with. */
659
+ readonly formats: readonly IJournalFormat[];
660
+ /**
661
+ * Commit every write in one transaction. The whole commit is refused,
662
+ * unchanged, for a stale lease, an undeclared format or version, a current
663
+ * revision whose stored format or version this port does not understand
664
+ * (checked first, since such a caller cannot have read it), or an expected
665
+ * revision that is not the address's current revision.
666
+ */
667
+ commit(lease: IWriterLease, request: IJournalCommit): readonly IJournalRecord[];
668
+ /** The current revision at one address, or undefined if the key was never written there. */
669
+ read(address: IJournalAddress): IJournalRecord | undefined;
670
+ /** The current revision of every key in one collection, in order of first write. */
671
+ list(query: IJournalQuery): readonly IJournalRecord[];
672
+ }
673
+
674
+ /**
675
+ * Selects promotion records into one target environment, optionally only
676
+ * those naming one exact result.
677
+ * @alpha
678
+ */
679
+ export declare interface IPromotionQuery {
680
+ /** The analysis and environment whose admitting promotions to read. */
681
+ readonly target: IHistoryScope;
682
+ /** When present, only promotions that name this exact result. */
683
+ readonly reference?: ICompletedResultReference;
684
+ }
685
+
686
+ /**
687
+ * One immutable promotion record. It admits the named results as candidates,
688
+ * dependencies and acceptance targets in its target environment and changes
689
+ * nothing else: each result keeps its exact reference, envelope, provenance
690
+ * and acceptances, and no current head moves in any environment. The target
691
+ * environment's later verifications record their own acceptances.
692
+ * @alpha
693
+ */
694
+ export declare interface IPromotionRecord {
695
+ /** Store-wide never-reused promotion identity, increasing in record order. */
696
+ readonly promotionId: number;
697
+ /** The analysis and environment the results were admitted into. */
698
+ readonly target: IHistoryScope;
699
+ /** The writer fence under which the promotion was recorded. */
700
+ readonly fence: number;
701
+ /** The promoter's evidence, decoded and frozen. */
702
+ readonly evidence: IVersionedRecord;
703
+ /** The admitted exact results, each in its own publishing scope, in recorded order. */
704
+ readonly references: readonly ICompletedResultReference[];
705
+ }
706
+
707
+ /**
708
+ * Asks History to admit exact completed results of other environments into
709
+ * one target environment of the same analysis (RUN-017). A trial result
710
+ * satisfies a production lookup only through such a recorded promotion. The
711
+ * target names where the results are admitted; each reference keeps naming
712
+ * its own publishing environment. The evidence is the promoter's versioned
713
+ * record of who promoted what and why; History stores it opaquely.
714
+ * @alpha
715
+ */
716
+ export declare interface IPromotionRequest {
717
+ /** The analysis and environment the results are admitted into. */
718
+ readonly target: IHistoryScope;
719
+ /**
720
+ * Distinct exact completed results of the target's analysis, none published
721
+ * in the target environment, in the promoter's order.
722
+ */
723
+ readonly references: readonly ICompletedResultReference[];
724
+ /** The promoter's versioned evidence for this promotion. */
725
+ readonly evidence: IVersionedRecord;
726
+ }
464
727
 
465
728
  /**
466
729
  * Read-only recovery of one identified execution. Recovery reports what
@@ -564,7 +827,8 @@ export declare type ISelectedFingerprintResolution = {
564
827
  * a lazy view, never a whole-object observation, so no member, identity or
565
828
  * serialized subtree is implied. Array length is carried so a view need not ask
566
829
  * again, but it becomes observation evidence only when a consumer reads it.
567
- * Shapes are never placed inside {@link ISelectedFact.fact}.
830
+ * Shape envelopes are never placed inside {@link ISelectedFact.fact}; Tracking
831
+ * may separately observe the bounded `container-kind` discriminant.
568
832
  * @alpha
569
833
  */
570
834
  export declare type ISelectedNode =
@@ -626,21 +890,23 @@ declare interface ISnapshotCapability {
626
890
  * directory, a missing parent directory, a file that is not a SQLite database,
627
891
  * or a location that cannot hold a persistent write-ahead-logged database,
628
892
  * including `:memory:` and the empty path. Opening never silently weakens the
629
- * host's durable configuration.
893
+ * host's durable configuration. Processes that open one new store at the same
894
+ * time all succeed within the bounded busy wait or fail with `SqliteBusyError`.
630
895
  * @alpha
631
896
  */
632
897
  export declare interface ISqliteCapability {
633
898
  /** Open or create the database file at `location` and return its owned connection. */
634
- openSqlite(location: string): ISqliteConnection;
899
+ openSqlite(location: string, options?: ISqliteOpenOptions): ISqliteConnection;
635
900
  }
636
901
 
637
902
  /**
638
903
  * An open connection to one persistent local SQLite database file. The caller
639
904
  * that opened it owns it and must close it. The host selects durable
640
- * configuration for every connection: write-ahead logging, FULL synchronous
905
+ * configuration for every connection: selected persistent journaling, FULL synchronous
641
906
  * commits, enforced foreign keys and a bounded wait on a locked database.
642
907
  * Callers supply every SQL statement and schema; the connection has no
643
- * knowledge of what the tables mean.
908
+ * knowledge of what the tables mean. A statement, exec or transaction that
909
+ * cannot get a lock within the bounded wait fails with `SqliteBusyError`.
644
910
  *
645
911
  * Transactions are synchronous, top-level and IMMEDIATE: the write lock is
646
912
  * taken before the callback runs, the callback's writes commit together when
@@ -675,6 +941,18 @@ export declare interface ISqliteConnection {
675
941
  close(): void;
676
942
  }
677
943
 
944
+ /** Host journal selection for dedicated storage; schema and retention remain caller-owned. @alpha */
945
+ export declare interface ISqliteOpenOptions {
946
+ /**
947
+ * WAL is the default. DELETE uses rollback journaling with FULL synchronous
948
+ * commits, allowing side-effect-free readers but permitting reader/writer
949
+ * contention. DELETE refuses existing WAL files instead of changing them.
950
+ * Cooperative owners must keep the pathname and journal layout stable from
951
+ * preflight through opening and for the lifetime of every handle.
952
+ */
953
+ readonly journalMode: 'wal' | 'delete';
954
+ }
955
+
678
956
  /**
679
957
  * One result row keyed by result column name. Rows are transport data owned by
680
958
  * the caller; they carry no driver type, prototype behavior or live link to
@@ -834,7 +1112,7 @@ export declare interface IVersionedSubject extends IScopedSubject {
834
1112
  /**
835
1113
  * The outcome of asking for the single logical writer. `held` reports an
836
1114
  * observed unexpired holder, not a failed compare-and-swap (PUB-005), and
837
- * grants nothing.
1115
+ * grants nothing; `contended` reports that storage was too busy to decide.
838
1116
  * @alpha
839
1117
  */
840
1118
  export declare type IWriterAcquisition = {
@@ -849,7 +1127,7 @@ export declare type IWriterAcquisition = {
849
1127
  readonly holder: string;
850
1128
  /** When that holder's lease expires, in History's clock domain. */
851
1129
  readonly expiresAt: number;
852
- };
1130
+ } | IWriterContention;
853
1131
 
854
1132
  /** A request for the writer lease. @alpha */
855
1133
  export declare interface IWriterAcquisitionRequest {
@@ -859,6 +1137,28 @@ export declare interface IWriterAcquisitionRequest {
859
1137
  readonly leaseMilliseconds: number;
860
1138
  }
861
1139
 
1140
+ /**
1141
+ * Storage contention on a lease operation: another connection, possibly in
1142
+ * another process, held SQLite's write lock past the host's bounded busy wait,
1143
+ * so History could not decide and changed nothing, not even the clock
1144
+ * high-water. It is a fact about storage, never about ownership (PUB-005): it
1145
+ * neither grants nor refuses, and whether to try again is the caller's policy.
1146
+ * @alpha
1147
+ */
1148
+ export declare interface IWriterContention {
1149
+ /** History could not take SQLite's write lock in time. */
1150
+ readonly kind: 'contended';
1151
+ /**
1152
+ * The writer recorded at that moment, read without the write lock: its
1153
+ * holder, fence and expiry as stored, whether or not the lease has expired.
1154
+ * Undefined when no holder is recorded, or when that read was itself busy;
1155
+ * History never guesses a holder.
1156
+ */
1157
+ readonly writer: IWriterLease | undefined;
1158
+ /** The host's diagnostic of the contention; it carries no stored values. */
1159
+ readonly detail: string;
1160
+ }
1161
+
862
1162
  /**
863
1163
  * Proof of current single-logical-writer ownership. The holder is an opaque
864
1164
  * caller identity; the fence is the store-wide token issued at acquisition,
@@ -877,6 +1177,46 @@ export declare interface IWriterLease {
877
1177
  readonly expiresAt: number;
878
1178
  }
879
1179
 
1180
+ /**
1181
+ * The outcome of renewing a lease the caller holds: `renewed` with the later
1182
+ * expiry, or `contended` when storage was too busy to decide, in which case
1183
+ * the lease is exactly as it was and is neither renewed nor refused. A stale
1184
+ * or expired lease is not an outcome but a refusal (`StaleWriterError`).
1185
+ * @alpha
1186
+ */
1187
+ export declare type IWriterRenewal = {
1188
+ /** The lease was extended. */
1189
+ readonly kind: 'renewed';
1190
+ /** The same holder and fence with the new expiry. */
1191
+ readonly lease: IWriterLease;
1192
+ } | IWriterContention;
1193
+
1194
+ /**
1195
+ * A journal commit's compare-and-set expectation does not hold: the presented
1196
+ * expected revision is not the key's current revision (a new-key expectation
1197
+ * met an existing key, or an update met a later or absent revision). The
1198
+ * whole commit was rolled back unchanged; the caller must re-read before
1199
+ * deciding again.
1200
+ * @alpha
1201
+ */
1202
+ export declare class JournalConflictError extends Error {
1203
+ /** Create a compare-and-set rejection with a diagnostic message. */
1204
+ constructor(message: string);
1205
+ }
1206
+
1207
+ /**
1208
+ * A journal record's format or format version is not one the journal port
1209
+ * declared. On a write the record is refused; on a read or list the stored
1210
+ * record is refused rather than returned; a commit over a current revision of
1211
+ * an undeclared version is refused rather than overwriting it. History never
1212
+ * interprets or converts the content of another format version.
1213
+ * @alpha
1214
+ */
1215
+ export declare class JournalVersionError extends Error {
1216
+ /** Create an undeclared-version refusal with a diagnostic message. */
1217
+ constructor(message: string);
1218
+ }
1219
+
880
1220
  /** Options for the isolated, non-durable test backend. @public */
881
1221
  export declare interface MemoryStoreOptions {
882
1222
  /** Metadata compatibility identifier; the initial store format uses sha256. */
@@ -954,6 +1294,23 @@ export declare type ResultKey = {
954
1294
  subjectHash: string;
955
1295
  };
956
1296
 
1297
+ /**
1298
+ * The SQLite capability gave up waiting for another connection, possibly in
1299
+ * another process, to release a lock it needs. A host raises it, instead of
1300
+ * any driver-specific error, when its bounded busy wait is exhausted while
1301
+ * opening a store or running a statement or transaction. The failed operation
1302
+ * had no effect, so the caller may retry it or report contention to its own
1303
+ * caller; telling a busy store apart from a broken one is the purpose of this
1304
+ * type. Hosts never use it for corruption, misuse or other failures.
1305
+ * @alpha
1306
+ */
1307
+ declare class SqliteBusyError extends Error {
1308
+ /** How long, in milliseconds, the host waited before giving up. */
1309
+ readonly waitedMilliseconds: number;
1310
+ /** Create a busy-exhaustion failure that records the wait that was spent. */
1311
+ constructor(message: string, waitedMilliseconds: number, options?: ErrorOptions);
1312
+ }
1313
+
957
1314
  /**
958
1315
  * A presented writer lease no longer matches the durable holder, fence or
959
1316
  * unexpired lease, so the mutation was rejected with no change other than the
@@ -90,6 +90,8 @@ export declare interface GenerationRow {
90
90
  /** Retained lifecycle states interpreted by repository and claim, not by storage. @public */
91
91
  export declare type GenerationState = 'claimed' | 'current' | 'superseded' | 'abandoned';
92
92
 
93
+ /* Excluded from this release type: HistoryBusyError */
94
+
93
95
  /* Excluded from this release type: HistoryClockError */
94
96
 
95
97
  /* Excluded from this release type: HistoryIntegrityError */
@@ -151,6 +153,20 @@ export declare type Identity = {
151
153
 
152
154
  /* Excluded from this release type: IHistoryScope */
153
155
 
156
+ /* Excluded from this release type: IJournalAddress */
157
+
158
+ /* Excluded from this release type: IJournalCommit */
159
+
160
+ /* Excluded from this release type: IJournalDeclaration */
161
+
162
+ /* Excluded from this release type: IJournalFormat */
163
+
164
+ /* Excluded from this release type: IJournalQuery */
165
+
166
+ /* Excluded from this release type: IJournalRecord */
167
+
168
+ /* Excluded from this release type: IJournalWrite */
169
+
154
170
  /** A patch attempted to modify an immutable address or managed CAS version. @public */
155
171
  export declare class InvalidStorePatchError extends Error {
156
172
  /** Identify a structurally forbidden patch before any columns are changed. @public */
@@ -159,6 +175,14 @@ export declare class InvalidStorePatchError extends Error {
159
175
 
160
176
  /* Excluded from this release type: IOperation */
161
177
 
178
+ /* Excluded from this release type: IOperationJournal */
179
+
180
+ /* Excluded from this release type: IPromotionQuery */
181
+
182
+ /* Excluded from this release type: IPromotionRecord */
183
+
184
+ /* Excluded from this release type: IPromotionRequest */
185
+
162
186
  /* Excluded from this release type: IRecoveryOutcome */
163
187
 
164
188
  /* Excluded from this release type: IResultVerification */
@@ -197,6 +221,8 @@ declare interface ISnapshotCapability {
197
221
 
198
222
  /* Excluded from this release type: ISqliteConnection */
199
223
 
224
+ /* Excluded from this release type: ISqliteOpenOptions */
225
+
200
226
  /* Excluded from this release type: ISqliteRow */
201
227
 
202
228
  /* Excluded from this release type: ISqliteRunResult */
@@ -225,8 +251,16 @@ declare interface ISnapshotCapability {
225
251
 
226
252
  /* Excluded from this release type: IWriterAcquisitionRequest */
227
253
 
254
+ /* Excluded from this release type: IWriterContention */
255
+
228
256
  /* Excluded from this release type: IWriterLease */
229
257
 
258
+ /* Excluded from this release type: IWriterRenewal */
259
+
260
+ /* Excluded from this release type: JournalConflictError */
261
+
262
+ /* Excluded from this release type: JournalVersionError */
263
+
230
264
  /** Options for the isolated, non-durable test backend. @public */
231
265
  export declare interface MemoryStoreOptions {
232
266
  /** Metadata compatibility identifier; the initial store format uses sha256. */
@@ -298,6 +332,8 @@ export declare type ResultKey = {
298
332
  subjectHash: string;
299
333
  };
300
334
 
335
+ /* Excluded from this release type: SqliteBusyError */
336
+
301
337
  /* Excluded from this release type: StaleWriterError */
302
338
 
303
339
  /**
@@ -90,6 +90,8 @@ export declare interface GenerationRow {
90
90
  /** Retained lifecycle states interpreted by repository and claim, not by storage. @public */
91
91
  export declare type GenerationState = 'claimed' | 'current' | 'superseded' | 'abandoned';
92
92
 
93
+ /* Excluded from this release type: HistoryBusyError */
94
+
93
95
  /* Excluded from this release type: HistoryClockError */
94
96
 
95
97
  /* Excluded from this release type: HistoryIntegrityError */
@@ -151,6 +153,20 @@ export declare type Identity = {
151
153
 
152
154
  /* Excluded from this release type: IHistoryScope */
153
155
 
156
+ /* Excluded from this release type: IJournalAddress */
157
+
158
+ /* Excluded from this release type: IJournalCommit */
159
+
160
+ /* Excluded from this release type: IJournalDeclaration */
161
+
162
+ /* Excluded from this release type: IJournalFormat */
163
+
164
+ /* Excluded from this release type: IJournalQuery */
165
+
166
+ /* Excluded from this release type: IJournalRecord */
167
+
168
+ /* Excluded from this release type: IJournalWrite */
169
+
154
170
  /** A patch attempted to modify an immutable address or managed CAS version. @public */
155
171
  export declare class InvalidStorePatchError extends Error {
156
172
  /** Identify a structurally forbidden patch before any columns are changed. @public */
@@ -159,6 +175,14 @@ export declare class InvalidStorePatchError extends Error {
159
175
 
160
176
  /* Excluded from this release type: IOperation */
161
177
 
178
+ /* Excluded from this release type: IOperationJournal */
179
+
180
+ /* Excluded from this release type: IPromotionQuery */
181
+
182
+ /* Excluded from this release type: IPromotionRecord */
183
+
184
+ /* Excluded from this release type: IPromotionRequest */
185
+
162
186
  /* Excluded from this release type: IRecoveryOutcome */
163
187
 
164
188
  /* Excluded from this release type: IResultVerification */
@@ -197,6 +221,8 @@ declare interface ISnapshotCapability {
197
221
 
198
222
  /* Excluded from this release type: ISqliteConnection */
199
223
 
224
+ /* Excluded from this release type: ISqliteOpenOptions */
225
+
200
226
  /* Excluded from this release type: ISqliteRow */
201
227
 
202
228
  /* Excluded from this release type: ISqliteRunResult */
@@ -225,8 +251,16 @@ declare interface ISnapshotCapability {
225
251
 
226
252
  /* Excluded from this release type: IWriterAcquisitionRequest */
227
253
 
254
+ /* Excluded from this release type: IWriterContention */
255
+
228
256
  /* Excluded from this release type: IWriterLease */
229
257
 
258
+ /* Excluded from this release type: IWriterRenewal */
259
+
260
+ /* Excluded from this release type: JournalConflictError */
261
+
262
+ /* Excluded from this release type: JournalVersionError */
263
+
230
264
  /** Options for the isolated, non-durable test backend. @public */
231
265
  export declare interface MemoryStoreOptions {
232
266
  /** Metadata compatibility identifier; the initial store format uses sha256. */
@@ -298,6 +332,8 @@ export declare type ResultKey = {
298
332
  subjectHash: string;
299
333
  };
300
334
 
335
+ /* Excluded from this release type: SqliteBusyError */
336
+
301
337
  /* Excluded from this release type: StaleWriterError */
302
338
 
303
339
  /**