@agentshouse/mdruntime 0.1.0-c389df724fd2f → 0.1.0-c38dcfe165d81

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 (184) hide show
  1. package/README.md +24 -11
  2. package/dist/adapter.d.ts +175 -54
  3. package/dist/adapter.d.ts.map +1 -1
  4. package/dist/attached-model.d.ts +5 -1
  5. package/dist/attached-model.d.ts.map +1 -1
  6. package/dist/attached-model.js +38 -4
  7. package/dist/attempt.d.ts +16 -0
  8. package/dist/attempt.d.ts.map +1 -0
  9. package/dist/attempt.js +70 -0
  10. package/dist/binary.d.ts +18 -0
  11. package/dist/binary.d.ts.map +1 -0
  12. package/dist/binary.js +8 -0
  13. package/dist/bootstrap.d.ts +33 -5
  14. package/dist/bootstrap.d.ts.map +1 -1
  15. package/dist/bootstrap.js +202 -48
  16. package/dist/chain.d.ts +12 -0
  17. package/dist/chain.d.ts.map +1 -0
  18. package/dist/chain.js +64 -0
  19. package/dist/change-set.d.ts +9 -14
  20. package/dist/change-set.d.ts.map +1 -1
  21. package/dist/change-set.js +11 -56
  22. package/dist/change.d.ts +45 -0
  23. package/dist/change.d.ts.map +1 -1
  24. package/dist/change.js +34 -0
  25. package/dist/client.d.ts +37 -17
  26. package/dist/client.d.ts.map +1 -1
  27. package/dist/client.js +123 -22
  28. package/dist/collection.d.ts +13 -14
  29. package/dist/collection.d.ts.map +1 -1
  30. package/dist/collection.js +52 -56
  31. package/dist/compile.d.ts +11 -0
  32. package/dist/compile.d.ts.map +1 -0
  33. package/dist/compile.js +586 -0
  34. package/dist/connection.d.ts +59 -20
  35. package/dist/connection.d.ts.map +1 -1
  36. package/dist/connection.js +3810 -905
  37. package/dist/context.d.ts +2 -0
  38. package/dist/context.d.ts.map +1 -0
  39. package/dist/context.js +7 -0
  40. package/dist/conversation.d.ts +50 -20
  41. package/dist/conversation.d.ts.map +1 -1
  42. package/dist/conversation.js +714 -242
  43. package/dist/digest.d.ts +7 -0
  44. package/dist/digest.d.ts.map +1 -0
  45. package/dist/digest.js +113 -0
  46. package/dist/durability.d.ts +4 -1
  47. package/dist/durability.d.ts.map +1 -1
  48. package/dist/durability.js +5 -0
  49. package/dist/entry.d.ts +20 -0
  50. package/dist/entry.d.ts.map +1 -0
  51. package/dist/entry.js +159 -0
  52. package/dist/expectation.d.ts +21 -0
  53. package/dist/expectation.d.ts.map +1 -0
  54. package/dist/expectation.js +70 -0
  55. package/dist/failure.d.ts +13 -0
  56. package/dist/failure.d.ts.map +1 -0
  57. package/dist/failure.js +19 -0
  58. package/dist/fence.d.ts +6 -0
  59. package/dist/fence.d.ts.map +1 -0
  60. package/dist/fence.js +10 -0
  61. package/dist/file.d.ts +2 -19
  62. package/dist/file.d.ts.map +1 -1
  63. package/dist/file.js +7 -122
  64. package/dist/host.d.ts +11 -3
  65. package/dist/host.d.ts.map +1 -1
  66. package/dist/host.js +128 -25
  67. package/dist/identity.d.ts +3 -0
  68. package/dist/identity.d.ts.map +1 -1
  69. package/dist/identity.js +13 -1
  70. package/dist/index.d.ts +23 -9
  71. package/dist/index.d.ts.map +1 -1
  72. package/dist/index.js +11 -0
  73. package/dist/job.d.ts +14 -0
  74. package/dist/job.d.ts.map +1 -0
  75. package/dist/job.js +28 -0
  76. package/dist/live.d.ts +23 -0
  77. package/dist/live.d.ts.map +1 -0
  78. package/dist/live.js +127 -0
  79. package/dist/media.d.ts +8 -0
  80. package/dist/media.d.ts.map +1 -0
  81. package/dist/media.js +218 -0
  82. package/dist/memory.d.ts +19 -7
  83. package/dist/memory.d.ts.map +1 -1
  84. package/dist/memory.js +251 -98
  85. package/dist/messages.d.ts +28 -0
  86. package/dist/messages.d.ts.map +1 -0
  87. package/dist/messages.js +89 -0
  88. package/dist/model.d.ts +13 -6
  89. package/dist/model.d.ts.map +1 -1
  90. package/dist/model.js +8 -5
  91. package/dist/name.d.ts +4 -0
  92. package/dist/name.d.ts.map +1 -0
  93. package/dist/name.js +122 -0
  94. package/dist/observation.d.ts +22 -4
  95. package/dist/observation.d.ts.map +1 -1
  96. package/dist/observation.js +120 -14
  97. package/dist/open.d.ts +2 -0
  98. package/dist/open.d.ts.map +1 -0
  99. package/dist/open.js +1 -0
  100. package/dist/opened.d.ts +22 -0
  101. package/dist/opened.d.ts.map +1 -0
  102. package/dist/opened.js +107 -0
  103. package/dist/outcome.d.ts +72 -5
  104. package/dist/outcome.d.ts.map +1 -1
  105. package/dist/outcome.js +81 -1
  106. package/dist/overlay.d.ts +15 -5
  107. package/dist/overlay.d.ts.map +1 -1
  108. package/dist/overlay.js +136 -180
  109. package/dist/paths.d.ts +1 -0
  110. package/dist/paths.d.ts.map +1 -1
  111. package/dist/paths.js +4 -0
  112. package/dist/query.d.ts +42 -181
  113. package/dist/query.d.ts.map +1 -1
  114. package/dist/query.js +3 -461
  115. package/dist/reach.d.ts +18 -4
  116. package/dist/reach.d.ts.map +1 -1
  117. package/dist/reach.js +234 -69
  118. package/dist/react.d.ts +14 -8
  119. package/dist/react.d.ts.map +1 -1
  120. package/dist/react.js +8 -17
  121. package/dist/readiness.d.ts +50 -0
  122. package/dist/readiness.d.ts.map +1 -0
  123. package/dist/readiness.js +27 -0
  124. package/dist/recovery.d.ts +26 -0
  125. package/dist/recovery.d.ts.map +1 -0
  126. package/dist/recovery.js +224 -0
  127. package/dist/refresh.d.ts +20 -7
  128. package/dist/refresh.d.ts.map +1 -1
  129. package/dist/refresh.js +148 -59
  130. package/dist/replica.d.ts +59 -33
  131. package/dist/replica.d.ts.map +1 -1
  132. package/dist/replica.js +320 -157
  133. package/dist/room-draft.d.ts +59 -11
  134. package/dist/room-draft.d.ts.map +1 -1
  135. package/dist/room-draft.js +276 -80
  136. package/dist/rows.d.ts +23 -35
  137. package/dist/rows.d.ts.map +1 -1
  138. package/dist/rows.js +61 -117
  139. package/dist/save.d.ts +73 -4
  140. package/dist/save.d.ts.map +1 -1
  141. package/dist/save.js +825 -150
  142. package/dist/search.d.ts +15 -54
  143. package/dist/search.d.ts.map +1 -1
  144. package/dist/search.js +10 -121
  145. package/dist/seed.d.ts +16 -0
  146. package/dist/seed.d.ts.map +1 -0
  147. package/dist/seed.js +75 -0
  148. package/dist/shared.d.ts +15 -0
  149. package/dist/shared.d.ts.map +1 -0
  150. package/dist/shared.js +421 -0
  151. package/dist/status.d.ts +7 -2
  152. package/dist/status.d.ts.map +1 -1
  153. package/dist/status.js +3 -9
  154. package/dist/store.d.ts +107 -62
  155. package/dist/store.d.ts.map +1 -1
  156. package/dist/store.js +318 -354
  157. package/dist/stored.d.ts +129 -0
  158. package/dist/stored.d.ts.map +1 -0
  159. package/dist/stored.js +495 -0
  160. package/dist/tables.d.ts +326 -0
  161. package/dist/tables.d.ts.map +1 -0
  162. package/dist/tables.js +574 -0
  163. package/dist/transfer.d.ts +0 -5
  164. package/dist/transfer.d.ts.map +1 -1
  165. package/dist/turn.d.ts +9 -0
  166. package/dist/turn.d.ts.map +1 -0
  167. package/dist/turn.js +75 -0
  168. package/dist/validation.d.ts +29 -0
  169. package/dist/validation.d.ts.map +1 -0
  170. package/dist/validation.js +104 -0
  171. package/dist/windows.d.ts +11 -0
  172. package/dist/windows.d.ts.map +1 -0
  173. package/dist/windows.js +16 -0
  174. package/dist/wire.d.ts +169 -33
  175. package/dist/wire.d.ts.map +1 -1
  176. package/dist/wire.js +68 -31
  177. package/package.json +26 -15
  178. package/AGENTS.md +0 -253
  179. package/dist/attachment.d.ts +0 -3
  180. package/dist/attachment.d.ts.map +0 -1
  181. package/dist/attachment.js +0 -8
  182. package/dist/read-side.d.ts +0 -18
  183. package/dist/read-side.d.ts.map +0 -1
  184. package/dist/read-side.js +0 -433
