@peerbit/shared-log 13.2.24 → 13.2.25
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.
- package/dist/src/checked-prune.d.ts +12 -0
- package/dist/src/checked-prune.d.ts.map +1 -1
- package/dist/src/checked-prune.js +33 -0
- package/dist/src/checked-prune.js.map +1 -1
- package/dist/src/coordinate-persistence.d.ts +211 -0
- package/dist/src/coordinate-persistence.d.ts.map +1 -0
- package/dist/src/coordinate-persistence.js +1133 -0
- package/dist/src/coordinate-persistence.js.map +1 -0
- package/dist/src/errors.d.ts +1 -0
- package/dist/src/errors.d.ts.map +1 -1
- package/dist/src/errors.js +19 -0
- package/dist/src/errors.js.map +1 -1
- package/dist/src/index.d.ts +127 -133
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +1400 -4269
- package/dist/src/index.js.map +1 -1
- package/dist/src/instance-lifecycle.d.ts +117 -0
- package/dist/src/instance-lifecycle.d.ts.map +1 -0
- package/dist/src/instance-lifecycle.js +254 -0
- package/dist/src/instance-lifecycle.js.map +1 -0
- package/dist/src/join-warmup.d.ts +86 -0
- package/dist/src/join-warmup.d.ts.map +1 -0
- package/dist/src/join-warmup.js +351 -0
- package/dist/src/join-warmup.js.map +1 -0
- package/dist/src/native-write-through-block-store.d.ts +123 -0
- package/dist/src/native-write-through-block-store.d.ts.map +1 -0
- package/dist/src/native-write-through-block-store.js +989 -0
- package/dist/src/native-write-through-block-store.js.map +1 -0
- package/dist/src/peer-session.d.ts +117 -0
- package/dist/src/peer-session.d.ts.map +1 -0
- package/dist/src/peer-session.js +259 -0
- package/dist/src/peer-session.js.map +1 -0
- package/dist/src/replication-announcement.d.ts +116 -0
- package/dist/src/replication-announcement.d.ts.map +1 -0
- package/dist/src/replication-announcement.js +515 -0
- package/dist/src/replication-announcement.js.map +1 -0
- package/dist/src/replicator-liveness.d.ts +59 -0
- package/dist/src/replicator-liveness.d.ts.map +1 -0
- package/dist/src/replicator-liveness.js +304 -0
- package/dist/src/replicator-liveness.js.map +1 -0
- package/dist/src/sync/dispatch-lifecycle.d.ts +48 -0
- package/dist/src/sync/dispatch-lifecycle.d.ts.map +1 -0
- package/dist/src/sync/dispatch-lifecycle.js +141 -0
- package/dist/src/sync/dispatch-lifecycle.js.map +1 -0
- package/dist/src/sync/factory.d.ts +29 -0
- package/dist/src/sync/factory.d.ts.map +1 -0
- package/dist/src/sync/factory.js +87 -0
- package/dist/src/sync/factory.js.map +1 -0
- package/dist/src/sync/pending-sync-store.d.ts +105 -0
- package/dist/src/sync/pending-sync-store.d.ts.map +1 -0
- package/dist/src/sync/pending-sync-store.js +877 -0
- package/dist/src/sync/pending-sync-store.js.map +1 -0
- package/dist/src/sync/rateless-iblt.d.ts +4 -1
- package/dist/src/sync/rateless-iblt.d.ts.map +1 -1
- package/dist/src/sync/rateless-iblt.js +102 -106
- package/dist/src/sync/rateless-iblt.js.map +1 -1
- package/dist/src/sync/simple.d.ts +10 -41
- package/dist/src/sync/simple.d.ts.map +1 -1
- package/dist/src/sync/simple.js +259 -952
- package/dist/src/sync/simple.js.map +1 -1
- package/dist/src/sync/sync-peer-state.d.ts +16 -0
- package/dist/src/sync/sync-peer-state.d.ts.map +1 -0
- package/dist/src/sync/sync-peer-state.js +82 -0
- package/dist/src/sync/sync-peer-state.js.map +1 -0
- package/package.json +9 -9
- package/src/checked-prune.ts +35 -0
- package/src/coordinate-persistence.ts +1796 -0
- package/src/errors.ts +21 -0
- package/src/index.ts +4014 -7858
- package/src/instance-lifecycle.ts +351 -0
- package/src/join-warmup.ts +507 -0
- package/src/native-write-through-block-store.ts +1170 -0
- package/src/peer-session.ts +336 -0
- package/src/replication-announcement.ts +744 -0
- package/src/replicator-liveness.ts +439 -0
- package/src/sync/dispatch-lifecycle.ts +230 -0
- package/src/sync/factory.ts +154 -0
- package/src/sync/pending-sync-store.ts +1085 -0
- package/src/sync/rateless-iblt.ts +122 -132
- package/src/sync/simple.ts +334 -1144
- package/src/sync/sync-peer-state.ts +107 -0
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
export type InstanceLifecyclePhase = "opening" | "active" | "poisoned" | "terminating" | "closed";
|
|
2
|
+
export type InstanceLifecycleTerminalReason = "close" | "drop" | "internal-close";
|
|
3
|
+
export type InstanceLifecycleDeps = {
|
|
4
|
+
/** host._instanceLifecycle — identity anchor for isCurrent() */
|
|
5
|
+
getCurrentLifecycle: () => InstanceLifecycle | undefined;
|
|
6
|
+
/** host._closeController */
|
|
7
|
+
getCloseController: () => AbortController | undefined;
|
|
8
|
+
/** host._replicationRangeMutationFailure (poison latch, fence A2) */
|
|
9
|
+
getPoisonFailure: () => unknown;
|
|
10
|
+
/** host.closed */
|
|
11
|
+
isHostClosed: () => boolean;
|
|
12
|
+
/** host.isTerminating() — closed || parent-detach || closeController aborted */
|
|
13
|
+
isHostTerminating: () => boolean;
|
|
14
|
+
/** host._checkedPrune — identity only, never dereferenced (fence A3) */
|
|
15
|
+
getCheckedPruneCoordinator: () => object | undefined;
|
|
16
|
+
/** host._replicationRangeMutationsClosing (terminal lane fence, A4) */
|
|
17
|
+
areRangeMutationsClosing: () => boolean;
|
|
18
|
+
/** host._pruneRemovesClosing (terminal lane fence, A4) */
|
|
19
|
+
arePruneRemovesClosing: () => boolean;
|
|
20
|
+
/** host.pruneDebouncedFn — identity only */
|
|
21
|
+
getPruneDebouncer: () => object | undefined;
|
|
22
|
+
/** host.replicationChangeDebounceFn — identity only */
|
|
23
|
+
getReplicationChangeDebouncer: () => object | undefined;
|
|
24
|
+
/** host.rebalanceParticipationDebounced — identity only */
|
|
25
|
+
getRebalanceDebouncer: () => object | undefined;
|
|
26
|
+
};
|
|
27
|
+
export declare class InstanceLifecycle {
|
|
28
|
+
private readonly deps;
|
|
29
|
+
roleGeneration: number;
|
|
30
|
+
_receiveOwnershipRevision: number;
|
|
31
|
+
_receiveOwnershipMutationAdmissions: number;
|
|
32
|
+
readonly ownershipLifecycleController: AbortController;
|
|
33
|
+
membershipLifecycleController?: AbortController;
|
|
34
|
+
declaredPhase: InstanceLifecyclePhase;
|
|
35
|
+
terminalReason?: InstanceLifecycleTerminalReason;
|
|
36
|
+
poisonCause?: unknown;
|
|
37
|
+
constructor(deps: InstanceLifecycleDeps);
|
|
38
|
+
markOpenComplete(): void;
|
|
39
|
+
beginTerminal(reason: InstanceLifecycleTerminalReason): void;
|
|
40
|
+
markPoisoned(cause: unknown): void;
|
|
41
|
+
/** ≡ legacy SharedLog.stopRepairLifecycle body (`controller?.abort()`),
|
|
42
|
+
* and the abort half of legacy startRepairLifecycle. Abort-in-place: the
|
|
43
|
+
* lifecycle identity is untouched (the poison contract — poison never
|
|
44
|
+
* rotates the lifecycle, so captures keep passing the identity term and
|
|
45
|
+
* fail on `signal.aborted`/poison exactly as before). */
|
|
46
|
+
abortOwnership(): void;
|
|
47
|
+
/** ≡ the legacy guarded abort in stopSubscriptionChangeCallbackAdmission:
|
|
48
|
+
* `if (!c?.signal.aborted) c?.abort(reason)`. */
|
|
49
|
+
abortMembership(reason?: unknown): void;
|
|
50
|
+
/** ≡ legacy `this._replicationLifecycleController = new AbortController()`
|
|
51
|
+
* in resetSubscriptionChangeCallbackTracking. Called exactly once per
|
|
52
|
+
* lifecycle, from open(); plain assignment kept (KEEP-OLD overwrite: the
|
|
53
|
+
* predecessor either is undefined or was aborted at close/drop). A
|
|
54
|
+
* direct out-of-open rotation (test-only) leaves the NEW lifecycle's
|
|
55
|
+
* membership undefined until the next open — a deliberate divergence
|
|
56
|
+
* from legacy, where the host field survived direct rotations; the two
|
|
57
|
+
* observables that path uses are pinned in the spec. */
|
|
58
|
+
beginMembership(): AbortController;
|
|
59
|
+
bumpRoleGeneration(): number;
|
|
60
|
+
isRoleCurrent(capturedRoleGeneration: number): boolean;
|
|
61
|
+
isCurrent(): boolean;
|
|
62
|
+
phase(): InstanceLifecyclePhase;
|
|
63
|
+
/** ≡ SharedLog.isRepairLifecycleActive(controller). Stage 4 note: the
|
|
64
|
+
* identity term compares against the OWNED controller. For a stale
|
|
65
|
+
* captured lifecycle with its co-captured controller the term now
|
|
66
|
+
* passes where the legacy host-current compare failed; the predicate
|
|
67
|
+
* still returns false via `signal.aborted`, guaranteed by the rotation
|
|
68
|
+
* invariant (non-current ⇒ abortOwnership already ran — see the field
|
|
69
|
+
* comment above). */
|
|
70
|
+
isActiveFor(controller: AbortController | undefined): boolean;
|
|
71
|
+
/**
|
|
72
|
+
* Controller-free form for stage-3 seams. Because this object OWNS its
|
|
73
|
+
* ownership controller (stage 4), lifecycle and controller rotate
|
|
74
|
+
* together by construction, so `capturedLifecycle.isActive()` ⇔
|
|
75
|
+
* `isRepairLifecycleActive(capturedController)` for captures taken
|
|
76
|
+
* together — the equivalence the unit spec asserts.
|
|
77
|
+
*/
|
|
78
|
+
isActive(): boolean;
|
|
79
|
+
/** ≡ SharedLog.throwIfReplicationOwnershipPoisoned — message and `cause`
|
|
80
|
+
* must stay byte-identical for stage-3 drop-in. */
|
|
81
|
+
throwIfPoisoned(): void;
|
|
82
|
+
/** ≡ SharedLog.throwIfReplicationOwnershipLifecycleInactive. */
|
|
83
|
+
throwIfInactive(controller?: AbortController | undefined): void;
|
|
84
|
+
/** ≡ SharedLog.captureReplicationOwnershipLifecycle, but returns the
|
|
85
|
+
* lifecycle; stage-3 sites capture this instead of the raw controller
|
|
86
|
+
* (which stays reachable via ownershipSignal()). */
|
|
87
|
+
capture(): InstanceLifecycle;
|
|
88
|
+
/** AbortControllers stay the signal carriers. */
|
|
89
|
+
ownershipSignal(): AbortSignal | undefined;
|
|
90
|
+
/** ≡ SharedLog.isReplicationLifecycleActive(controller).
|
|
91
|
+
* NOTE the asymmetry vs isActiveFor: this side uses isTerminating()
|
|
92
|
+
* (closeController + parent-detach), not `closed` — preserve exactly. */
|
|
93
|
+
isMembershipActiveFor(controller: AbortController | undefined): boolean;
|
|
94
|
+
membershipSignal(): AbortSignal | undefined;
|
|
95
|
+
closeSignal(): AbortSignal | undefined;
|
|
96
|
+
/** ≡ prune()'s isCheckedPruneLifecycleCurrent triple for captures taken
|
|
97
|
+
* at the same admission point. Stage 3 extension: an omitted
|
|
98
|
+
* `closeController` SKIPS that term (the non-prune() checked-prune seats
|
|
99
|
+
* never compared it — adding the compare would strengthen their
|
|
100
|
+
* predicates), and `controller` lets a seat honor an explicitly threaded
|
|
101
|
+
* (possibly stale) ownership capture instead of the current one. */
|
|
102
|
+
isCheckedPruneCurrent(coordinator: object | undefined, closeController?: AbortController, controller?: AbortController | undefined): boolean;
|
|
103
|
+
/** Exact fold of prune()'s throwIfCheckedPruneLifecycleInactive and of
|
|
104
|
+
* revalidateCheckedPruneOwnership's controller branch (there with the
|
|
105
|
+
* closeController term omitted). Error order MUST stay: poison Error →
|
|
106
|
+
* ownership TerminalOperationNotStartedError ("Replication ownership
|
|
107
|
+
* lifecycle is no longer active") → checked-prune
|
|
108
|
+
* TerminalOperationNotStartedError ("Checked prune lifecycle is no
|
|
109
|
+
* longer active"). */
|
|
110
|
+
throwIfCheckedPruneInactive(coordinator: object | undefined, closeController?: AbortController, controller?: AbortController | undefined): void;
|
|
111
|
+
areRangeMutationsClosing(): boolean;
|
|
112
|
+
arePruneRemovesClosing(): boolean;
|
|
113
|
+
isPruneDebouncerCurrent(fn: object | undefined): boolean;
|
|
114
|
+
isReplicationChangeDebouncerCurrent(fn: object | undefined): boolean;
|
|
115
|
+
isRebalanceDebouncerCurrent(fn: object | undefined): boolean;
|
|
116
|
+
}
|
|
117
|
+
//# sourceMappingURL=instance-lifecycle.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-lifecycle.d.ts","sourceRoot":"","sources":["../../src/instance-lifecycle.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,254 @@
|
|
|
1
|
+
// One InstanceLifecycle per SharedLog.open(). Stage 2 of the
|
|
2
|
+
// session/lifecycle refactor introduced the object as a WRAPPER over the
|
|
3
|
+
// existing fences via late-bound readers; stage 3 migrated the documented
|
|
4
|
+
// multi-fence seams onto this API; stage 4 makes it the physical owner of
|
|
5
|
+
// the per-open state: the role sub-generation, the receive-ownership
|
|
6
|
+
// counters, and the ownership/membership AbortControllers themselves (the
|
|
7
|
+
// index.ts ratchet entries moved file-to-file into this file's baseline in
|
|
8
|
+
// scripts/ci/check-fence-ratchet.mjs). The remaining deps are late-bound
|
|
9
|
+
// readers for host state that outlives any single lifecycle (poison latch,
|
|
10
|
+
// close controller, coordinator/debouncer identities).
|
|
11
|
+
import { TerminalOperationNotStartedError } from "@peerbit/program";
|
|
12
|
+
export class InstanceLifecycle {
|
|
13
|
+
deps;
|
|
14
|
+
// The ONLY state that physically moved in stage 2 (absorbed the former
|
|
15
|
+
// SharedLog._localReplicationRoleGeneration; the accessor shim was deleted
|
|
16
|
+
// in stage 3). Bumped by replicate()'s
|
|
17
|
+
// fixed-role replacement and by full unreplication WITHOUT rotating the
|
|
18
|
+
// lifecycle: unreplicate() deliberately keeps the store open, so admitted
|
|
19
|
+
// adaptive planners are invalidated by this sub-generation, not by
|
|
20
|
+
// retiring the instance identity.
|
|
21
|
+
roleGeneration = 0;
|
|
22
|
+
// Moved from SharedLog (fences C1/C2, same names — the sanctioned
|
|
23
|
+
// file-to-file ratchet move). Physically owned per-open counters read and
|
|
24
|
+
// written directly through the lifecycle owner; the fresh lifecycle object
|
|
25
|
+
// at open() IS the legacy reset-to-0 (same pattern as roleGeneration above).
|
|
26
|
+
//
|
|
27
|
+
// Receive-side ownership plans may span lower-log joins that invoke user
|
|
28
|
+
// code. Incremented synchronously with leader-cache invalidation so the
|
|
29
|
+
// handler can detect whether its pre-join plan needs one fresh
|
|
30
|
+
// post-persist audit.
|
|
31
|
+
_receiveOwnershipRevision = 0;
|
|
32
|
+
// Count of ownership-changing range mutations from queue admission
|
|
33
|
+
// through settlement, including mutations already pending when a receive
|
|
34
|
+
// starts.
|
|
35
|
+
_receiveOwnershipMutationAdmissions = 0;
|
|
36
|
+
// ---- stage 4: physically owned controllers (moved from SharedLog) ----
|
|
37
|
+
// Fences A1/A5; the index.ts ratchet entries _repairLifecycleController /
|
|
38
|
+
// _replicationLifecycleController moved file-to-file under these names.
|
|
39
|
+
// Rotate-with-the-lifecycle by construction: a fresh InstanceLifecycle IS
|
|
40
|
+
// the rotation of both controllers; within one lifecycle the ownership
|
|
41
|
+
// controller identity never changes (readonly) — poison and terminal
|
|
42
|
+
// paths abort it IN PLACE, exactly like the legacy un-reassigned host
|
|
43
|
+
// field. Background repair work can outlive the await that admitted it;
|
|
44
|
+
// the per-open replacement of this whole object keeps an older runner
|
|
45
|
+
// from dispatching into or mutating a freshly opened lifecycle.
|
|
46
|
+
//
|
|
47
|
+
// INVARIANT every rotation site must keep: whatever installs a new
|
|
48
|
+
// host._instanceLifecycle aborts the outgoing lifecycle's ownership
|
|
49
|
+
// controller in the same synchronous block (startRepairLifecycle does).
|
|
50
|
+
// The stale-capture predicates in isActiveFor lean on
|
|
51
|
+
// non-current ⇒ aborted now that the identity term compares against the
|
|
52
|
+
// owned field rather than the host-current controller.
|
|
53
|
+
ownershipLifecycleController = new AbortController();
|
|
54
|
+
// undefined until open() reaches resetSubscriptionChangeCallbackTracking
|
|
55
|
+
// (beginMembership) — preserves the legacy `?: AbortController` decl-site
|
|
56
|
+
// semantics for constructed-but-never-opened hosts.
|
|
57
|
+
membershipLifecycleController;
|
|
58
|
+
// Stage-2 bookkeeping. WRITE-ONLY in production paths: no query method
|
|
59
|
+
// consults these (phase() is derived from the wrapped fences), so a
|
|
60
|
+
// missed or doubled transition cannot change behavior. Stage 3 flips
|
|
61
|
+
// phase() onto declaredPhase once the transitions have soaked in CI.
|
|
62
|
+
declaredPhase = "opening";
|
|
63
|
+
terminalReason;
|
|
64
|
+
poisonCause;
|
|
65
|
+
constructor(deps) {
|
|
66
|
+
this.deps = deps;
|
|
67
|
+
}
|
|
68
|
+
// ---- rotation-point transitions (stage 2: diagnostics only) ----
|
|
69
|
+
markOpenComplete() {
|
|
70
|
+
if (this.declaredPhase === "opening")
|
|
71
|
+
this.declaredPhase = "active";
|
|
72
|
+
}
|
|
73
|
+
beginTerminal(reason) {
|
|
74
|
+
this.terminalReason ??= reason;
|
|
75
|
+
if (this.declaredPhase !== "poisoned")
|
|
76
|
+
this.declaredPhase = "terminating";
|
|
77
|
+
}
|
|
78
|
+
markPoisoned(cause) {
|
|
79
|
+
this.poisonCause ??= cause;
|
|
80
|
+
this.declaredPhase = "poisoned";
|
|
81
|
+
}
|
|
82
|
+
// ---- owned-controller transitions (stage 4) ----
|
|
83
|
+
/** ≡ legacy SharedLog.stopRepairLifecycle body (`controller?.abort()`),
|
|
84
|
+
* and the abort half of legacy startRepairLifecycle. Abort-in-place: the
|
|
85
|
+
* lifecycle identity is untouched (the poison contract — poison never
|
|
86
|
+
* rotates the lifecycle, so captures keep passing the identity term and
|
|
87
|
+
* fail on `signal.aborted`/poison exactly as before). */
|
|
88
|
+
abortOwnership() {
|
|
89
|
+
this.ownershipLifecycleController.abort();
|
|
90
|
+
}
|
|
91
|
+
/** ≡ the legacy guarded abort in stopSubscriptionChangeCallbackAdmission:
|
|
92
|
+
* `if (!c?.signal.aborted) c?.abort(reason)`. */
|
|
93
|
+
abortMembership(reason) {
|
|
94
|
+
if (!this.membershipLifecycleController?.signal.aborted) {
|
|
95
|
+
this.membershipLifecycleController?.abort(reason);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
/** ≡ legacy `this._replicationLifecycleController = new AbortController()`
|
|
99
|
+
* in resetSubscriptionChangeCallbackTracking. Called exactly once per
|
|
100
|
+
* lifecycle, from open(); plain assignment kept (KEEP-OLD overwrite: the
|
|
101
|
+
* predecessor either is undefined or was aborted at close/drop). A
|
|
102
|
+
* direct out-of-open rotation (test-only) leaves the NEW lifecycle's
|
|
103
|
+
* membership undefined until the next open — a deliberate divergence
|
|
104
|
+
* from legacy, where the host field survived direct rotations; the two
|
|
105
|
+
* observables that path uses are pinned in the spec. */
|
|
106
|
+
beginMembership() {
|
|
107
|
+
return (this.membershipLifecycleController = new AbortController());
|
|
108
|
+
}
|
|
109
|
+
// ---- role sub-generation (absorbed fence A6) ----
|
|
110
|
+
bumpRoleGeneration() {
|
|
111
|
+
return ++this.roleGeneration;
|
|
112
|
+
}
|
|
113
|
+
isRoleCurrent(capturedRoleGeneration) {
|
|
114
|
+
return this.roleGeneration === capturedRoleGeneration;
|
|
115
|
+
}
|
|
116
|
+
// ---- identity ----
|
|
117
|
+
isCurrent() {
|
|
118
|
+
return this.deps.getCurrentLifecycle() === this;
|
|
119
|
+
}
|
|
120
|
+
// ---- derived phase (single source of truth = the wrapped fences) ----
|
|
121
|
+
phase() {
|
|
122
|
+
if (this.deps.getPoisonFailure() !== undefined)
|
|
123
|
+
return "poisoned";
|
|
124
|
+
if (this.deps.isHostClosed())
|
|
125
|
+
return "closed";
|
|
126
|
+
// The legacy `ownership == null` arm is gone: a lifecycle object owns
|
|
127
|
+
// its controller, so the absent-controller state is unrepresentable
|
|
128
|
+
// (clones have no lifecycle and cannot reach phase()).
|
|
129
|
+
if (!this.isCurrent() || this.ownershipLifecycleController.signal.aborted) {
|
|
130
|
+
return "terminating";
|
|
131
|
+
}
|
|
132
|
+
return this.declaredPhase === "opening" ? "opening" : "active";
|
|
133
|
+
}
|
|
134
|
+
// ---- ownership half: exact folds of the legacy predicates ----
|
|
135
|
+
/** ≡ SharedLog.isRepairLifecycleActive(controller). Stage 4 note: the
|
|
136
|
+
* identity term compares against the OWNED controller. For a stale
|
|
137
|
+
* captured lifecycle with its co-captured controller the term now
|
|
138
|
+
* passes where the legacy host-current compare failed; the predicate
|
|
139
|
+
* still returns false via `signal.aborted`, guaranteed by the rotation
|
|
140
|
+
* invariant (non-current ⇒ abortOwnership already ran — see the field
|
|
141
|
+
* comment above). */
|
|
142
|
+
isActiveFor(controller) {
|
|
143
|
+
return (controller != null &&
|
|
144
|
+
controller === this.ownershipLifecycleController &&
|
|
145
|
+
!controller.signal.aborted &&
|
|
146
|
+
this.deps.getPoisonFailure() === undefined &&
|
|
147
|
+
!this.deps.isHostClosed());
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* Controller-free form for stage-3 seams. Because this object OWNS its
|
|
151
|
+
* ownership controller (stage 4), lifecycle and controller rotate
|
|
152
|
+
* together by construction, so `capturedLifecycle.isActive()` ⇔
|
|
153
|
+
* `isRepairLifecycleActive(capturedController)` for captures taken
|
|
154
|
+
* together — the equivalence the unit spec asserts.
|
|
155
|
+
*/
|
|
156
|
+
isActive() {
|
|
157
|
+
return (this.isCurrent() && this.isActiveFor(this.ownershipLifecycleController));
|
|
158
|
+
}
|
|
159
|
+
/** ≡ SharedLog.throwIfReplicationOwnershipPoisoned — message and `cause`
|
|
160
|
+
* must stay byte-identical for stage-3 drop-in. */
|
|
161
|
+
throwIfPoisoned() {
|
|
162
|
+
const failure = this.deps.getPoisonFailure();
|
|
163
|
+
if (failure !== undefined) {
|
|
164
|
+
throw new Error("Replication ownership recovery is required before further planning", { cause: failure });
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
/** ≡ SharedLog.throwIfReplicationOwnershipLifecycleInactive. */
|
|
168
|
+
throwIfInactive(controller = this.ownershipLifecycleController) {
|
|
169
|
+
this.throwIfPoisoned();
|
|
170
|
+
if (!(this.isCurrent() && this.isActiveFor(controller))) {
|
|
171
|
+
throw new TerminalOperationNotStartedError("Replication ownership lifecycle is no longer active");
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
/** ≡ SharedLog.captureReplicationOwnershipLifecycle, but returns the
|
|
175
|
+
* lifecycle; stage-3 sites capture this instead of the raw controller
|
|
176
|
+
* (which stays reachable via ownershipSignal()). */
|
|
177
|
+
capture() {
|
|
178
|
+
this.throwIfInactive();
|
|
179
|
+
return this;
|
|
180
|
+
}
|
|
181
|
+
/** AbortControllers stay the signal carriers. */
|
|
182
|
+
ownershipSignal() {
|
|
183
|
+
return this.ownershipLifecycleController.signal;
|
|
184
|
+
}
|
|
185
|
+
// ---- membership half (fence A5): exact fold ----
|
|
186
|
+
/** ≡ SharedLog.isReplicationLifecycleActive(controller).
|
|
187
|
+
* NOTE the asymmetry vs isActiveFor: this side uses isTerminating()
|
|
188
|
+
* (closeController + parent-detach), not `closed` — preserve exactly. */
|
|
189
|
+
isMembershipActiveFor(controller) {
|
|
190
|
+
return (controller != null &&
|
|
191
|
+
controller === this.membershipLifecycleController &&
|
|
192
|
+
!controller.signal.aborted &&
|
|
193
|
+
!this.deps.isHostTerminating());
|
|
194
|
+
}
|
|
195
|
+
membershipSignal() {
|
|
196
|
+
return this.membershipLifecycleController?.signal;
|
|
197
|
+
}
|
|
198
|
+
closeSignal() {
|
|
199
|
+
return this.deps.getCloseController()?.signal;
|
|
200
|
+
}
|
|
201
|
+
// ---- checked-prune identity (seams 4 and 7) ----
|
|
202
|
+
/** ≡ prune()'s isCheckedPruneLifecycleCurrent triple for captures taken
|
|
203
|
+
* at the same admission point. Stage 3 extension: an omitted
|
|
204
|
+
* `closeController` SKIPS that term (the non-prune() checked-prune seats
|
|
205
|
+
* never compared it — adding the compare would strengthen their
|
|
206
|
+
* predicates), and `controller` lets a seat honor an explicitly threaded
|
|
207
|
+
* (possibly stale) ownership capture instead of the current one. */
|
|
208
|
+
isCheckedPruneCurrent(coordinator, closeController, controller = this.ownershipLifecycleController) {
|
|
209
|
+
return (this.isCurrent() &&
|
|
210
|
+
this.isActiveFor(controller) &&
|
|
211
|
+
coordinator === this.deps.getCheckedPruneCoordinator() &&
|
|
212
|
+
(closeController === undefined ||
|
|
213
|
+
closeController === this.deps.getCloseController()));
|
|
214
|
+
}
|
|
215
|
+
/** Exact fold of prune()'s throwIfCheckedPruneLifecycleInactive and of
|
|
216
|
+
* revalidateCheckedPruneOwnership's controller branch (there with the
|
|
217
|
+
* closeController term omitted). Error order MUST stay: poison Error →
|
|
218
|
+
* ownership TerminalOperationNotStartedError ("Replication ownership
|
|
219
|
+
* lifecycle is no longer active") → checked-prune
|
|
220
|
+
* TerminalOperationNotStartedError ("Checked prune lifecycle is no
|
|
221
|
+
* longer active"). */
|
|
222
|
+
throwIfCheckedPruneInactive(coordinator, closeController, controller = this.ownershipLifecycleController) {
|
|
223
|
+
this.throwIfInactive(controller);
|
|
224
|
+
if (coordinator !== this.deps.getCheckedPruneCoordinator() ||
|
|
225
|
+
(closeController !== undefined &&
|
|
226
|
+
closeController !== this.deps.getCloseController())) {
|
|
227
|
+
throw new TerminalOperationNotStartedError("Checked prune lifecycle is no longer active");
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
// ---- terminal lane fences (A4): exposed, NOT folded into isActive ----
|
|
231
|
+
// Folding them would change which TerminalOperationNotStartedError message
|
|
232
|
+
// the admission sites throw ("Replication range mutations are closing",
|
|
233
|
+
// "Prune removals are closing") — a behavior change.
|
|
234
|
+
areRangeMutationsClosing() {
|
|
235
|
+
return this.deps.areRangeMutationsClosing();
|
|
236
|
+
}
|
|
237
|
+
arePruneRemovesClosing() {
|
|
238
|
+
return this.deps.arePruneRemovesClosing();
|
|
239
|
+
}
|
|
240
|
+
// ---- debouncer identities (seam 6 et al.) ----
|
|
241
|
+
// Bare === on purpose: at rebalanceParticipation the captured default
|
|
242
|
+
// parameter may be undefined and `undefined === undefined` legitimately
|
|
243
|
+
// passes today. A null-guard would break that.
|
|
244
|
+
isPruneDebouncerCurrent(fn) {
|
|
245
|
+
return fn === this.deps.getPruneDebouncer();
|
|
246
|
+
}
|
|
247
|
+
isReplicationChangeDebouncerCurrent(fn) {
|
|
248
|
+
return fn === this.deps.getReplicationChangeDebouncer();
|
|
249
|
+
}
|
|
250
|
+
isRebalanceDebouncerCurrent(fn) {
|
|
251
|
+
return fn === this.deps.getRebalanceDebouncer();
|
|
252
|
+
}
|
|
253
|
+
}
|
|
254
|
+
//# sourceMappingURL=instance-lifecycle.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-lifecycle.js","sourceRoot":"","sources":["../../src/instance-lifecycle.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* One WarmupSession per join-warmup attempt window for a target. The
|
|
3
|
+
* instance IS the legacy opaque generation token — always compared by
|
|
4
|
+
* identity, never inspected — now carrying diagnostics. Rotation points are
|
|
5
|
+
* unchanged: created on demand, dropped at cancelJoinWarmupTarget so the
|
|
6
|
+
* next touch mints a fresh identity. Deliberately NOT hosted on
|
|
7
|
+
* PeerSession: warmup windows rotate independently of subscription epochs
|
|
8
|
+
* (poison and committed removals leave the subscription session alone), and
|
|
9
|
+
* a warmup target may have no session at all — auto-creating one as a
|
|
10
|
+
* warmup side effect would flip `isCurrent(peer, null)` from true to false
|
|
11
|
+
* at every receive-admission seat.
|
|
12
|
+
*/
|
|
13
|
+
export declare class WarmupSession {
|
|
14
|
+
readonly target: string;
|
|
15
|
+
readonly createdAt: number;
|
|
16
|
+
constructor(target: string);
|
|
17
|
+
}
|
|
18
|
+
export type JoinWarmupSendState<E> = {
|
|
19
|
+
bypassKnownPeerHints: boolean;
|
|
20
|
+
entries: Map<string, E>;
|
|
21
|
+
session: WarmupSession;
|
|
22
|
+
lastCompletedAt: number;
|
|
23
|
+
pending: boolean;
|
|
24
|
+
running: boolean;
|
|
25
|
+
};
|
|
26
|
+
export type JoinWarmupRetryTimer = {
|
|
27
|
+
handle: ReturnType<typeof setTimeout>;
|
|
28
|
+
resolve?: () => void;
|
|
29
|
+
};
|
|
30
|
+
export type JoinWarmupScheduledRetryBatch<E> = {
|
|
31
|
+
bypassKnownPeerHints: boolean;
|
|
32
|
+
entries: Map<string, E>;
|
|
33
|
+
remainingAttempts: number;
|
|
34
|
+
};
|
|
35
|
+
export type JoinWarmupScheduledRetryCohort<E> = {
|
|
36
|
+
batches: JoinWarmupScheduledRetryBatch<E>[];
|
|
37
|
+
dueAt: number;
|
|
38
|
+
};
|
|
39
|
+
export type JoinWarmupScheduledRetrySlot<E> = {
|
|
40
|
+
cohorts: JoinWarmupScheduledRetryCohort<E>[];
|
|
41
|
+
head: number;
|
|
42
|
+
timer?: JoinWarmupRetryTimer;
|
|
43
|
+
timerDueAt?: number;
|
|
44
|
+
};
|
|
45
|
+
export type JoinWarmupScheduledRetries<E> = {
|
|
46
|
+
session: WarmupSession;
|
|
47
|
+
slotsByDelay: Map<number, JoinWarmupScheduledRetrySlot<E>>;
|
|
48
|
+
};
|
|
49
|
+
export type JoinWarmupDeps<E> = {
|
|
50
|
+
isLifecycleActive: (controller: AbortController) => boolean;
|
|
51
|
+
getCurrentLifecycleController: () => AbortController;
|
|
52
|
+
getRepairRetryTimers: () => Set<ReturnType<typeof setTimeout>>;
|
|
53
|
+
isClosed: () => boolean;
|
|
54
|
+
onTargetCancelled: (target: string) => void;
|
|
55
|
+
bumpSimpleFallbackPasses: () => void;
|
|
56
|
+
sendEntriesSimple: (target: string, entries: ReadonlyMap<string, E>, options: {
|
|
57
|
+
bypassKnownPeers: boolean;
|
|
58
|
+
bypassRecentKnownPeers: boolean;
|
|
59
|
+
isStillCurrent: () => boolean;
|
|
60
|
+
signal: AbortSignal;
|
|
61
|
+
}) => Promise<void>;
|
|
62
|
+
logError: (error: any) => void;
|
|
63
|
+
};
|
|
64
|
+
export declare class JoinWarmupCoordinator<E> {
|
|
65
|
+
private readonly deps;
|
|
66
|
+
_warmupSessionsByTarget: Map<string, WarmupSession>;
|
|
67
|
+
_joinWarmupSendStateByTarget: Map<string, JoinWarmupSendState<E>>;
|
|
68
|
+
_joinWarmupRetryTimersByTarget: Map<string, Set<JoinWarmupRetryTimer>>;
|
|
69
|
+
_joinWarmupScheduledRetriesByTarget: Map<string, JoinWarmupScheduledRetries<E>>;
|
|
70
|
+
_repairSweepWarmupSessionByTarget: Map<string, WarmupSession>;
|
|
71
|
+
constructor(deps: JoinWarmupDeps<E>);
|
|
72
|
+
reset(): void;
|
|
73
|
+
ensureWarmupSession(target: string): WarmupSession;
|
|
74
|
+
clearRepairSweepWarmupSessions(): void;
|
|
75
|
+
trackJoinWarmupTimer(target: string, timer: JoinWarmupRetryTimer): void;
|
|
76
|
+
untrackJoinWarmupTimer(target: string, timer: JoinWarmupRetryTimer): void;
|
|
77
|
+
cancelJoinWarmupTimers(target: string): void;
|
|
78
|
+
cancelJoinWarmupTarget(target: string): void;
|
|
79
|
+
cancelAllJoinWarmupTargets(): void;
|
|
80
|
+
sleepJoinWarmupTracked(target: string, delayMs: number, repairLifecycleController: AbortController): Promise<void>;
|
|
81
|
+
scheduleJoinWarmupRetries(target: string, session: WarmupSession, delaysMs: Iterable<number>, entries: ReadonlyMap<string, E>, bypassKnownPeerHints: boolean, repairLifecycleController?: AbortController): void;
|
|
82
|
+
armJoinWarmupRetrySlot(target: string, scheduled: JoinWarmupScheduledRetries<E>, delayMs: number, slot: JoinWarmupScheduledRetrySlot<E>, repairLifecycleController: AbortController): void;
|
|
83
|
+
queueJoinWarmupSend(target: string, session: WarmupSession, entries: ReadonlyMap<string, E>, bypassKnownPeerHints: boolean, repairLifecycleController?: AbortController): void;
|
|
84
|
+
drainJoinWarmupSends(target: string, state: JoinWarmupSendState<E>, repairLifecycleController: AbortController): Promise<void>;
|
|
85
|
+
}
|
|
86
|
+
//# sourceMappingURL=join-warmup.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"join-warmup.d.ts","sourceRoot":"","sources":["../../src/join-warmup.ts"],"names":[],"mappings":"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"}
|