@agentshouse/mdruntime-adapter 0.1.0-cf22c8563f9f4 → 0.1.0-cf41d9210cb6b
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/README.md +2 -2
- package/dist/actions.d.ts +51 -2
- package/dist/actions.d.ts.map +1 -1
- package/dist/actions.js +123 -214
- package/dist/adapter.d.ts +1 -0
- package/dist/adapter.d.ts.map +1 -1
- package/dist/adapter.js +336 -109
- package/dist/app-reference.d.ts +2 -0
- package/dist/app-reference.d.ts.map +1 -0
- package/dist/app-reference.js +2 -0
- package/dist/crockford.d.ts +4 -0
- package/dist/crockford.d.ts.map +1 -0
- package/dist/crockford.js +3 -0
- package/dist/discovery.d.ts +9 -11
- package/dist/discovery.d.ts.map +1 -1
- package/dist/discovery.js +55 -36
- package/dist/gather.d.ts +1 -1
- package/dist/gather.d.ts.map +1 -1
- package/dist/gather.js +15 -20
- package/dist/house-model.d.ts +2 -0
- package/dist/house-model.d.ts.map +1 -0
- package/dist/house-model.js +489 -0
- package/dist/index.d.ts +8 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +7 -0
- package/dist/model.d.ts +6 -2
- package/dist/model.d.ts.map +1 -1
- package/dist/model.js +32 -20
- package/dist/part.d.ts +14 -0
- package/dist/part.d.ts.map +1 -0
- package/dist/part.js +90 -0
- package/dist/read.d.ts +74 -20
- package/dist/read.d.ts.map +1 -1
- package/dist/read.js +353 -168
- package/dist/refusal.d.ts +2 -5
- package/dist/refusal.d.ts.map +1 -1
- package/dist/refusal.js +6 -9
- package/dist/room-stream.d.ts +19 -0
- package/dist/room-stream.d.ts.map +1 -0
- package/dist/room-stream.js +57 -0
- package/dist/room-types.d.ts +7 -0
- package/dist/room-types.d.ts.map +1 -0
- package/dist/room-types.js +125 -0
- package/dist/site.d.ts +1 -1
- package/dist/site.d.ts.map +1 -1
- package/dist/site.js +131 -62
- package/dist/stream.d.ts +6 -4
- package/dist/stream.d.ts.map +1 -1
- package/dist/stream.js +366 -44
- package/dist/transport.d.ts +76 -11
- package/dist/transport.d.ts.map +1 -1
- package/dist/transport.js +4 -0
- package/dist/upload.d.ts +12 -0
- package/dist/upload.d.ts.map +1 -0
- package/dist/upload.js +63 -0
- package/dist/version.d.ts +1 -0
- package/dist/version.d.ts.map +1 -1
- package/dist/version.js +1 -1
- package/dist/write.d.ts +18 -9
- package/dist/write.d.ts.map +1 -1
- package/dist/write.js +164 -41
- package/package.json +9 -6
- package/AGENTS.md +0 -244
- package/dist/links.d.ts +0 -20
- package/dist/links.d.ts.map +0 -1
- package/dist/links.js +0 -104
package/dist/read.js
CHANGED
|
@@ -1,13 +1,72 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { paced, patching, ROW_WEIGHT, stepped, } from '@agentshouse/mdruntime';
|
|
2
|
+
import { gunzipped } from './part.js';
|
|
3
|
+
import { DECIMAL, readPosition, roomVersion } from './version.js';
|
|
4
|
+
const REVISION_FILE = /^fr_([0-9a-z]+)\.[0-9a-z]+\.[0-9a-z]$/u;
|
|
5
|
+
function fileOf(revision) {
|
|
6
|
+
return REVISION_FILE.exec(revision)?.[1];
|
|
7
|
+
}
|
|
8
|
+
export function answering() {
|
|
9
|
+
return {
|
|
10
|
+
documents: new Map(),
|
|
11
|
+
revisions: new Map(),
|
|
12
|
+
fileIds: new Map(),
|
|
13
|
+
changes: new Map(),
|
|
14
|
+
binaryFiles: new Map(),
|
|
15
|
+
removals: new Set(),
|
|
16
|
+
folders: new Set(),
|
|
17
|
+
folderRemovals: new Set(),
|
|
18
|
+
};
|
|
19
|
+
}
|
|
20
|
+
export function revised(answer, path, revision) {
|
|
21
|
+
answer.revisions.set(path, revision);
|
|
22
|
+
const file = fileOf(revision);
|
|
23
|
+
if (file !== undefined)
|
|
24
|
+
answer.fileIds.set(path, file);
|
|
25
|
+
}
|
|
26
|
+
export function forgotten(answer, path) {
|
|
27
|
+
answer.documents.delete(path);
|
|
28
|
+
answer.revisions.delete(path);
|
|
29
|
+
answer.fileIds.delete(path);
|
|
30
|
+
answer.changes.delete(path);
|
|
31
|
+
answer.binaryFiles.delete(path);
|
|
32
|
+
answer.removals.delete(path);
|
|
33
|
+
}
|
|
34
|
+
export function folded(answer, path, removed) {
|
|
35
|
+
if (removed) {
|
|
36
|
+
answer.folders.delete(path);
|
|
37
|
+
answer.folderRemovals.add(path);
|
|
38
|
+
}
|
|
39
|
+
else {
|
|
40
|
+
answer.folderRemovals.delete(path);
|
|
41
|
+
answer.folders.add(path);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
function* pathsOf(paths) {
|
|
45
|
+
const list = [];
|
|
46
|
+
for (const path of paths) {
|
|
47
|
+
list.push(path);
|
|
48
|
+
yield ROW_WEIGHT;
|
|
49
|
+
}
|
|
50
|
+
return list;
|
|
51
|
+
}
|
|
52
|
+
export function* answered(answer) {
|
|
53
|
+
const removals = yield* pathsOf(answer.removals);
|
|
54
|
+
return {
|
|
55
|
+
documents: yield* patching({}, answer.documents),
|
|
56
|
+
revisions: yield* patching({}, answer.revisions),
|
|
57
|
+
...(answer.fileIds.size === 0 ? {} : { fileIds: yield* patching({}, answer.fileIds) }),
|
|
58
|
+
changes: yield* patching({}, answer.changes),
|
|
59
|
+
binaryFiles: yield* patching({}, answer.binaryFiles),
|
|
60
|
+
removals,
|
|
61
|
+
...(answer.folders.size === 0 ? {} : { folders: yield* pathsOf(answer.folders) }),
|
|
62
|
+
...(answer.folderRemovals.size === 0
|
|
63
|
+
? {}
|
|
64
|
+
: { folderRemovals: yield* pathsOf(answer.folderRemovals) }),
|
|
65
|
+
};
|
|
66
|
+
}
|
|
2
67
|
export function authorityRoot(handle) {
|
|
3
68
|
return `/rooms/${handle}`;
|
|
4
69
|
}
|
|
5
|
-
export function contentPrefixes(tracked) {
|
|
6
|
-
return [
|
|
7
|
-
authorityRoot(tracked.handle),
|
|
8
|
-
...tracked.schemas.map((schema) => schemaPath(tracked.handle, schema)),
|
|
9
|
-
];
|
|
10
|
-
}
|
|
11
70
|
export function schemaPath(handle, schema) {
|
|
12
71
|
return `${authorityRoot(handle)}/${schema}`;
|
|
13
72
|
}
|
|
@@ -20,22 +79,39 @@ export function parseGrant(body) {
|
|
|
20
79
|
const transfer = body.transfer;
|
|
21
80
|
if (typeof transfer.url !== 'string')
|
|
22
81
|
return null;
|
|
23
|
-
if (transfer.method === 'GET')
|
|
24
|
-
return { method: 'GET', url: transfer.url };
|
|
25
82
|
if (transfer.method !== 'POST' || typeof transfer.operation !== 'string')
|
|
26
83
|
return null;
|
|
27
|
-
return {
|
|
84
|
+
return { operation: transfer.operation, url: transfer.url };
|
|
85
|
+
}
|
|
86
|
+
export function parseFileAddress(body) {
|
|
87
|
+
if (typeof body !== 'object' || body === null)
|
|
88
|
+
return null;
|
|
89
|
+
const { download, name, sha256, media_type: mediaType } = body;
|
|
90
|
+
if (typeof download !== 'string' ||
|
|
91
|
+
typeof name !== 'string' ||
|
|
92
|
+
typeof sha256 !== 'string' ||
|
|
93
|
+
typeof mediaType !== 'string') {
|
|
94
|
+
return null;
|
|
95
|
+
}
|
|
96
|
+
return { url: download, name, sha256, mediaType };
|
|
28
97
|
}
|
|
29
98
|
function changeAuthor(value) {
|
|
30
99
|
if (typeof value !== 'object' || value === null)
|
|
31
100
|
return null;
|
|
32
|
-
const { user, site, name } = value;
|
|
101
|
+
const { user, site, inbox, app, name } = value;
|
|
33
102
|
if (typeof name !== 'string')
|
|
34
103
|
return null;
|
|
35
|
-
|
|
104
|
+
const named = [user, site, inbox, app].filter((id) => id !== undefined);
|
|
105
|
+
if (named.length !== 1)
|
|
106
|
+
return null;
|
|
107
|
+
if (typeof user === 'string')
|
|
36
108
|
return { kind: 'user', id: user, name };
|
|
37
|
-
if (typeof site === 'string'
|
|
109
|
+
if (typeof site === 'string')
|
|
38
110
|
return { kind: 'site', id: site, name };
|
|
111
|
+
if (typeof inbox === 'string')
|
|
112
|
+
return { kind: 'inbox', id: inbox, name };
|
|
113
|
+
if (typeof app === 'string')
|
|
114
|
+
return { kind: 'app', id: app, name };
|
|
39
115
|
return null;
|
|
40
116
|
}
|
|
41
117
|
export function headChange(held) {
|
|
@@ -51,32 +127,16 @@ export function headChange(held) {
|
|
|
51
127
|
function headed(head) {
|
|
52
128
|
return head === undefined ? {} : { head };
|
|
53
129
|
}
|
|
54
|
-
function
|
|
55
|
-
if (
|
|
56
|
-
return
|
|
57
|
-
const {
|
|
58
|
-
if (typeof
|
|
59
|
-
return null;
|
|
60
|
-
if (typeof bytes !== 'number' || !Number.isSafeInteger(bytes) || bytes < 0)
|
|
61
|
-
return null;
|
|
62
|
-
if (mediaType !== null && typeof mediaType !== 'string')
|
|
130
|
+
export function binaryFileOf(held) {
|
|
131
|
+
if (held.media_type === undefined)
|
|
132
|
+
return undefined;
|
|
133
|
+
const { bytes, media_type: mediaType, sha256 } = held;
|
|
134
|
+
if (typeof bytes !== 'number' || typeof mediaType !== 'string' || typeof sha256 !== 'string')
|
|
63
135
|
return null;
|
|
64
|
-
return {
|
|
136
|
+
return { byteLength: bytes, mediaType, sha256 };
|
|
65
137
|
}
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
return null;
|
|
69
|
-
const attachments = [];
|
|
70
|
-
for (const entry of value) {
|
|
71
|
-
const attachment = parseOriginal(entry);
|
|
72
|
-
if (attachment === null)
|
|
73
|
-
return null;
|
|
74
|
-
attachments.push(attachment);
|
|
75
|
-
}
|
|
76
|
-
return attachments;
|
|
77
|
-
}
|
|
78
|
-
function declared(attachments) {
|
|
79
|
-
return attachments === undefined ? {} : { attachments };
|
|
138
|
+
function binaried(binary) {
|
|
139
|
+
return binary === undefined ? {} : { binary };
|
|
80
140
|
}
|
|
81
141
|
function parseFile(value, mode) {
|
|
82
142
|
if (typeof value !== 'object' || value === null)
|
|
@@ -85,24 +145,54 @@ function parseFile(value, mode) {
|
|
|
85
145
|
if (typeof file.path !== 'string')
|
|
86
146
|
return null;
|
|
87
147
|
const head = headChange(file);
|
|
88
|
-
|
|
148
|
+
const binary = binaryFileOf(file);
|
|
149
|
+
if (head === null || binary === null)
|
|
89
150
|
return null;
|
|
90
151
|
if (mode === 'site') {
|
|
91
152
|
if (typeof file.sha256 !== 'string')
|
|
92
153
|
return null;
|
|
93
|
-
return {
|
|
154
|
+
return {
|
|
155
|
+
path: file.path,
|
|
156
|
+
revision: binary?.sha256,
|
|
157
|
+
version: file.sha256,
|
|
158
|
+
...headed(head),
|
|
159
|
+
...binaried(binary),
|
|
160
|
+
};
|
|
94
161
|
}
|
|
95
162
|
if (typeof file.revision !== 'string')
|
|
96
163
|
return null;
|
|
97
|
-
return {
|
|
164
|
+
return {
|
|
165
|
+
path: file.path,
|
|
166
|
+
revision: file.revision,
|
|
167
|
+
version: file.revision,
|
|
168
|
+
...(typeof file.sha256 === 'string' ? { sha256: file.sha256 } : {}),
|
|
169
|
+
...headed(head),
|
|
170
|
+
...binaried(binary),
|
|
171
|
+
};
|
|
172
|
+
}
|
|
173
|
+
function parseModels(value, mode) {
|
|
174
|
+
if (!Array.isArray(value))
|
|
175
|
+
return null;
|
|
176
|
+
const files = [];
|
|
177
|
+
const contents = [];
|
|
178
|
+
for (const entry of value) {
|
|
179
|
+
const file = parseFile(entry, mode);
|
|
180
|
+
const { content } = entry;
|
|
181
|
+
if (file === null || typeof content !== 'string')
|
|
182
|
+
return null;
|
|
183
|
+
files.push(file);
|
|
184
|
+
contents.push({ path: file.path, content });
|
|
185
|
+
}
|
|
186
|
+
return { files, contents };
|
|
98
187
|
}
|
|
99
|
-
function
|
|
188
|
+
function parseRoomHead(value, mode) {
|
|
100
189
|
if (typeof value !== 'object' || value === null)
|
|
101
190
|
return null;
|
|
102
191
|
const held = value;
|
|
103
192
|
if (typeof held.manifest !== 'object' || held.manifest === null)
|
|
104
193
|
return null;
|
|
105
|
-
|
|
194
|
+
const models = parseModels(held.models, mode);
|
|
195
|
+
if (models === null)
|
|
106
196
|
return null;
|
|
107
197
|
const manifest = held.manifest;
|
|
108
198
|
if (manifest.scope !== 'room')
|
|
@@ -112,47 +202,125 @@ function parseScope(value, mode) {
|
|
|
112
202
|
return null;
|
|
113
203
|
if (typeof manifest.room_handle !== 'string' || manifest.room_handle.length === 0)
|
|
114
204
|
return null;
|
|
115
|
-
|
|
205
|
+
return { anchor: manifest.anchor, ...at, models };
|
|
206
|
+
}
|
|
207
|
+
export async function roomHead(payload, mode) {
|
|
208
|
+
let text = '';
|
|
209
|
+
try {
|
|
210
|
+
for await (const chunk of gunzipped(payload))
|
|
211
|
+
text += chunk;
|
|
212
|
+
return text.endsWith('\n') && text.indexOf('\n') === text.length - 1
|
|
213
|
+
? parseRoomHead(JSON.parse(text), mode)
|
|
214
|
+
: null;
|
|
215
|
+
}
|
|
216
|
+
catch {
|
|
116
217
|
return null;
|
|
117
|
-
const files = [];
|
|
118
|
-
for (const entry of manifest.files) {
|
|
119
|
-
const file = parseFile(entry, mode);
|
|
120
|
-
if (file === null)
|
|
121
|
-
return null;
|
|
122
|
-
files.push(file);
|
|
123
218
|
}
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
219
|
+
}
|
|
220
|
+
export function manifested(room, pageToken, models) {
|
|
221
|
+
return {
|
|
222
|
+
kind: 'bootstrap',
|
|
223
|
+
roomVersion: roomVersion(room),
|
|
224
|
+
documents: {},
|
|
225
|
+
revisions: {},
|
|
226
|
+
changes: {},
|
|
227
|
+
binaryFiles: {},
|
|
228
|
+
pageToken,
|
|
229
|
+
...(models === undefined ? {} : { models }),
|
|
230
|
+
};
|
|
231
|
+
}
|
|
232
|
+
export function modelScope(room) {
|
|
233
|
+
return { ...emptyScope(room), files: room.models.files, contents: room.models.contents };
|
|
234
|
+
}
|
|
235
|
+
export function emptyScope(room) {
|
|
236
|
+
return {
|
|
237
|
+
anchor: room.anchor,
|
|
238
|
+
position: room.position,
|
|
239
|
+
logEpoch: room.logEpoch,
|
|
240
|
+
files: [],
|
|
241
|
+
contents: [],
|
|
242
|
+
};
|
|
243
|
+
}
|
|
244
|
+
function partLine(line, mode, read) {
|
|
245
|
+
if (read.ended)
|
|
246
|
+
return false;
|
|
247
|
+
let entry;
|
|
248
|
+
try {
|
|
249
|
+
entry = JSON.parse(line);
|
|
132
250
|
}
|
|
133
|
-
|
|
134
|
-
return
|
|
135
|
-
|
|
136
|
-
if (
|
|
137
|
-
|
|
138
|
-
|
|
251
|
+
catch {
|
|
252
|
+
return false;
|
|
253
|
+
}
|
|
254
|
+
if (endLine(entry)) {
|
|
255
|
+
read.ended = true;
|
|
256
|
+
return true;
|
|
257
|
+
}
|
|
258
|
+
if (folderLine(entry)) {
|
|
259
|
+
read.folders.push(entry.folder);
|
|
260
|
+
return true;
|
|
261
|
+
}
|
|
262
|
+
const file = parseFile(entry, mode);
|
|
263
|
+
if (file === null)
|
|
264
|
+
return false;
|
|
265
|
+
read.files.push(file);
|
|
266
|
+
const { content } = entry;
|
|
267
|
+
if (typeof content === 'string')
|
|
268
|
+
read.contents.push({ path: file.path, content });
|
|
269
|
+
else if (content !== undefined)
|
|
270
|
+
return false;
|
|
271
|
+
return true;
|
|
139
272
|
}
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
273
|
+
async function partRead(chunks, mode) {
|
|
274
|
+
const read = { files: [], contents: [], folders: [], ended: false };
|
|
275
|
+
const pace = paced();
|
|
276
|
+
const unfinished = [];
|
|
277
|
+
for (let chunk = await chunks.read(); chunk.done !== true; chunk = await chunks.read()) {
|
|
278
|
+
const text = chunk.value;
|
|
279
|
+
let start = 0;
|
|
280
|
+
for (let end = text.indexOf('\n'); end !== -1; end = text.indexOf('\n', start)) {
|
|
281
|
+
const piece = text.slice(start, end);
|
|
282
|
+
const line = unfinished.length === 0 ? piece : unfinished.splice(0).join('') + piece;
|
|
283
|
+
if (!partLine(line, mode, read)) {
|
|
284
|
+
await chunks.cancel();
|
|
285
|
+
return null;
|
|
286
|
+
}
|
|
287
|
+
start = end + 1;
|
|
288
|
+
const due = pace(line.length + ROW_WEIGHT);
|
|
289
|
+
if (due instanceof Promise)
|
|
290
|
+
await due;
|
|
291
|
+
}
|
|
292
|
+
if (start < text.length)
|
|
293
|
+
unfinished.push(text.slice(start));
|
|
151
294
|
}
|
|
152
|
-
return
|
|
295
|
+
return unfinished.length === 0 ? read : null;
|
|
296
|
+
}
|
|
297
|
+
function endLine(entry) {
|
|
298
|
+
if (typeof entry !== 'object' || entry === null || !('end' in entry))
|
|
299
|
+
return false;
|
|
300
|
+
return entry.end === true && Object.keys(entry).length === 1;
|
|
301
|
+
}
|
|
302
|
+
function folderLine(entry) {
|
|
303
|
+
if (typeof entry !== 'object' || entry === null || !('folder' in entry))
|
|
304
|
+
return false;
|
|
305
|
+
return typeof entry.folder === 'string' && Object.keys(entry).length === 1;
|
|
153
306
|
}
|
|
154
|
-
export function
|
|
155
|
-
|
|
307
|
+
export async function housePart(room, payload, mode) {
|
|
308
|
+
const read = await partRead(gunzipped(payload).getReader(), mode).catch(() => null);
|
|
309
|
+
if (read === null)
|
|
310
|
+
return { kind: 'transport-uncertainty' };
|
|
311
|
+
const { ended, ...scope } = read;
|
|
312
|
+
return { scope: { ...emptyScope(room), ...scope }, ended };
|
|
313
|
+
}
|
|
314
|
+
function folderChange(value) {
|
|
315
|
+
if (typeof value !== 'object' || value === null)
|
|
316
|
+
return null;
|
|
317
|
+
const { path, folder, removed, ...rest } = value;
|
|
318
|
+
return typeof path === 'string' &&
|
|
319
|
+
folder === true &&
|
|
320
|
+
(removed === undefined || removed === true) &&
|
|
321
|
+
Object.keys(rest).length === 0
|
|
322
|
+
? { path, removed: removed === true }
|
|
323
|
+
: null;
|
|
156
324
|
}
|
|
157
325
|
function parseChange(value, mode) {
|
|
158
326
|
if (typeof value !== 'object' || value === null)
|
|
@@ -163,8 +331,15 @@ function parseChange(value, mode) {
|
|
|
163
331
|
if (held.removed === true)
|
|
164
332
|
return { path: held.path, removed: true };
|
|
165
333
|
const head = headChange(held);
|
|
166
|
-
|
|
334
|
+
const binary = binaryFileOf(held);
|
|
335
|
+
if (head === null || binary === null)
|
|
167
336
|
return null;
|
|
337
|
+
if (binary !== undefined) {
|
|
338
|
+
if (mode === 'credential' && typeof held.revision !== 'string')
|
|
339
|
+
return null;
|
|
340
|
+
const revision = typeof held.revision === 'string' ? held.revision : binary.sha256;
|
|
341
|
+
return { path: held.path, binary, revision, version: revision, ...headed(head) };
|
|
342
|
+
}
|
|
168
343
|
if (mode === 'site') {
|
|
169
344
|
if (typeof held.content !== 'string' || typeof held.sha256 !== 'string')
|
|
170
345
|
return null;
|
|
@@ -185,12 +360,6 @@ function parseChange(value, mode) {
|
|
|
185
360
|
...headed(head),
|
|
186
361
|
};
|
|
187
362
|
}
|
|
188
|
-
if (typeof held.reference === 'object' && held.reference !== null) {
|
|
189
|
-
const reference = held.reference;
|
|
190
|
-
if (typeof reference.revision !== 'string')
|
|
191
|
-
return null;
|
|
192
|
-
return { path: held.path, reference: { revision: reference.revision } };
|
|
193
|
-
}
|
|
194
363
|
return null;
|
|
195
364
|
}
|
|
196
365
|
export function parseEnumeration(body, mode) {
|
|
@@ -209,124 +378,140 @@ export function parseEnumeration(body, mode) {
|
|
|
209
378
|
if (!Array.isArray(held.changes))
|
|
210
379
|
return null;
|
|
211
380
|
const changes = [];
|
|
381
|
+
const folders = [];
|
|
212
382
|
for (const change of held.changes) {
|
|
383
|
+
const folder = folderChange(change);
|
|
384
|
+
if (folder !== null) {
|
|
385
|
+
folders.push(folder);
|
|
386
|
+
continue;
|
|
387
|
+
}
|
|
213
388
|
const mapped = parseChange(change, mode);
|
|
214
389
|
if (mapped === null)
|
|
215
390
|
return null;
|
|
216
391
|
changes.push(mapped);
|
|
217
392
|
}
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
continue;
|
|
221
|
-
}
|
|
222
|
-
const attachments = parseOriginals(held.originals);
|
|
223
|
-
if (attachments === null)
|
|
393
|
+
const next = held.next === undefined ? undefined : readPage(held.next);
|
|
394
|
+
if (next === null)
|
|
224
395
|
return null;
|
|
225
|
-
authorities.push({
|
|
396
|
+
authorities.push({
|
|
397
|
+
authority: held.authority,
|
|
398
|
+
...at,
|
|
399
|
+
changes,
|
|
400
|
+
...(folders.length === 0 ? {} : { folders }),
|
|
401
|
+
...(next === undefined ? {} : { next }),
|
|
402
|
+
});
|
|
226
403
|
}
|
|
227
404
|
return { authorities };
|
|
228
405
|
}
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
406
|
+
function readPage(held) {
|
|
407
|
+
if (typeof held !== 'object' || held === null)
|
|
408
|
+
return null;
|
|
409
|
+
const { after, through, read } = held;
|
|
410
|
+
if (typeof after !== 'string' || !DECIMAL.test(after))
|
|
411
|
+
return null;
|
|
412
|
+
if (typeof through !== 'string' || !DECIMAL.test(through))
|
|
413
|
+
return null;
|
|
414
|
+
if (typeof read !== 'number' || !Number.isSafeInteger(read) || read < 0)
|
|
415
|
+
return null;
|
|
416
|
+
return { after, through, read };
|
|
417
|
+
}
|
|
418
|
+
function advances(asked, next) {
|
|
419
|
+
const moved = BigInt(next.through) - BigInt(asked.through);
|
|
420
|
+
return moved > 0n || (moved === 0n && next.after === asked.after && next.read > asked.read);
|
|
421
|
+
}
|
|
422
|
+
export async function wholeView(first, more) {
|
|
423
|
+
const changes = new Map(first.changes.map((change) => [change.path, change]));
|
|
424
|
+
const folders = new Map((first.folders ?? []).map((folder) => [folder.path, folder]));
|
|
425
|
+
let view = first;
|
|
426
|
+
while (view.next !== undefined) {
|
|
427
|
+
const asked = view.next;
|
|
428
|
+
const page = await more(asked);
|
|
429
|
+
if ('kind' in page)
|
|
430
|
+
return page;
|
|
431
|
+
if (page.position !== asked.through ||
|
|
432
|
+
page.logEpoch !== first.logEpoch ||
|
|
433
|
+
(page.next !== undefined && !advances(asked, page.next))) {
|
|
434
|
+
return { kind: 'transport-uncertainty' };
|
|
246
435
|
}
|
|
247
|
-
const
|
|
248
|
-
|
|
436
|
+
for (const change of page.changes) {
|
|
437
|
+
changes.delete(change.path);
|
|
438
|
+
changes.set(change.path, change);
|
|
439
|
+
}
|
|
440
|
+
for (const folder of page.folders ?? []) {
|
|
441
|
+
folders.delete(folder.path);
|
|
442
|
+
folders.set(folder.path, folder);
|
|
443
|
+
}
|
|
444
|
+
view = page;
|
|
249
445
|
}
|
|
250
446
|
return {
|
|
251
|
-
|
|
447
|
+
authority: first.authority,
|
|
252
448
|
position: view.position,
|
|
253
|
-
logEpoch:
|
|
254
|
-
|
|
255
|
-
|
|
449
|
+
logEpoch: first.logEpoch,
|
|
450
|
+
changes: [...changes.values()],
|
|
451
|
+
...(folders.size === 0 ? {} : { folders: [...folders.values()] }),
|
|
256
452
|
};
|
|
257
453
|
}
|
|
258
|
-
export function
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
const
|
|
265
|
-
const changes = {};
|
|
266
|
-
const binaryTargets = [];
|
|
454
|
+
export function* bootstrapping(scope) {
|
|
455
|
+
const contents = new Map();
|
|
456
|
+
for (const entry of scope.contents) {
|
|
457
|
+
contents.set(entry.path, entry.content);
|
|
458
|
+
yield ROW_WEIGHT;
|
|
459
|
+
}
|
|
460
|
+
const answer = answering();
|
|
267
461
|
for (const file of scope.files) {
|
|
268
|
-
|
|
269
|
-
revisions[file.path] = file.revision;
|
|
462
|
+
yield ROW_WEIGHT;
|
|
270
463
|
if (file.head !== undefined)
|
|
271
|
-
changes
|
|
464
|
+
answer.changes.set(file.path, file.head);
|
|
272
465
|
const content = contents.get(file.path);
|
|
273
|
-
if (
|
|
274
|
-
|
|
275
|
-
else
|
|
276
|
-
documents
|
|
466
|
+
if (file.binary !== undefined)
|
|
467
|
+
answer.binaryFiles.set(file.path, file.binary);
|
|
468
|
+
else if (content !== undefined)
|
|
469
|
+
answer.documents.set(file.path, content);
|
|
470
|
+
if (file.revision !== undefined)
|
|
471
|
+
revised(answer, file.path, file.revision);
|
|
277
472
|
}
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
revisions,
|
|
283
|
-
changes,
|
|
284
|
-
binaryTargets: binaryTargets.sort(),
|
|
285
|
-
...declared(scope.attachments),
|
|
286
|
-
};
|
|
473
|
+
for (const folder of scope.folders ?? [])
|
|
474
|
+
folded(answer, folder, false);
|
|
475
|
+
const { removals: _removals, folderRemovals: _folderRemovals, ...page } = yield* answered(answer);
|
|
476
|
+
return { kind: 'bootstrap', roomVersion: roomVersion(scope), ...page };
|
|
287
477
|
}
|
|
288
478
|
export function schemaOf(scope, schema) {
|
|
289
479
|
const file = scope.files.find((entry) => entry.path === schema);
|
|
290
480
|
if (file === undefined)
|
|
291
|
-
return { schema: null, version: null };
|
|
481
|
+
return { schema: null, version: null, revision: null };
|
|
292
482
|
const content = scope.contents.find((entry) => entry.path === schema);
|
|
293
|
-
return content === undefined
|
|
483
|
+
return content === undefined
|
|
484
|
+
? null
|
|
485
|
+
: { schema: content.content, version: file.version, revision: file.revision ?? null };
|
|
294
486
|
}
|
|
295
487
|
export function viewOf(enumeration, tracked) {
|
|
296
488
|
return enumeration.authorities.find((entry) => entry.authority === tracked.authority);
|
|
297
489
|
}
|
|
298
|
-
|
|
490
|
+
function* refreshing(view, fromRoomVersion) {
|
|
299
491
|
if (roomVersion(view) === fromRoomVersion)
|
|
300
492
|
return { kind: 'still-current' };
|
|
301
|
-
const
|
|
302
|
-
const revisions = {};
|
|
303
|
-
const changes = {};
|
|
304
|
-
const binaryTargets = [];
|
|
305
|
-
const removals = [];
|
|
493
|
+
const answer = answering();
|
|
306
494
|
for (const change of view.changes) {
|
|
495
|
+
yield ROW_WEIGHT;
|
|
307
496
|
if ('removed' in change) {
|
|
308
|
-
removals.
|
|
497
|
+
answer.removals.add(change.path);
|
|
309
498
|
continue;
|
|
310
499
|
}
|
|
311
|
-
if ('content' in change)
|
|
312
|
-
documents
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
binaryTargets.push(change.path);
|
|
320
|
-
revisions[change.path] = change.reference.revision;
|
|
500
|
+
if ('content' in change)
|
|
501
|
+
answer.documents.set(change.path, change.content);
|
|
502
|
+
else
|
|
503
|
+
answer.binaryFiles.set(change.path, change.binary);
|
|
504
|
+
if (change.head !== undefined)
|
|
505
|
+
answer.changes.set(change.path, change.head);
|
|
506
|
+
if (change.revision !== undefined)
|
|
507
|
+
revised(answer, change.path, change.revision);
|
|
321
508
|
}
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
...declared(view.attachments),
|
|
331
|
-
};
|
|
509
|
+
for (const folder of view.folders ?? []) {
|
|
510
|
+
yield ROW_WEIGHT;
|
|
511
|
+
folded(answer, folder.path, folder.removed);
|
|
512
|
+
}
|
|
513
|
+
return { kind: 'net-advancement', roomVersion: roomVersion(view), ...(yield* answered(answer)) };
|
|
514
|
+
}
|
|
515
|
+
export async function refreshFrom(view, fromRoomVersion) {
|
|
516
|
+
return stepped(refreshing(view, fromRoomVersion));
|
|
332
517
|
}
|
package/dist/refusal.d.ts
CHANGED
|
@@ -1,9 +1,6 @@
|
|
|
1
1
|
import type { AdapterFailure, DiscoverResult, ProviderRefusal, ScopedRefusal } from '@agentshouse/mdruntime';
|
|
2
|
-
export
|
|
3
|
-
|
|
4
|
-
};
|
|
5
|
-
export declare function doorRefusal(body: unknown): DoorRefusal | null;
|
|
6
|
-
export declare function scopedRefusal(locator: string, scope: ScopedRefusal['scope'], refusal: DoorRefusal): ScopedRefusal;
|
|
2
|
+
export declare function doorRefusal(body: unknown): ProviderRefusal | null;
|
|
3
|
+
export declare function scopedRefusal(locator: string, scope: ScopedRefusal['scope'], refusal: ProviderRefusal): ScopedRefusal;
|
|
7
4
|
export declare function classifyDoor(status: number, body: unknown, locator: string): AdapterFailure | null;
|
|
8
5
|
export declare function classifyRead(status: number, body: unknown, locator: string): AdapterFailure | {
|
|
9
6
|
kind: 'beyond-horizon';
|
package/dist/refusal.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"refusal.d.ts","sourceRoot":"","sources":["../src/refusal.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,cAAc,EACd,cAAc,EACd,eAAe,EACf,aAAa,EACd,MAAM,wBAAwB,CAAC;AAEhC,
|
|
1
|
+
{"version":3,"file":"refusal.d.ts","sourceRoot":"","sources":["../src/refusal.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,cAAc,EACd,cAAc,EACd,eAAe,EACf,aAAa,EACd,MAAM,wBAAwB,CAAC;AAEhC,wBAAgB,WAAW,CAAC,IAAI,EAAE,OAAO,GAAG,eAAe,GAAG,IAAI,CAOjE;AAED,wBAAgB,aAAa,CAC3B,OAAO,EAAE,MAAM,EACf,KAAK,EAAE,aAAa,CAAC,OAAO,CAAC,EAC7B,OAAO,EAAE,eAAe,GACvB,aAAa,CAEf;AAqBD,wBAAgB,YAAY,CAC1B,MAAM,EAAE,MAAM,EACd,IAAI,EAAE,OAAO,EACb,OAAO,EAAE,MAAM,GACd,cAAc,GAAG,IAAI,CAMvB;AAED,wBAAgB,YAAY,CAC1B,MAAM,EAAE,MAAM,EACd,IAAI,EAAE,OAAO,EACb,OAAO,EAAE,MAAM,GACd,cAAc,GAAG;IAAE,IAAI,EAAE,gBAAgB,CAAA;CAAE,GAAG,IAAI,CAGpD;AAED,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,GAAG,cAAc,GAAG,IAAI,CAQrF"}
|