@loomwork/ui-lineage 0.0.0-stage → 0.1.1
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/LICENSE +202 -0
- package/NOTICE +8 -0
- package/README.md +471 -2
- package/dist/conformance.d.ts +4 -0
- package/dist/conformance.d.ts.map +1 -0
- package/dist/conformance.js +143 -0
- package/dist/conformance.js.map +1 -0
- package/dist/derive.d.ts +15 -0
- package/dist/derive.d.ts.map +1 -0
- package/dist/derive.js +35 -0
- package/dist/derive.js.map +1 -0
- package/dist/esm/conformance.js +140 -0
- package/dist/esm/conformance.js.map +1 -0
- package/dist/esm/derive.js +29 -0
- package/dist/esm/derive.js.map +1 -0
- package/dist/esm/events.js +101 -0
- package/dist/esm/events.js.map +1 -0
- package/dist/esm/index.js +12 -0
- package/dist/esm/index.js.map +1 -0
- package/dist/esm/lineage.js +1376 -0
- package/dist/esm/lineage.js.map +1 -0
- package/dist/esm/retention.js +73 -0
- package/dist/esm/retention.js.map +1 -0
- package/dist/esm/rootsFor.js +49 -0
- package/dist/esm/rootsFor.js.map +1 -0
- package/dist/esm/seen.js +733 -0
- package/dist/esm/seen.js.map +1 -0
- package/dist/esm/seenCrypto.js +197 -0
- package/dist/esm/seenCrypto.js.map +1 -0
- package/dist/esm/seenGc.js +122 -0
- package/dist/esm/seenGc.js.map +1 -0
- package/dist/esm/state.js +185 -0
- package/dist/esm/state.js.map +1 -0
- package/dist/esm/store.js +172 -0
- package/dist/esm/store.js.map +1 -0
- package/dist/events.d.ts +781 -0
- package/dist/events.d.ts.map +1 -0
- package/dist/events.js +106 -0
- package/dist/events.js.map +1 -0
- package/dist/index.d.ts +23 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +60 -0
- package/dist/index.js.map +1 -0
- package/dist/lineage.d.ts +394 -0
- package/dist/lineage.d.ts.map +1 -0
- package/dist/lineage.js +1383 -0
- package/dist/lineage.js.map +1 -0
- package/dist/retention.d.ts +45 -0
- package/dist/retention.d.ts.map +1 -0
- package/dist/retention.js +78 -0
- package/dist/retention.js.map +1 -0
- package/dist/rootsFor.d.ts +33 -0
- package/dist/rootsFor.d.ts.map +1 -0
- package/dist/rootsFor.js +52 -0
- package/dist/rootsFor.js.map +1 -0
- package/dist/seen.d.ts +375 -0
- package/dist/seen.d.ts.map +1 -0
- package/dist/seen.js +739 -0
- package/dist/seen.js.map +1 -0
- package/dist/seenCrypto.d.ts +72 -0
- package/dist/seenCrypto.d.ts.map +1 -0
- package/dist/seenCrypto.js +210 -0
- package/dist/seenCrypto.js.map +1 -0
- package/dist/seenGc.d.ts +73 -0
- package/dist/seenGc.d.ts.map +1 -0
- package/dist/seenGc.js +126 -0
- package/dist/seenGc.js.map +1 -0
- package/dist/state.d.ts +66 -0
- package/dist/state.d.ts.map +1 -0
- package/dist/state.js +190 -0
- package/dist/state.js.map +1 -0
- package/dist/store.d.ts +93 -0
- package/dist/store.d.ts.map +1 -0
- package/dist/store.js +177 -0
- package/dist/store.js.map +1 -0
- package/package.json +60 -3
- package/src/conformance.ts +148 -0
- package/src/derive.ts +57 -0
- package/src/events.ts +125 -0
- package/src/index.ts +79 -0
- package/src/lineage.ts +1655 -0
- package/src/retention.ts +118 -0
- package/src/rootsFor.ts +75 -0
- package/src/seen.ts +965 -0
- package/src/seenCrypto.ts +271 -0
- package/src/seenGc.ts +233 -0
- package/src/state.ts +268 -0
- package/src/store.ts +274 -0
package/dist/seen.d.ts
ADDED
|
@@ -0,0 +1,375 @@
|
|
|
1
|
+
import { type ContentStore } from "@loomwork/plugin-content";
|
|
2
|
+
import { type Audience, type DeclaredToolClasses, type ProjectionCatalog, type ReadPolicy, type SeenEntry, type SeenSnapshot, type UndeclaredToolPolicy, type Viewer } from "@loomwork/ui-core";
|
|
3
|
+
import { z } from "zod";
|
|
4
|
+
import type { Lineage, LineageResult, Refused } from "./lineage";
|
|
5
|
+
import { type SeenKeyStore } from "./seenCrypto";
|
|
6
|
+
import { type LineageStore } from "./store";
|
|
7
|
+
export declare const VIEW_RECORDED = "VIEW_RECORDED";
|
|
8
|
+
/** A retention watermark: every record at or below `floor` has rolled off. */
|
|
9
|
+
export declare const VIEWS_RETAINED = "VIEWS_RETAINED";
|
|
10
|
+
/** The viewer was erased (written AFTER the key is destroyed; a rerun completes it). */
|
|
11
|
+
export declare const VIEWER_ERASED = "VIEWER_ERASED";
|
|
12
|
+
/** The reserved-stream namespace a viewer's record lives under (distinct from the lineage's). */
|
|
13
|
+
export declare const SEEN_STREAM_PREFIX = "__loom_ui_seen__:";
|
|
14
|
+
export declare const SEEN_WORKFLOW_ID = "loom-ui.seen";
|
|
15
|
+
/** Default most views a viewer's log keeps readable; older ones roll off (never a refusal). */
|
|
16
|
+
export declare const DEFAULT_MAX_SEEN_VIEWS = 10000;
|
|
17
|
+
/** Most records one read returns. */
|
|
18
|
+
export declare const MAX_SEEN_READ = 500;
|
|
19
|
+
export declare const ViewRecordPayload: z.ZodObject<{
|
|
20
|
+
experienceId: z.ZodString;
|
|
21
|
+
versionHash: z.ZodString;
|
|
22
|
+
viewerId: z.ZodString;
|
|
23
|
+
/** The clearance the viewer held when shown the surface (informational: reads use the READER's). */
|
|
24
|
+
clearance: z.ZodOptional<z.ZodString>;
|
|
25
|
+
entries: z.ZodArray<z.ZodObject<{
|
|
26
|
+
source: z.ZodDiscriminatedUnion<"kind", [z.ZodObject<{
|
|
27
|
+
kind: z.ZodLiteral<"handle">;
|
|
28
|
+
handle: z.ZodString;
|
|
29
|
+
}, "strip", z.ZodTypeAny, {
|
|
30
|
+
kind: "handle";
|
|
31
|
+
handle: string;
|
|
32
|
+
}, {
|
|
33
|
+
kind: "handle";
|
|
34
|
+
handle: string;
|
|
35
|
+
}>, z.ZodObject<{
|
|
36
|
+
kind: z.ZodLiteral<"projection">;
|
|
37
|
+
id: z.ZodString;
|
|
38
|
+
path: z.ZodString;
|
|
39
|
+
version: z.ZodString;
|
|
40
|
+
}, "strip", z.ZodTypeAny, {
|
|
41
|
+
path: string;
|
|
42
|
+
kind: "projection";
|
|
43
|
+
id: string;
|
|
44
|
+
version: string;
|
|
45
|
+
}, {
|
|
46
|
+
path: string;
|
|
47
|
+
kind: "projection";
|
|
48
|
+
id: string;
|
|
49
|
+
version: string;
|
|
50
|
+
}>]>;
|
|
51
|
+
nodeIds: z.ZodArray<z.ZodString, "many">;
|
|
52
|
+
class: z.ZodString;
|
|
53
|
+
state: z.ZodEnum<["seen", "absent", "oversize", "over-budget", "unreadable"]>;
|
|
54
|
+
status: z.ZodOptional<z.ZodString>;
|
|
55
|
+
/** Only for `oversize` / `over-budget` (where the size is the recorded fact). A `seen` entry's size lives inside `sealed`. */
|
|
56
|
+
bytes: z.ZodOptional<z.ZodNumber>;
|
|
57
|
+
/** `{ref, bytes}`, constant-length padded and AEAD-sealed under the viewer's data key (see the header). Never a plain address. */
|
|
58
|
+
sealed: z.ZodOptional<z.ZodString>;
|
|
59
|
+
}, "strip", z.ZodTypeAny, {
|
|
60
|
+
state: "seen" | "absent" | "oversize" | "over-budget" | "unreadable";
|
|
61
|
+
source: {
|
|
62
|
+
kind: "handle";
|
|
63
|
+
handle: string;
|
|
64
|
+
} | {
|
|
65
|
+
path: string;
|
|
66
|
+
kind: "projection";
|
|
67
|
+
id: string;
|
|
68
|
+
version: string;
|
|
69
|
+
};
|
|
70
|
+
nodeIds: string[];
|
|
71
|
+
class: string;
|
|
72
|
+
status?: string | undefined;
|
|
73
|
+
bytes?: number | undefined;
|
|
74
|
+
sealed?: string | undefined;
|
|
75
|
+
}, {
|
|
76
|
+
state: "seen" | "absent" | "oversize" | "over-budget" | "unreadable";
|
|
77
|
+
source: {
|
|
78
|
+
kind: "handle";
|
|
79
|
+
handle: string;
|
|
80
|
+
} | {
|
|
81
|
+
path: string;
|
|
82
|
+
kind: "projection";
|
|
83
|
+
id: string;
|
|
84
|
+
version: string;
|
|
85
|
+
};
|
|
86
|
+
nodeIds: string[];
|
|
87
|
+
class: string;
|
|
88
|
+
status?: string | undefined;
|
|
89
|
+
bytes?: number | undefined;
|
|
90
|
+
sealed?: string | undefined;
|
|
91
|
+
}>, "many">;
|
|
92
|
+
omitted: z.ZodNumber;
|
|
93
|
+
restricted: z.ZodBoolean;
|
|
94
|
+
/** Keyed digest (HMAC under the viewer's key) of the manifest's meaning: an identical consecutive view is not re-recorded. */
|
|
95
|
+
digest: z.ZodString;
|
|
96
|
+
/** The retention floor in force when this was written (see the header). */
|
|
97
|
+
floor: z.ZodOptional<z.ZodNumber>;
|
|
98
|
+
}, "strip", z.ZodTypeAny, {
|
|
99
|
+
entries: {
|
|
100
|
+
state: "seen" | "absent" | "oversize" | "over-budget" | "unreadable";
|
|
101
|
+
source: {
|
|
102
|
+
kind: "handle";
|
|
103
|
+
handle: string;
|
|
104
|
+
} | {
|
|
105
|
+
path: string;
|
|
106
|
+
kind: "projection";
|
|
107
|
+
id: string;
|
|
108
|
+
version: string;
|
|
109
|
+
};
|
|
110
|
+
nodeIds: string[];
|
|
111
|
+
class: string;
|
|
112
|
+
status?: string | undefined;
|
|
113
|
+
bytes?: number | undefined;
|
|
114
|
+
sealed?: string | undefined;
|
|
115
|
+
}[];
|
|
116
|
+
experienceId: string;
|
|
117
|
+
versionHash: string;
|
|
118
|
+
viewerId: string;
|
|
119
|
+
omitted: number;
|
|
120
|
+
restricted: boolean;
|
|
121
|
+
digest: string;
|
|
122
|
+
clearance?: string | undefined;
|
|
123
|
+
floor?: number | undefined;
|
|
124
|
+
}, {
|
|
125
|
+
entries: {
|
|
126
|
+
state: "seen" | "absent" | "oversize" | "over-budget" | "unreadable";
|
|
127
|
+
source: {
|
|
128
|
+
kind: "handle";
|
|
129
|
+
handle: string;
|
|
130
|
+
} | {
|
|
131
|
+
path: string;
|
|
132
|
+
kind: "projection";
|
|
133
|
+
id: string;
|
|
134
|
+
version: string;
|
|
135
|
+
};
|
|
136
|
+
nodeIds: string[];
|
|
137
|
+
class: string;
|
|
138
|
+
status?: string | undefined;
|
|
139
|
+
bytes?: number | undefined;
|
|
140
|
+
sealed?: string | undefined;
|
|
141
|
+
}[];
|
|
142
|
+
experienceId: string;
|
|
143
|
+
versionHash: string;
|
|
144
|
+
viewerId: string;
|
|
145
|
+
omitted: number;
|
|
146
|
+
restricted: boolean;
|
|
147
|
+
digest: string;
|
|
148
|
+
clearance?: string | undefined;
|
|
149
|
+
floor?: number | undefined;
|
|
150
|
+
}>;
|
|
151
|
+
export type ViewRecordPayload = z.infer<typeof ViewRecordPayload>;
|
|
152
|
+
/** How long a viewer's views stay readable (and their value blobs live). Old views roll off; new ones always record. */
|
|
153
|
+
export interface SeenRetention {
|
|
154
|
+
/** Most views kept readable per viewer (default {@link DEFAULT_MAX_SEEN_VIEWS}). */
|
|
155
|
+
readonly maxViews?: number;
|
|
156
|
+
/** Views older than this (ms, by the record's own time) roll off. Default: no age limit. */
|
|
157
|
+
readonly maxAgeMs?: number;
|
|
158
|
+
/**
|
|
159
|
+
* The clock skew tolerated between writers (ms, default {@link DEFAULT_MAX_SKEW_MS}). READS apply
|
|
160
|
+
* `maxAgeMs` exactly, but the two IRREVERSIBLE age actions are conservative by this much: a
|
|
161
|
+
* persisted `VIEWS_RETAINED` watermark only covers views older than `maxAgeMs + maxSkewMs` by the
|
|
162
|
+
* writer's clock, and the collector keeps the blobs of views younger than that. So a writer whose
|
|
163
|
+
* clock runs ahead by up to `maxSkewMs` cannot roll off, or get swept, a view that is still inside
|
|
164
|
+
* the window by true time (a writer further ahead than this is an operator clock fault).
|
|
165
|
+
*/
|
|
166
|
+
readonly maxSkewMs?: number;
|
|
167
|
+
}
|
|
168
|
+
/** The smallest power of two >= `n` (0 stays 0): the only size an `oversize` / `over-budget` entry stores. */
|
|
169
|
+
export declare function sizeClass(n: number): number;
|
|
170
|
+
/** Default tolerated clock skew between writers (5 minutes). */
|
|
171
|
+
export declare const DEFAULT_MAX_SKEW_MS = 300000;
|
|
172
|
+
/** What the collector could not read inside the live window (see {@link SeenLog.forEachLiveRef}). */
|
|
173
|
+
export interface SeenUnreadable {
|
|
174
|
+
/** Streams whose key does not round-trip `seenStreamKey`. */
|
|
175
|
+
readonly streams: number;
|
|
176
|
+
/** `VIEW_RECORDED` records that failed to parse (a newer writer's shape, corruption) or name another viewer. */
|
|
177
|
+
readonly records: number;
|
|
178
|
+
/** Sealed refs that failed to open while the key IS present (unknown version, rotated key, tamper). */
|
|
179
|
+
readonly refs: number;
|
|
180
|
+
/** Where to look: at most {@link UNREADABLE_EXAMPLES} identifiers per kind (stream keys; `experience/viewer@sequence` records; `experience/viewer@sequence#entry` refs). */
|
|
181
|
+
readonly examples: {
|
|
182
|
+
readonly streams: readonly string[];
|
|
183
|
+
readonly records: readonly string[];
|
|
184
|
+
readonly refs: readonly string[];
|
|
185
|
+
};
|
|
186
|
+
}
|
|
187
|
+
/** Cap on the offenders named per kind in {@link SeenUnreadable.examples}. */
|
|
188
|
+
export declare const UNREADABLE_EXAMPLES = 16;
|
|
189
|
+
export interface SeenLogOptions {
|
|
190
|
+
/** A `LineageStore` over a namespace of its own (`eventStoreLineageStore(store, { streamPrefix: SEEN_STREAM_PREFIX, workflowId: SEEN_WORKFLOW_ID })`). */
|
|
191
|
+
readonly events: LineageStore;
|
|
192
|
+
/** Where value bytes live. The same store the lineage uses is fine: addresses are content hashes. */
|
|
193
|
+
readonly content: ContentStore;
|
|
194
|
+
/** Resolves the version a record names (and refuses one that is not a version of the line). */
|
|
195
|
+
readonly lineage: Lineage;
|
|
196
|
+
/** Per-(experience, viewer) data keys. Destroying one erases that viewer. A loom `KeyStore` fits. */
|
|
197
|
+
readonly keys: SeenKeyStore;
|
|
198
|
+
readonly retention?: SeenRetention;
|
|
199
|
+
readonly now?: () => string;
|
|
200
|
+
/**
|
|
201
|
+
* The read policy bound ONCE: every `record` and `read` applies it, joined (raise-only) with the
|
|
202
|
+
* `lineage`'s own bound policy and with any per-call values. Absent = the lineage's policy alone.
|
|
203
|
+
*/
|
|
204
|
+
readonly readPolicy?: ReadPolicy;
|
|
205
|
+
}
|
|
206
|
+
/**
|
|
207
|
+
* Why a seen-log call did not happen. It IS a lineage `Refused` (`kind`, `finding`), so a
|
|
208
|
+
* `SeenResult<T>` is assignable to a `LineageResult<T>`, and it keeps the flat `code` / `message`
|
|
209
|
+
* every seen-log caller already reads (the same values as `finding.code` / `finding.message`).
|
|
210
|
+
*/
|
|
211
|
+
export type SeenRefusal = Refused & {
|
|
212
|
+
readonly code: string;
|
|
213
|
+
readonly message: string;
|
|
214
|
+
};
|
|
215
|
+
export type SeenResult<T> = {
|
|
216
|
+
ok: true;
|
|
217
|
+
value: T;
|
|
218
|
+
} | {
|
|
219
|
+
ok: false;
|
|
220
|
+
refusal: SeenRefusal;
|
|
221
|
+
};
|
|
222
|
+
export interface SeenView {
|
|
223
|
+
readonly sequence: number;
|
|
224
|
+
readonly at: string;
|
|
225
|
+
readonly versionHash: string;
|
|
226
|
+
/** The entries THIS reader may see, values resolved. */
|
|
227
|
+
readonly entries: readonly SeenEntry[];
|
|
228
|
+
/** Something was withheld from this reader (a class, an unreadable stamp, a missing artifact): no count, no name. */
|
|
229
|
+
readonly restricted: boolean;
|
|
230
|
+
/** Sources the capture dropped at its source cap. */
|
|
231
|
+
readonly omitted: number;
|
|
232
|
+
}
|
|
233
|
+
export declare const seenStreamKey: (experienceId: string, viewerId: string) => string;
|
|
234
|
+
export declare class SeenLog {
|
|
235
|
+
private readonly events;
|
|
236
|
+
private readonly content;
|
|
237
|
+
private readonly lineage;
|
|
238
|
+
private readonly keys;
|
|
239
|
+
private readonly maxViews;
|
|
240
|
+
private readonly maxAgeMs;
|
|
241
|
+
private readonly maxSkewMs;
|
|
242
|
+
private readonly slack;
|
|
243
|
+
private readonly now;
|
|
244
|
+
private readonly policy;
|
|
245
|
+
constructor(opts: SeenLogOptions);
|
|
246
|
+
/** The content store value blobs live in (for the collector). */
|
|
247
|
+
get contentStore(): ContentStore;
|
|
248
|
+
/** The lineage the records name versions of (for the collector's roots). */
|
|
249
|
+
get lineageOf(): Lineage;
|
|
250
|
+
private lastRecords;
|
|
251
|
+
private after;
|
|
252
|
+
/** The live views (oldest first) of a window: after the floor, inside the age limit, newest `maxViews`. */
|
|
253
|
+
private liveViews;
|
|
254
|
+
/**
|
|
255
|
+
* Record that `viewerId` was shown `snapshot` (built with core's `snapshotSeen`). The snapshot is
|
|
256
|
+
* not trusted: its version must be a version of the line, its entries are re-validated, re-capped
|
|
257
|
+
* and RESTAMPED against that version's artifact (a stamp laxer than the artifact says is raised; an
|
|
258
|
+
* entry the recording viewer may not see is dropped), and values are measured again. An identical
|
|
259
|
+
* consecutive view records nothing (`recorded: false`). A new view ALWAYS records: when the
|
|
260
|
+
* viewer's window is full, the oldest views roll off (see the header). Refuses an erased viewer.
|
|
261
|
+
* Performs no authorization: `viewerId` and `viewer` are the host's claims.
|
|
262
|
+
*/
|
|
263
|
+
record(input: {
|
|
264
|
+
readonly experienceId: string;
|
|
265
|
+
readonly viewerId: string;
|
|
266
|
+
readonly snapshot: SeenSnapshot;
|
|
267
|
+
readonly viewer?: Viewer;
|
|
268
|
+
/** The audience the surface was drawn for: `"broadcast"` records only what a viewer with no clearance saw. */
|
|
269
|
+
readonly audience?: Audience;
|
|
270
|
+
readonly projections?: ProjectionCatalog;
|
|
271
|
+
readonly hydrationProjectionId?: string;
|
|
272
|
+
readonly declaredToolClasses?: DeclaredToolClasses;
|
|
273
|
+
readonly undeclared?: UndeclaredToolPolicy;
|
|
274
|
+
}): Promise<SeenResult<{
|
|
275
|
+
readonly recorded: boolean;
|
|
276
|
+
readonly sequence: number;
|
|
277
|
+
}>>;
|
|
278
|
+
/**
|
|
279
|
+
* Retention: append a watermark when enough has aged out. Best effort (a lost race or a failure
|
|
280
|
+
* only defers it: reads and the collector apply the window themselves, so correctness never
|
|
281
|
+
* depends on a watermark having been written). `slack` batches the writes: one watermark per
|
|
282
|
+
* `slack` roll-offs, not one per view.
|
|
283
|
+
*/
|
|
284
|
+
private rollOff;
|
|
285
|
+
/**
|
|
286
|
+
* Erase a viewer: destroy their data key (the irreversible step), then write a tombstone. After
|
|
287
|
+
* it, the stream holds no decryptable ref, `read` reports `erased: true`, and `record` refuses.
|
|
288
|
+
* Idempotent and safe to rerun after a crash (a rerun completes whichever half is missing). The
|
|
289
|
+
* value BLOBS the viewer cited are reclaimed by the next `collectSeenGarbage` pass (unless another
|
|
290
|
+
* viewer or the lineage still cites them). The stream's structure stays (see the header).
|
|
291
|
+
* AUTHORIZATION IS THE HOST'S: erasing a (experience, viewer) pair that never existed still
|
|
292
|
+
* writes a tombstone stream (and permanently bars that viewer from recording there), so the host
|
|
293
|
+
* decides who may erase what; this method performs no check.
|
|
294
|
+
*/
|
|
295
|
+
eraseViewer(input: {
|
|
296
|
+
readonly experienceId: string;
|
|
297
|
+
readonly viewerId: string;
|
|
298
|
+
}): Promise<SeenResult<{
|
|
299
|
+
readonly erased: true;
|
|
300
|
+
}>>;
|
|
301
|
+
/**
|
|
302
|
+
* Erase ONE data subject across every experience: enumerate the seen streams (`listStreams`;
|
|
303
|
+
* refused with `seen-enumeration-unavailable` if the store cannot), and erase `viewerId`'s stream in
|
|
304
|
+
* each experience (see {@link eraseViewer}, including its authorization note). Idempotent and
|
|
305
|
+
* resumable: a rerun skips what is erased and completes what is not. A per-experience failure does
|
|
306
|
+
* not stop the others; `complete` is true only when every experience was erased.
|
|
307
|
+
*
|
|
308
|
+
* COVERAGE: only streams that EXIST when enumeration runs are erased. A stream created after
|
|
309
|
+
* that point (a new view by this viewer during the erase) is not covered: the host must serialize
|
|
310
|
+
* erasure against new views for the subject, or rerun. An orphan key with no stream (a crash
|
|
311
|
+
* between `getOrCreate` and the first append) is not destroyed by this enumeration; it holds no
|
|
312
|
+
* data (a key and nothing sealed under it).
|
|
313
|
+
*/
|
|
314
|
+
eraseViewerEverywhere(input: {
|
|
315
|
+
readonly viewerId: string;
|
|
316
|
+
}): Promise<SeenResult<{
|
|
317
|
+
readonly results: ReadonlyArray<{
|
|
318
|
+
readonly experienceId: string;
|
|
319
|
+
readonly erased: boolean;
|
|
320
|
+
readonly refusal?: SeenRefusal;
|
|
321
|
+
}>;
|
|
322
|
+
readonly complete: boolean;
|
|
323
|
+
}>>;
|
|
324
|
+
/**
|
|
325
|
+
* What `viewerId` was shown, newest first (at most `limit`, default 20, hard cap
|
|
326
|
+
* `MAX_SEEN_READ`), as seen by `reader`: entries the reader may not see are withheld (and
|
|
327
|
+
* `restricted` says only that something was), BEFORE any value blob is fetched. Only views inside
|
|
328
|
+
* the retention window are returned. A malformed record is counted in `malformed`, never thrown.
|
|
329
|
+
* `until` (ISO time) keeps records at or before it: the view as of then. An erased viewer (key
|
|
330
|
+
* destroyed or tombstoned) returns `{ erased: true, views: [] }`: nothing is decryptable, so
|
|
331
|
+
* nothing is shown.
|
|
332
|
+
*/
|
|
333
|
+
read(input: {
|
|
334
|
+
readonly experienceId: string;
|
|
335
|
+
readonly viewerId: string;
|
|
336
|
+
readonly reader?: Viewer;
|
|
337
|
+
/** The audience the READ serves: `"broadcast"` reads as a viewer with no clearance. */
|
|
338
|
+
readonly audience?: Audience;
|
|
339
|
+
readonly limit?: number;
|
|
340
|
+
readonly until?: string;
|
|
341
|
+
readonly projections?: ProjectionCatalog;
|
|
342
|
+
readonly hydrationProjectionId?: string;
|
|
343
|
+
readonly declaredToolClasses?: DeclaredToolClasses;
|
|
344
|
+
readonly undeclared?: UndeclaredToolPolicy;
|
|
345
|
+
}): Promise<SeenResult<{
|
|
346
|
+
readonly views: readonly SeenView[];
|
|
347
|
+
readonly malformed: number;
|
|
348
|
+
readonly erased: boolean;
|
|
349
|
+
}>>;
|
|
350
|
+
private openRef;
|
|
351
|
+
/**
|
|
352
|
+
* Call `visit` with the content address of every DECRYPTABLE ref inside every viewer's retention
|
|
353
|
+
* window (kept conservatively: views inside `maxAgeMs + maxSkewMs`; with out-of-order timestamps within `maxSkewMs` at the `maxViews` cap this window can differ from the exact read window's newest-N, in the direction of keeping MORE): the seen log's half of the
|
|
354
|
+
* collector's root set. Erased viewers (key ABSENT: the shred path) and rolled-off views
|
|
355
|
+
* contribute nothing, which is exactly what lets their unique blobs be swept. THROWS if the store
|
|
356
|
+
* cannot enumerate its streams or the key store fails (an unreadable root is not an absent one).
|
|
357
|
+
*
|
|
358
|
+
* Returns what it could NOT read inside the live window (a stream key that does not round-trip, a
|
|
359
|
+
* record that fails to parse, a sealed ref that fails to open under a PRESENT key). Those are not
|
|
360
|
+
* absent either: whatever they cite is unrooted here, so a collector must refuse to sweep on a
|
|
361
|
+
* non-zero count (see `collectSeenGarbage`).
|
|
362
|
+
*
|
|
363
|
+
* `visitVersion` (optional) is called with the (experience, version) of every live view: the seen log
|
|
364
|
+
* READS that version's artifact from the lineage, so a collector that reclaims old versions must
|
|
365
|
+
* keep it (see `collectSeenRoots`).
|
|
366
|
+
*/
|
|
367
|
+
forEachLiveRef(visit: (address: string) => void, visitVersion?: (experienceId: string, versionHash: string) => void): Promise<SeenUnreadable>;
|
|
368
|
+
}
|
|
369
|
+
/** Convenience: the manifest stream a `SeenLog` over an `EventStore` should use. */
|
|
370
|
+
export declare const seenStoreOptions: {
|
|
371
|
+
readonly streamPrefix: "__loom_ui_seen__:";
|
|
372
|
+
readonly workflowId: "loom-ui.seen";
|
|
373
|
+
};
|
|
374
|
+
export type { LineageResult };
|
|
375
|
+
//# sourceMappingURL=seen.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"seen.d.ts","sourceRoot":"","sources":["../src/seen.ts"],"names":[],"mappings":"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"}
|