@@ -0,0 +1,129 @@
1
+ import type { HeadChange } from './adapter.js';
2
+ import { type Composed, type Composition } from './collection.js';
3
+ import type { HeldBinary } from './overlay.js';
4
+ import type { Connection } from './tables.js';
5
+ export declare const REPLICA_TABLES: readonly string[];
6
+ export type View = 'confirmed' | 'visible' | 'refreshed';
7
+ export type StoredEntry = {
8
+ readonly path: string;
9
+ readonly content: string | null;
10
+ readonly binary: HeldBinary | null;
11
+ readonly revision: string | null;
12
+ readonly fileId: string | null;
13
+ readonly change: HeadChange | null;
14
+ readonly written: string | null;
15
+ };
16
+ export type OverlayEntry = StoredEntry & {
17
+ readonly present: boolean;
18
+ };
19
+ export type HeldEntry = StoredEntry & {
20
+ readonly type: string | null;
21
+ };
22
+ export type TypedEntry = {
23
+ readonly path: string;
24
+ readonly type: string | null;
25
+ readonly binary: boolean;
26
+ };
27
+ export type Referrer = {
28
+ readonly path: string;
29
+ readonly target: string;
30
+ readonly kind: string;
31
+ };
32
+ export type HeldKey = {
33
+ readonly key: number;
34
+ readonly locator: string;
35
+ readonly transfer: string;
36
+ readonly rederiving: number | null;
37
+ };
38
+ export type ReplicaOpened = {
39
+ readonly rooms: readonly {
40
+ readonly locator: string;
41
+ readonly key: number;
42
+ readonly record: string;
43
+ }[];
44
+ readonly keys: readonly HeldKey[];
45
+ readonly facts: Readonly<Record<string, string>>;
46
+ readonly presentation: readonly {
47
+ readonly app: string;
48
+ readonly value: string;
49
+ }[];
50
+ readonly overlaid: readonly {
51
+ readonly key: number;
52
+ readonly path: string;
53
+ }[];
54
+ readonly erasing: readonly {
55
+ readonly key: number;
56
+ readonly locator: string;
57
+ }[];
58
+ readonly orphans: readonly number[];
59
+ };
60
+ export type RoomCommit = {
61
+ readonly locator: string;
62
+ readonly key: number;
63
+ readonly record?: string;
64
+ readonly roots?: readonly string[];
65
+ readonly published?: {
66
+ readonly from: number | null;
67
+ };
68
+ readonly refreshed?: true;
69
+ readonly composed: Composed;
70
+ readonly confirmed?: {
71
+ readonly set: readonly StoredEntry[];
72
+ readonly removed: readonly string[];
73
+ };
74
+ readonly overlay?: {
75
+ readonly set: readonly OverlayEntry[];
76
+ readonly cleared: readonly string[];
77
+ };
78
+ };
79
+ export type Committed = {
80
+ readonly counts: Readonly<Record<string, number>>;
81
+ readonly changed: Readonly<Record<string, readonly string[] | null>>;
82
+ readonly indexed: Readonly<Record<string, boolean>>;
83
+ };
84
+ export type CountedRoom = {
85
+ readonly key: number;
86
+ readonly roots: readonly string[];
87
+ };
88
+ export declare function entered(connection: Connection, locator: string, composition: Composition, rows: readonly StoredEntry[]): number;
89
+ export declare function stage(connection: Connection, request: {
90
+ readonly locator: string;
91
+ readonly transfer: string;
92
+ readonly key: number | null;
93
+ readonly fingerprint: string;
94
+ readonly entries: readonly StoredEntry[];
95
+ readonly folders: readonly string[];
96
+ }): number;
97
+ export declare function refreshing(connection: Connection, request: {
98
+ readonly key: number;
99
+ readonly composed: Composed;
100
+ readonly entries: readonly StoredEntry[];
101
+ readonly removals: readonly string[];
102
+ readonly folders: readonly string[];
103
+ readonly folderRemovals: readonly string[];
104
+ }): null;
105
+ export declare function unrefresh(connection: Connection, key: number): null;
106
+ export declare function counts(connection: Connection, rooms: readonly CountedRoom[]): number[];
107
+ export declare function commit(connection: Connection, rooms: readonly RoomCommit[]): Committed;
108
+ export declare function fenceRooms(connection: Connection, locators: readonly string[]): null;
109
+ export declare function abandon(connection: Connection, locator: string): null;
110
+ export declare function release(connection: Connection, key: number): null;
111
+ export declare function erase(connection: Connection, locator: string | null, limit: number): {
112
+ readonly remaining: boolean;
113
+ };
114
+ export declare function rederive(connection: Connection, key: number, composed: Composed, bytes: number, ms: number, floor: number): {
115
+ readonly done: boolean;
116
+ readonly text: number;
117
+ };
118
+ export declare function entries(connection: Connection, key: number, view: View, list: readonly string[]): HeldEntry[];
119
+ export declare function typed(connection: Connection, key: number, view: View, list: readonly string[]): TypedEntry[];
120
+ export declare function referrers(connection: Connection, key: number, view: View, targets: readonly string[], kinds: readonly string[]): Referrer[];
121
+ export declare function files(connection: Connection, key: number, view: View, after: string | null, limit: number): {
122
+ readonly path: string;
123
+ readonly revision: string;
124
+ }[];
125
+ export declare function folders(connection: Connection, key: number, view: View, list: readonly string[]): string[];
126
+ export declare function typedWithin(connection: Connection, key: number, view: View, roots: readonly string[], within: boolean): boolean;
127
+ export declare function opened(connection: Connection): ReplicaOpened;
128
+ export declare function ended(connection: Connection): void;
129
+ //# sourceMappingURL=stored.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"stored.d.ts","sourceRoot":"","sources":["../src/stored.ts"],"names":[],"mappings":"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"}
package/dist/stored.js ADDED
@@ -0,0 +1,495 @@
1
+ import { sql } from '@agentshouse/mdmodel';
2
+ import { composedOf } from './collection.js';
3
+ import { described, derived } from './rows.js';
4
+ export const REPLICA_TABLES = [
5
+ 'CREATE TABLE replica_keys (key INTEGER PRIMARY KEY AUTOINCREMENT, locator TEXT NOT NULL, transfer TEXT NOT NULL, fingerprint TEXT NOT NULL, rederiving INTEGER)',
6
+ 'CREATE TABLE replica_rooms (locator TEXT PRIMARY KEY, key INTEGER NOT NULL, record TEXT NOT NULL) WITHOUT ROWID',
7
+ 'CREATE TABLE replica_entries (id INTEGER PRIMARY KEY, key INTEGER NOT NULL, layer INTEGER NOT NULL, path TEXT NOT NULL, visible INTEGER NOT NULL, present INTEGER NOT NULL, queried INTEGER NOT NULL, binary TEXT, revision TEXT, file_id TEXT, change TEXT, written TEXT, type TEXT, declared TEXT, folder TEXT NOT NULL, fields TEXT, content TEXT)',
8
+ 'CREATE UNIQUE INDEX replica_entries_path ON replica_entries (key, layer, path)',
9
+ 'CREATE INDEX replica_entries_visible ON replica_entries (key, visible, present, path, binary)',
10
+ 'CREATE INDEX replica_entries_folder ON replica_entries (key, folder, path)',
11
+ 'CREATE INDEX replica_entries_type ON replica_entries (key, type, visible, present, queried, folder)',
12
+ 'CREATE INDEX replica_entries_key ON replica_entries (key)',
13
+ sql.VALUE_TABLE,
14
+ 'CREATE TABLE replica_links (doc INTEGER NOT NULL, key INTEGER NOT NULL, kind TEXT NOT NULL, keys TEXT NOT NULL, places TEXT NOT NULL, target TEXT NOT NULL, field TEXT NOT NULL, PRIMARY KEY (doc, kind, keys, places, target)) WITHOUT ROWID',
15
+ 'CREATE INDEX replica_links_target ON replica_links (key, target, kind, keys)',
16
+ 'CREATE TABLE replica_folders (key INTEGER NOT NULL, layer INTEGER NOT NULL, path TEXT NOT NULL, present INTEGER NOT NULL, PRIMARY KEY (key, layer, path)) WITHOUT ROWID',
17
+ 'CREATE TABLE replica_erasing (key INTEGER PRIMARY KEY, locator TEXT NOT NULL)',
18
+ 'CREATE TABLE replica_facts (name TEXT PRIMARY KEY, value TEXT NOT NULL) WITHOUT ROWID',
19
+ 'CREATE TABLE replica_presentation (app TEXT PRIMARY KEY, value TEXT NOT NULL) WITHOUT ROWID',
20
+ ];
21
+ const CONFIRMED = 0;
22
+ const OVERLAY = 1;
23
+ const REFRESHED = 2;
24
+ const DERIVED_ROWS = 64;
25
+ const ENTRY_WEIGHT = 256;
26
+ const ABSENT = {
27
+ type: null,
28
+ declared: null,
29
+ queried: false,
30
+ folder: '',
31
+ fields: null,
32
+ values: [],
33
+ links: [],
34
+ };
35
+ function text(value) {
36
+ return typeof value === 'string' ? value : null;
37
+ }
38
+ function number(value) {
39
+ return typeof value === 'bigint' ? Number(value) : value;
40
+ }
41
+ function json(value) {
42
+ return typeof value === 'string' ? JSON.parse(value) : null;
43
+ }
44
+ function flag(value) {
45
+ return value ? 1 : 0;
46
+ }
47
+ function paths(list) {
48
+ return JSON.stringify(list);
49
+ }
50
+ function dropDerived(connection, doc) {
51
+ connection.run('DELETE FROM replica_values WHERE doc = ?', [doc]);
52
+ connection.run('DELETE FROM replica_links WHERE doc = ?', [doc]);
53
+ }
54
+ function writeDerived(connection, doc, key, made) {
55
+ if (made.values.length > 0) {
56
+ const inserted = sql.insertedValues(doc, made.values);
57
+ connection.run(inserted.sql, inserted.bind);
58
+ }
59
+ if (made.links.length > 0) {
60
+ connection.run('INSERT OR IGNORE INTO replica_links (doc, key, kind, keys, places, target, field) SELECT ?, ?, value ->> 0, value ->> 1, value ->> 2, value ->> 3, value ->> 4 FROM json_each(?)', [
61
+ doc,
62
+ key,
63
+ JSON.stringify(made.links.map((link) => [link.kind, link.keys, link.places, link.target, link.field])),
64
+ ]);
65
+ }
66
+ }
67
+ function entryId(connection, key, layer, path) {
68
+ const [row] = connection.rows('SELECT id FROM replica_entries WHERE key = ? AND layer = ? AND path = ?', [key, layer, path]);
69
+ return row === undefined ? null : number(row.id);
70
+ }
71
+ function removeEntry(connection, key, layer, path) {
72
+ const id = entryId(connection, key, layer, path);
73
+ if (id === null)
74
+ return;
75
+ dropDerived(connection, id);
76
+ connection.run('DELETE FROM replica_entries WHERE id = ?', [id]);
77
+ }
78
+ function insertEntry(connection, key, layer, entry, present, made) {
79
+ connection.run('INSERT INTO replica_entries (key, layer, path, visible, present, queried, content, binary, revision, file_id, change, written, type, declared, folder, fields) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)', [
80
+ key,
81
+ layer,
82
+ entry.path,
83
+ flag(present && layer !== REFRESHED),
84
+ flag(present),
85
+ flag(made.queried),
86
+ entry.binary === null ? entry.content : null,
87
+ entry.binary === null ? null : JSON.stringify(entry.binary),
88
+ entry.revision,
89
+ entry.fileId,
90
+ entry.change === null ? null : JSON.stringify(entry.change),
91
+ entry.written,
92
+ made.type,
93
+ made.declared,
94
+ made.folder,
95
+ made.fields,
96
+ ]);
97
+ }
98
+ function textOf(entry) {
99
+ return entry.binary === null ? entry.content : null;
100
+ }
101
+ function putEntry(connection, key, layer, entry, present, composition) {
102
+ removeEntry(connection, key, layer, entry.path);
103
+ const content = textOf(entry);
104
+ const made = present ? derived(entry.path, content, composition) : ABSENT;
105
+ insertEntry(connection, key, layer, entry, present, made);
106
+ if (!present)
107
+ return;
108
+ const id = entryId(connection, key, layer, entry.path);
109
+ writeDerived(connection, id, key, made);
110
+ }
111
+ function placeEntry(connection, key, entry) {
112
+ removeEntry(connection, key, CONFIRMED, entry.path);
113
+ insertEntry(connection, key, CONFIRMED, entry, true, described(entry.path, textOf(entry)));
114
+ }
115
+ function revealed(connection, key, touched) {
116
+ if (touched.length === 0)
117
+ return;
118
+ connection.run(`UPDATE replica_entries SET visible = CASE WHEN layer = ${OVERLAY} THEN present ELSE NOT EXISTS (SELECT 1 FROM replica_entries o WHERE o.key = replica_entries.key AND o.layer = ${OVERLAY} AND o.path = replica_entries.path) END WHERE key = ? AND layer IN (${CONFIRMED}, ${OVERLAY}) AND path IN (SELECT value FROM json_each(?))`, [key, paths(touched)]);
119
+ }
120
+ function newKey(connection, locator, transfer, fingerprint, built) {
121
+ const owed = built ? null : 0;
122
+ connection.run('INSERT INTO replica_keys (locator, transfer, fingerprint, rederiving) VALUES (?, ?, ?, ?)', [locator, transfer, fingerprint, owed]);
123
+ const [row] = connection.rows('SELECT last_insert_rowid() AS key');
124
+ return number(row.key);
125
+ }
126
+ function recomposed(connection, key, fingerprint) {
127
+ const [row] = connection.rows('SELECT fingerprint FROM replica_keys WHERE key = ?', [key]);
128
+ if (row === undefined || text(row.fingerprint) === fingerprint)
129
+ return;
130
+ const held = connection.rows('SELECT 1 FROM replica_entries WHERE key = ? LIMIT 1', [key]);
131
+ connection.run(`UPDATE replica_keys SET fingerprint = ?${held.length === 0 ? '' : ', rederiving = 0'} WHERE key = ?`, [fingerprint, key]);
132
+ }
133
+ export function entered(connection, locator, composition, rows) {
134
+ const key = newKey(connection, locator, '', composedOf(composition).fingerprint, true);
135
+ for (const entry of rows)
136
+ putEntry(connection, key, CONFIRMED, entry, true, composition);
137
+ return key;
138
+ }
139
+ export function stage(connection, request) {
140
+ const key = request.key ??
141
+ newKey(connection, request.locator, request.transfer, request.fingerprint, false);
142
+ recomposed(connection, key, request.fingerprint);
143
+ connection.run('UPDATE replica_keys SET rederiving = coalesce(rederiving, last) FROM (SELECT coalesce(max(id), 0) AS last FROM replica_entries) WHERE key = ?', [key]);
144
+ for (const entry of request.entries)
145
+ placeEntry(connection, key, entry);
146
+ for (const path of request.folders) {
147
+ connection.run('INSERT OR REPLACE INTO replica_folders (key, layer, path, present) VALUES (?, ?, ?, 1)', [key, CONFIRMED, path]);
148
+ }
149
+ return key;
150
+ }
151
+ export function refreshing(connection, request) {
152
+ const held = connection.rows('SELECT 1 FROM replica_keys k WHERE k.key = ? AND NOT EXISTS (SELECT 1 FROM replica_erasing e WHERE e.key = k.key)', [request.key]);
153
+ if (held.length === 0)
154
+ return null;
155
+ recomposed(connection, request.key, request.composed.fingerprint);
156
+ const composition = request.composed.composition;
157
+ for (const entry of request.entries) {
158
+ putEntry(connection, request.key, REFRESHED, entry, true, composition);
159
+ }
160
+ for (const path of request.removals) {
161
+ putEntry(connection, request.key, REFRESHED, {
162
+ path,
163
+ content: null,
164
+ binary: null,
165
+ revision: null,
166
+ fileId: null,
167
+ change: null,
168
+ written: null,
169
+ }, false, composition);
170
+ }
171
+ for (const [list, present] of [
172
+ [request.folders, 1],
173
+ [request.folderRemovals, 0],
174
+ ]) {
175
+ for (const path of list) {
176
+ connection.run('INSERT OR REPLACE INTO replica_folders (key, layer, path, present) VALUES (?, ?, ?, ?)', [request.key, REFRESHED, path, present]);
177
+ }
178
+ }
179
+ return null;
180
+ }
181
+ function dropLayer(connection, key, layer) {
182
+ for (const table of ['replica_values', 'replica_links']) {
183
+ connection.run(`DELETE FROM ${table} WHERE doc IN (SELECT id FROM replica_entries WHERE key = ? AND layer = ?)`, [key, layer]);
184
+ }
185
+ connection.run('DELETE FROM replica_entries WHERE key = ? AND layer = ?', [key, layer]);
186
+ connection.run('DELETE FROM replica_folders WHERE key = ? AND layer = ?', [key, layer]);
187
+ }
188
+ export function unrefresh(connection, key) {
189
+ dropLayer(connection, key, REFRESHED);
190
+ return null;
191
+ }
192
+ function refreshedPaths(connection, key) {
193
+ return connection
194
+ .rows('SELECT path FROM replica_entries WHERE key = ? AND layer = ?', [key, REFRESHED])
195
+ .map((row) => text(row.path));
196
+ }
197
+ function applyRefresh(connection, key) {
198
+ const touched = refreshedPaths(connection, key);
199
+ const replaced = `SELECT c.id FROM replica_entries c JOIN replica_entries r ON r.key = c.key AND r.layer = ${REFRESHED} AND r.path = c.path WHERE c.key = ? AND c.layer = ${CONFIRMED}`;
200
+ for (const table of ['replica_values', 'replica_links']) {
201
+ connection.run(`DELETE FROM ${table} WHERE doc IN (${replaced})`, [key]);
202
+ }
203
+ connection.run(`DELETE FROM replica_entries WHERE id IN (${replaced})`, [key]);
204
+ connection.run('DELETE FROM replica_entries WHERE key = ? AND layer = ? AND present = 0', [
205
+ key,
206
+ REFRESHED,
207
+ ]);
208
+ connection.run('UPDATE replica_entries SET layer = ? WHERE key = ? AND layer = ?', [
209
+ CONFIRMED,
210
+ key,
211
+ REFRESHED,
212
+ ]);
213
+ connection.run(`DELETE FROM replica_folders WHERE key = ? AND layer = ${CONFIRMED} AND path IN (SELECT path FROM replica_folders WHERE key = ? AND layer = ${REFRESHED})`, [key, key]);
214
+ connection.run(`UPDATE replica_folders SET layer = ${CONFIRMED} WHERE key = ? AND layer = ${REFRESHED} AND present = 1`, [key]);
215
+ connection.run('DELETE FROM replica_folders WHERE key = ? AND layer = ?', [key, REFRESHED]);
216
+ return touched;
217
+ }
218
+ function beneathRoots(path) {
219
+ return `EXISTS (SELECT 1 FROM json_each(?) r WHERE ${path} = r.value OR (${path} >= r.value || '/' AND ${path} < r.value || '0'))`;
220
+ }
221
+ function counted(connection, key, roots) {
222
+ const [row] = connection.rows(`SELECT count(*) AS held FROM replica_entries WHERE key = ? AND visible = 1 AND present = 1 AND (binary IS NOT NULL OR substr(path, -3) = '.md') AND NOT ${beneathRoots('replica_entries.path')}`, [key, JSON.stringify(roots)]);
223
+ return number(row.held);
224
+ }
225
+ export function counts(connection, rooms) {
226
+ return rooms.map(({ key, roots }) => counted(connection, key, roots));
227
+ }
228
+ function erasing(connection, key, locator) {
229
+ connection.run('INSERT OR REPLACE INTO replica_erasing (key, locator) VALUES (?, ?)', [
230
+ key,
231
+ locator,
232
+ ]);
233
+ }
234
+ function commitRoom(connection, room) {
235
+ const touched = new Set();
236
+ recomposed(connection, room.key, room.composed.fingerprint);
237
+ const composition = room.composed.composition;
238
+ if (room.published !== undefined &&
239
+ room.published.from !== null &&
240
+ room.published.from !== room.key) {
241
+ erasing(connection, room.published.from, room.locator);
242
+ }
243
+ if (room.refreshed === true) {
244
+ for (const path of applyRefresh(connection, room.key))
245
+ touched.add(path);
246
+ }
247
+ for (const entry of room.confirmed?.set ?? []) {
248
+ putEntry(connection, room.key, CONFIRMED, entry, true, composition);
249
+ touched.add(entry.path);
250
+ }
251
+ for (const path of room.confirmed?.removed ?? []) {
252
+ removeEntry(connection, room.key, CONFIRMED, path);
253
+ touched.add(path);
254
+ }
255
+ for (const entry of room.overlay?.set ?? []) {
256
+ putEntry(connection, room.key, OVERLAY, entry, entry.present, composition);
257
+ touched.add(entry.path);
258
+ }
259
+ for (const path of room.overlay?.cleared ?? []) {
260
+ removeEntry(connection, room.key, OVERLAY, path);
261
+ touched.add(path);
262
+ }
263
+ const changed = [...touched];
264
+ revealed(connection, room.key, changed);
265
+ if (room.record !== undefined) {
266
+ connection.run('INSERT OR REPLACE INTO replica_rooms (locator, key, record) VALUES (?, ?, ?)', [
267
+ room.locator,
268
+ room.key,
269
+ room.record,
270
+ ]);
271
+ }
272
+ return room.published === undefined ? changed : null;
273
+ }
274
+ export function commit(connection, rooms) {
275
+ const counted = {};
276
+ const changed = {};
277
+ const indexed = {};
278
+ for (const room of rooms) {
279
+ changed[room.locator] = commitRoom(connection, room);
280
+ counted[room.locator] = counts(connection, [
281
+ { key: room.key, roots: room.roots ?? rootsOf(connection, room.locator) },
282
+ ])[0];
283
+ const [held] = connection.rows('SELECT rederiving FROM replica_keys WHERE key = ?', [room.key]);
284
+ indexed[room.locator] = held !== undefined && held.rederiving === null;
285
+ }
286
+ return { counts: counted, changed, indexed };
287
+ }
288
+ function rootsOf(connection, locator) {
289
+ const [row] = connection.rows('SELECT record FROM replica_rooms WHERE locator = ?', [locator]);
290
+ const record = json(row?.record);
291
+ return record?.typedSelection?.roots ?? [];
292
+ }
293
+ export function fenceRooms(connection, locators) {
294
+ for (const locator of locators) {
295
+ for (const row of connection.rows('SELECT key FROM replica_keys WHERE locator = ? UNION SELECT key FROM replica_rooms WHERE locator = ?', [locator, locator])) {
296
+ erasing(connection, number(row.key), locator);
297
+ }
298
+ connection.run('DELETE FROM replica_rooms WHERE locator = ?', [locator]);
299
+ }
300
+ return null;
301
+ }
302
+ export function abandon(connection, locator) {
303
+ for (const row of connection.rows(`SELECT k.key FROM replica_keys k WHERE k.locator = ?
304
+ AND NOT EXISTS (SELECT 1 FROM replica_rooms r WHERE r.key = k.key)
305
+ AND NOT EXISTS (SELECT 1 FROM replica_erasing e WHERE e.key = k.key)`, [locator])) {
306
+ erasing(connection, number(row.key), locator);
307
+ }
308
+ return null;
309
+ }
310
+ export function release(connection, key) {
311
+ const [held] = connection.rows(`SELECT k.locator FROM replica_keys k WHERE k.key = ?
312
+ AND NOT EXISTS (SELECT 1 FROM replica_rooms r WHERE r.key = k.key)`, [key]);
313
+ if (held !== undefined)
314
+ erasing(connection, key, text(held.locator));
315
+ return null;
316
+ }
317
+ export function erase(connection, locator, limit) {
318
+ const [held] = connection.rows(`SELECT key FROM replica_erasing${locator === null ? '' : ' WHERE locator = ?'} ORDER BY key LIMIT 1`, locator === null ? [] : [locator]);
319
+ if (held === undefined)
320
+ return { remaining: false };
321
+ const key = number(held.key);
322
+ const batch = 'SELECT id FROM replica_entries WHERE key = ? ORDER BY id LIMIT ?';
323
+ for (const table of ['replica_values', 'replica_links']) {
324
+ connection.run(`DELETE FROM ${table} WHERE doc IN (${batch})`, [key, limit]);
325
+ }
326
+ connection.run(`DELETE FROM replica_entries WHERE id IN (${batch})`, [key, limit]);
327
+ const left = connection.rows('SELECT 1 FROM replica_entries WHERE key = ? LIMIT 1', [key]).length > 0;
328
+ if (!left) {
329
+ connection.run('DELETE FROM replica_folders WHERE key = ?', [key]);
330
+ connection.run('DELETE FROM replica_erasing WHERE key = ?', [key]);
331
+ connection.run('DELETE FROM replica_keys WHERE key = ?', [key]);
332
+ }
333
+ const [more] = connection.rows(`SELECT 1 FROM replica_erasing${locator === null ? '' : ' WHERE locator = ?'} LIMIT 1`, locator === null ? [] : [locator]);
334
+ return { remaining: more !== undefined };
335
+ }
336
+ function cursor(value) {
337
+ return value === null || value === undefined ? null : number(value);
338
+ }
339
+ export function rederive(connection, key, composed, bytes, ms, floor) {
340
+ const started = performance.now();
341
+ recomposed(connection, key, composed.fingerprint);
342
+ const [held] = connection.rows('SELECT rederiving FROM replica_keys WHERE key = ?', [key]);
343
+ const deriving = cursor(held?.rederiving);
344
+ if (deriving === null)
345
+ return { done: true, text: 0 };
346
+ const composition = composed.composition;
347
+ let last = deriving;
348
+ let spent = 0;
349
+ let built = 0;
350
+ let read = false;
351
+ reading: for (;;) {
352
+ const rows = connection.rows('SELECT id, path, content FROM replica_entries WHERE key = ? AND present = 1 AND id > ? ORDER BY id LIMIT ?', [key, last, DERIVED_ROWS]);
353
+ for (const row of rows) {
354
+ const id = number(row.id);
355
+ const path = text(row.path);
356
+ const content = text(row.content);
357
+ const made = derived(path, content, composition);
358
+ dropDerived(connection, id);
359
+ writeDerived(connection, id, key, made);
360
+ built += content?.length ?? 0;
361
+ last = id;
362
+ spent += ENTRY_WEIGHT + (content?.length ?? 0);
363
+ if (spent >= bytes || (spent >= floor && performance.now() - started >= ms))
364
+ break reading;
365
+ }
366
+ if (rows.length < DERIVED_ROWS) {
367
+ read = true;
368
+ break;
369
+ }
370
+ }
371
+ connection.run('UPDATE replica_keys SET rederiving = ? WHERE key = ?', [read ? null : last, key]);
372
+ return { done: read, text: built };
373
+ }
374
+ function heldEntry(row) {
375
+ return {
376
+ path: text(row.path),
377
+ content: text(row.content),
378
+ binary: json(row.binary),
379
+ revision: text(row.revision),
380
+ fileId: text(row.file_id),
381
+ change: json(row.change),
382
+ written: text(row.written),
383
+ type: text(row.type),
384
+ };
385
+ }
386
+ const ENTRY_COLUMNS = 'e.path, e.content, e.binary, e.revision, e.file_id, e.change, e.written, e.type';
387
+ function unrefreshed(alias) {
388
+ return `NOT EXISTS (SELECT 1 FROM replica_entries r WHERE r.key = ${alias}.key AND r.layer = ${REFRESHED} AND r.path = ${alias}.path)`;
389
+ }
390
+ function viewed(view, alias) {
391
+ if (view === 'visible')
392
+ return `${alias}.visible = 1 AND ${alias}.present = 1`;
393
+ if (view === 'confirmed')
394
+ return `${alias}.layer = ${CONFIRMED}`;
395
+ return `${alias}.present = 1 AND (${alias}.layer = ${REFRESHED} OR (${alias}.layer = ${CONFIRMED} AND ${unrefreshed(alias)}))`;
396
+ }
397
+ function layers(view) {
398
+ if (view !== 'refreshed')
399
+ return [viewed(view, 'e')];
400
+ return [
401
+ `e.layer = ${REFRESHED} AND e.present = 1`,
402
+ `e.layer = ${CONFIRMED} AND e.present = 1 AND ${unrefreshed('e')}`,
403
+ ];
404
+ }
405
+ function pathOrdered(connection, columns, key, view, condition, after, limit) {
406
+ const beyond = after === null ? '' : ' AND e.path > ?';
407
+ const parts = layers(view).map((layer) => `SELECT ${columns} FROM replica_entries e WHERE e.key = ? AND ${layer}${condition}${beyond}`);
408
+ return connection.rows(`${parts.join(' UNION ALL ')} ORDER BY path LIMIT ?`, [
409
+ ...parts.flatMap(() => (after === null ? [key] : [key, after])),
410
+ limit,
411
+ ]);
412
+ }
413
+ export function entries(connection, key, view, list) {
414
+ if (list.length === 0)
415
+ return [];
416
+ return connection
417
+ .rows(`SELECT ${ENTRY_COLUMNS} FROM replica_entries e WHERE e.key = ? AND ${viewed(view, 'e')} AND e.path IN (SELECT value FROM json_each(?))`, [key, paths(list)])
418
+ .map(heldEntry);
419
+ }
420
+ export function typed(connection, key, view, list) {
421
+ if (list.length === 0)
422
+ return [];
423
+ return connection
424
+ .rows(`SELECT e.path, e.declared, e.binary IS NOT NULL AS binary FROM replica_entries e WHERE e.key = ? AND ${viewed(view, 'e')} AND e.path IN (SELECT value FROM json_each(?))`, [key, paths(list)])
425
+ .map((row) => ({
426
+ path: text(row.path),
427
+ type: text(row.declared),
428
+ binary: number(row.binary) === 1,
429
+ }));
430
+ }
431
+ export function referrers(connection, key, view, targets, kinds) {
432
+ if (targets.length === 0)
433
+ return [];
434
+ return connection
435
+ .rows(`SELECT DISTINCT e.path, l.target, l.kind FROM replica_links l JOIN replica_entries e ON e.id = l.doc WHERE l.key = ? AND l.target IN (SELECT value FROM json_each(?)) AND l.kind IN (SELECT value FROM json_each(?)) AND ${viewed(view, 'e')}`, [key, paths(targets), JSON.stringify(kinds)])
436
+ .map((row) => ({
437
+ path: text(row.path),
438
+ target: text(row.target),
439
+ kind: text(row.kind),
440
+ }));
441
+ }
442
+ export function files(connection, key, view, after, limit) {
443
+ return pathOrdered(connection, 'e.path, e.revision', key, view, ' AND e.content IS NOT NULL AND e.revision IS NOT NULL', after, limit).map((row) => ({ path: text(row.path), revision: text(row.revision) }));
444
+ }
445
+ export function folders(connection, key, view, list) {
446
+ return list.filter((path) => connection.rows(`SELECT 1 FROM replica_folders f WHERE f.key = ? AND f.layer = ${CONFIRMED} AND f.present = 1 AND f.path = ? UNION ALL SELECT 1 FROM replica_entries e WHERE e.key = ? AND ${viewed(view, 'e')} AND e.path >= ? AND e.path < ? LIMIT 1`, [key, path, key, `${path}/`, `${path}0`]).length > 0);
447
+ }
448
+ export function typedWithin(connection, key, view, roots, within) {
449
+ return (connection.rows(`SELECT 1 FROM replica_entries e WHERE e.key = ? AND ${viewed(view, 'e')} AND e.declared IS NOT NULL AND e.declared <> 'any' AND ${within ? '' : 'NOT '}${beneathRoots('e.path')} LIMIT 1`, [key, JSON.stringify(roots)]).length > 0);
450
+ }
451
+ export function opened(connection) {
452
+ const facts = {};
453
+ for (const row of connection.rows('SELECT name, value FROM replica_facts')) {
454
+ facts[text(row.name)] = text(row.value);
455
+ }
456
+ return {
457
+ rooms: connection.rows('SELECT locator, key, record FROM replica_rooms').map((row) => ({
458
+ locator: text(row.locator),
459
+ key: number(row.key),
460
+ record: text(row.record),
461
+ })),
462
+ keys: connection
463
+ .rows('SELECT key, locator, transfer, rederiving FROM replica_keys')
464
+ .map((row) => ({
465
+ key: number(row.key),
466
+ locator: text(row.locator),
467
+ transfer: text(row.transfer),
468
+ rederiving: cursor(row.rederiving),
469
+ })),
470
+ facts,
471
+ presentation: connection.rows('SELECT app, value FROM replica_presentation').map((row) => ({
472
+ app: text(row.app),
473
+ value: text(row.value),
474
+ })),
475
+ overlaid: connection
476
+ .rows(`SELECT key, path FROM replica_entries WHERE layer = ${OVERLAY}`)
477
+ .map((row) => ({ key: number(row.key), path: text(row.path) })),
478
+ orphans: connection
479
+ .rows(`SELECT k.key FROM replica_keys k
480
+ WHERE NOT EXISTS (SELECT 1 FROM replica_rooms r WHERE r.key = k.key)
481
+ AND NOT EXISTS (SELECT 1 FROM replica_erasing e WHERE e.key = k.key)`)
482
+ .map((row) => number(row.key)),
483
+ erasing: connection.rows('SELECT key, locator FROM replica_erasing').map((row) => ({
484
+ key: number(row.key),
485
+ locator: text(row.locator),
486
+ })),
487
+ };
488
+ }
489
+ export function ended(connection) {
490
+ for (const statement of REPLICA_TABLES) {
491
+ const table = /^CREATE TABLE (\w+)/u.exec(statement)?.[1];
492
+ if (table !== undefined)
493
+ connection.run(`DELETE FROM ${table}`);
494
+ }
495
+ }