oui-spec 0.10.0 → 0.11.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +27 -0
- package/dist/{chunk-JOWXACVF.js → chunk-G4HLDVAI.js} +110 -4
- package/dist/chunk-G4HLDVAI.js.map +1 -0
- package/dist/{chunk-Z464LS7K.cjs → chunk-LCH3H5ZH.cjs} +143 -30
- package/dist/chunk-LCH3H5ZH.cjs.map +1 -0
- package/dist/{chunk-OJ6Y2WWS.cjs → chunk-MZ25RAQX.cjs} +117 -3
- package/dist/chunk-MZ25RAQX.cjs.map +1 -0
- package/dist/{chunk-UNQZXT7C.js → chunk-XJ34LTWV.js} +120 -8
- package/dist/chunk-XJ34LTWV.js.map +1 -0
- package/dist/core/index.cjs +11 -7
- package/dist/core/index.d.cts +2 -2
- package/dist/core/index.d.ts +2 -2
- package/dist/core/index.js +2 -2
- package/dist/index.cjs +75 -39
- package/dist/index.d.cts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +2 -2
- package/dist/react/index.d.cts +1 -1
- package/dist/react/index.d.ts +1 -1
- package/dist/spec/index.cjs +66 -34
- package/dist/spec/index.d.cts +59 -1
- package/dist/spec/index.d.ts +59 -1
- package/dist/spec/index.js +1 -1
- package/dist/{surface-runtime-DCPEz_JF.d.cts → surface-runtime-C3883XHJ.d.cts} +29 -1
- package/dist/{surface-runtime-B6NED8eV.d.ts → surface-runtime-Da1FSjNF.d.ts} +29 -1
- package/package.json +1 -1
- package/spec/OUI-SPEC-v0.1.md +30 -0
- package/dist/chunk-JOWXACVF.js.map +0 -1
- package/dist/chunk-OJ6Y2WWS.cjs.map +0 -1
- package/dist/chunk-UNQZXT7C.js.map +0 -1
- package/dist/chunk-Z464LS7K.cjs.map +0 -1
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var chunkMZ25RAQX_cjs = require('./chunk-MZ25RAQX.cjs');
|
|
4
4
|
var chunk2FFUDX2L_cjs = require('./chunk-2FFUDX2L.cjs');
|
|
5
5
|
|
|
6
6
|
// src/core/brand.ts
|
|
@@ -10,9 +10,9 @@ function brand(value) {
|
|
|
10
10
|
|
|
11
11
|
// src/core/define-surface.ts
|
|
12
12
|
function defineSurface(definition) {
|
|
13
|
-
if (definition.id ===
|
|
13
|
+
if (definition.id === chunkMZ25RAQX_cjs.OUI_RUNTIME_SURFACE) {
|
|
14
14
|
throw new Error(
|
|
15
|
-
`[OUI] "${
|
|
15
|
+
`[OUI] "${chunkMZ25RAQX_cjs.OUI_RUNTIME_SURFACE}" is the surface runtime's own id: give the surface another`
|
|
16
16
|
);
|
|
17
17
|
}
|
|
18
18
|
const actionIds = /* @__PURE__ */ new Set();
|
|
@@ -160,6 +160,8 @@ function createOUI(config) {
|
|
|
160
160
|
}
|
|
161
161
|
|
|
162
162
|
// src/core/surface-runtime.ts
|
|
163
|
+
var ATTACHMENT_LIST_MAX = 20;
|
|
164
|
+
var ATTACHMENT_RESOLVE_CONCURRENCY = 4;
|
|
163
165
|
var DEFAULT_QUIET_MS = 250;
|
|
164
166
|
var DEFAULT_SETTLE_TIMEOUT_MS = 5e3;
|
|
165
167
|
var DEFAULT_DEDUPE_WINDOW = 500;
|
|
@@ -192,7 +194,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
192
194
|
const indexOf = (surface) => {
|
|
193
195
|
let index = indexes.get(surface);
|
|
194
196
|
if (!index)
|
|
195
|
-
indexes.set(surface, index =
|
|
197
|
+
indexes.set(surface, index = chunkMZ25RAQX_cjs.surfaceIndex(manifestOf(surface)));
|
|
196
198
|
return index;
|
|
197
199
|
};
|
|
198
200
|
let nextKey = 1;
|
|
@@ -229,7 +231,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
229
231
|
return "it needs the user's approval, and the request carries none";
|
|
230
232
|
let hash;
|
|
231
233
|
try {
|
|
232
|
-
hash = await
|
|
234
|
+
hash = await chunkMZ25RAQX_cjs.argsHash(request.params ?? {});
|
|
233
235
|
} catch (err) {
|
|
234
236
|
return `its params cannot be checked against an approval: ${err instanceof Error ? err.message : String(err)}`;
|
|
235
237
|
}
|
|
@@ -461,9 +463,70 @@ function createSurfaceRuntime(options = {}) {
|
|
|
461
463
|
await sleep(Math.min(SETTLE_TICK_MS, deadline - now));
|
|
462
464
|
}
|
|
463
465
|
}
|
|
466
|
+
async function withAttachments(action, params) {
|
|
467
|
+
const misplaced = chunkMZ25RAQX_cjs.misplacedAttachmentInputs(action?.input);
|
|
468
|
+
if (misplaced.length > 0) {
|
|
469
|
+
return {
|
|
470
|
+
error: {
|
|
471
|
+
code: "ATTACHMENT_INPUT_UNSUPPORTED",
|
|
472
|
+
message: `This action declares an attached file at ${misplaced.join(", ")}, where none can be taken: a file is a property of the input, or an item of a list property.`
|
|
473
|
+
}
|
|
474
|
+
};
|
|
475
|
+
}
|
|
476
|
+
const wanted = chunkMZ25RAQX_cjs.attachmentIdsIn(action?.input, params);
|
|
477
|
+
if (wanted.length === 0) return { resolved: params };
|
|
478
|
+
const resolver = options.attachments;
|
|
479
|
+
if (!resolver) {
|
|
480
|
+
return {
|
|
481
|
+
error: {
|
|
482
|
+
code: "ATTACHMENTS_UNSUPPORTED",
|
|
483
|
+
message: "This page cannot take attached files: it was not given a way to open them."
|
|
484
|
+
}
|
|
485
|
+
};
|
|
486
|
+
}
|
|
487
|
+
const resolved = { ...params };
|
|
488
|
+
const once = /* @__PURE__ */ new Map();
|
|
489
|
+
for (const { path, input } of chunkMZ25RAQX_cjs.attachmentInputs(action?.input)) {
|
|
490
|
+
const value = params[path[0]];
|
|
491
|
+
const one = (id) => {
|
|
492
|
+
if (!chunkMZ25RAQX_cjs.isAttachmentId(id))
|
|
493
|
+
return Promise.reject(
|
|
494
|
+
new Error(`"${String(id)}" is not an attachment's id.`)
|
|
495
|
+
);
|
|
496
|
+
const key = `${input.as}:${id}`;
|
|
497
|
+
if (!once.has(key)) once.set(key, resolveOne(resolver, id, input));
|
|
498
|
+
return once.get(key);
|
|
499
|
+
};
|
|
500
|
+
try {
|
|
501
|
+
if (path.length === 2) {
|
|
502
|
+
if (Array.isArray(value)) {
|
|
503
|
+
if (value.length > ATTACHMENT_LIST_MAX)
|
|
504
|
+
throw new Error(
|
|
505
|
+
`it names ${value.length} files; a list takes at most ${ATTACHMENT_LIST_MAX}.`
|
|
506
|
+
);
|
|
507
|
+
resolved[path[0]] = await mapBounded(
|
|
508
|
+
value,
|
|
509
|
+
ATTACHMENT_RESOLVE_CONCURRENCY,
|
|
510
|
+
one
|
|
511
|
+
);
|
|
512
|
+
}
|
|
513
|
+
} else if (value !== void 0) {
|
|
514
|
+
resolved[path[0]] = await one(value);
|
|
515
|
+
}
|
|
516
|
+
} catch (err) {
|
|
517
|
+
return {
|
|
518
|
+
error: {
|
|
519
|
+
code: "ATTACHMENT_UNAVAILABLE",
|
|
520
|
+
message: `${path[0]}: ${err instanceof Error ? err.message : String(err)}`
|
|
521
|
+
}
|
|
522
|
+
};
|
|
523
|
+
}
|
|
524
|
+
}
|
|
525
|
+
return { resolved };
|
|
526
|
+
}
|
|
464
527
|
async function run(request) {
|
|
465
528
|
const startedAt = Date.now();
|
|
466
|
-
if (request.surfaceId ===
|
|
529
|
+
if (request.surfaceId === chunkMZ25RAQX_cjs.OUI_RUNTIME_SURFACE)
|
|
467
530
|
return builtin(request, startedAt);
|
|
468
531
|
const entry = activeFor(request.surfaceId);
|
|
469
532
|
let result;
|
|
@@ -481,17 +544,19 @@ function createSurfaceRuntime(options = {}) {
|
|
|
481
544
|
const declared = entry.surface.actions.find(
|
|
482
545
|
(a) => a.id === request.actionId
|
|
483
546
|
);
|
|
484
|
-
const refusal = declared &&
|
|
547
|
+
const refusal = declared && chunkMZ25RAQX_cjs.requiresApproval(declared.effect, declared.confirm) ? await approvalRefusal(request) : null;
|
|
485
548
|
result = refusal ? {
|
|
486
549
|
success: false,
|
|
487
550
|
error: {
|
|
488
551
|
code: "APPROVAL_REQUIRED",
|
|
489
552
|
message: `"${request.actionId}" was not run: ${refusal}.`
|
|
490
553
|
}
|
|
491
|
-
} : await
|
|
492
|
-
|
|
493
|
-
|
|
494
|
-
|
|
554
|
+
} : await withAttachments(declared, request.params ?? {}).then(
|
|
555
|
+
(params) => "error" in params ? { success: false, error: params.error } : entry.surface.executeAction(
|
|
556
|
+
request.actionId,
|
|
557
|
+
params.resolved,
|
|
558
|
+
entry.getContext()
|
|
559
|
+
)
|
|
495
560
|
);
|
|
496
561
|
if (result.success) {
|
|
497
562
|
const action = entry.surface.actions.find(
|
|
@@ -534,18 +599,18 @@ function createSurfaceRuntime(options = {}) {
|
|
|
534
599
|
surfacesHash: page.surfacesHash
|
|
535
600
|
};
|
|
536
601
|
const fit = {};
|
|
537
|
-
const carried =
|
|
538
|
-
const dataLimit = answerBytes -
|
|
539
|
-
const dataBytes =
|
|
602
|
+
const carried = chunkMZ25RAQX_cjs.jsonBytes(out.index ?? out.surfaces) >= answerBytes ? { ...out, index: void 0, surfaces: void 0 } : out;
|
|
603
|
+
const dataLimit = answerBytes - chunkMZ25RAQX_cjs.jsonBytes({ ...carried, data: void 0 }) - OBSERVATION_FLOOR_BYTES;
|
|
604
|
+
const dataBytes = chunkMZ25RAQX_cjs.jsonBytes(out.data);
|
|
540
605
|
if (dataBytes > Math.max(0, dataLimit)) {
|
|
541
606
|
delete out.data;
|
|
542
607
|
fit.data = { bytes: dataBytes, limit: Math.max(0, dataLimit) };
|
|
543
608
|
}
|
|
544
|
-
const fitted =
|
|
609
|
+
const fitted = chunkMZ25RAQX_cjs.fitObservations(
|
|
545
610
|
page.observations,
|
|
546
611
|
Math.max(
|
|
547
612
|
0,
|
|
548
|
-
answerBytes -
|
|
613
|
+
answerBytes - chunkMZ25RAQX_cjs.jsonBytes(
|
|
549
614
|
out.data === void 0 ? { ...carried, data: void 0 } : carried
|
|
550
615
|
)
|
|
551
616
|
)
|
|
@@ -566,7 +631,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
566
631
|
});
|
|
567
632
|
const refuse = (code, message) => done({ success: false, error: { code, message } });
|
|
568
633
|
const params = request.params ?? {};
|
|
569
|
-
if (request.actionId ===
|
|
634
|
+
if (request.actionId === chunkMZ25RAQX_cjs.OUI_DESCRIBE_ACTION) {
|
|
570
635
|
const asked = params.actions;
|
|
571
636
|
if (!Array.isArray(asked) || asked.length === 0 || !asked.every(
|
|
572
637
|
(a) => a && typeof a === "object" && typeof a.surface === "string" && typeof a.action === "string"
|
|
@@ -587,7 +652,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
587
652
|
missing.push({ surface, action });
|
|
588
653
|
continue;
|
|
589
654
|
}
|
|
590
|
-
const size =
|
|
655
|
+
const size = chunkMZ25RAQX_cjs.jsonBytes(definition);
|
|
591
656
|
if (definitions.length > 0 && bytes + size > answerBytes - OBSERVATION_FLOOR_BYTES) {
|
|
592
657
|
deferred.push({ surface, action });
|
|
593
658
|
continue;
|
|
@@ -604,7 +669,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
604
669
|
}
|
|
605
670
|
});
|
|
606
671
|
}
|
|
607
|
-
if (request.actionId ===
|
|
672
|
+
if (request.actionId === chunkMZ25RAQX_cjs.OUI_READ_ACTION) {
|
|
608
673
|
const { surface, observation } = params;
|
|
609
674
|
const path = params.path === void 0 ? "" : params.path;
|
|
610
675
|
const offset = params.offset === void 0 ? 0 : params.offset;
|
|
@@ -631,7 +696,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
631
696
|
}
|
|
632
697
|
let value;
|
|
633
698
|
try {
|
|
634
|
-
value =
|
|
699
|
+
value = chunkMZ25RAQX_cjs.atPointer(values.get(observation), path);
|
|
635
700
|
} catch (err) {
|
|
636
701
|
return refuse(
|
|
637
702
|
"INVALID_PARAMS",
|
|
@@ -651,7 +716,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
651
716
|
offset,
|
|
652
717
|
offset + limit
|
|
653
718
|
);
|
|
654
|
-
while (rows.length > 1 &&
|
|
719
|
+
while (rows.length > 1 && chunkMZ25RAQX_cjs.jsonBytes(rows) > room)
|
|
655
720
|
rows = rows.slice(0, Math.ceil(rows.length / 2));
|
|
656
721
|
const next = offset + rows.length;
|
|
657
722
|
return done({
|
|
@@ -664,7 +729,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
664
729
|
}
|
|
665
730
|
});
|
|
666
731
|
}
|
|
667
|
-
const fitted =
|
|
732
|
+
const fitted = chunkMZ25RAQX_cjs.fitObservations(
|
|
668
733
|
{ [surface]: { [observation]: value } },
|
|
669
734
|
room
|
|
670
735
|
);
|
|
@@ -679,7 +744,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
679
744
|
}
|
|
680
745
|
return refuse(
|
|
681
746
|
"ACTION_NOT_FOUND",
|
|
682
|
-
`The runtime answers "${
|
|
747
|
+
`The runtime answers "${chunkMZ25RAQX_cjs.OUI_DESCRIBE_ACTION}" and "${chunkMZ25RAQX_cjs.OUI_READ_ACTION}"; it has no "${request.actionId}".`
|
|
683
748
|
);
|
|
684
749
|
}
|
|
685
750
|
function answer(result, onReceived) {
|
|
@@ -732,20 +797,20 @@ function createSurfaceRuntime(options = {}) {
|
|
|
732
797
|
}
|
|
733
798
|
if (form === "index") {
|
|
734
799
|
const index = active.map((e) => indexOf(e.surface));
|
|
735
|
-
return { index, observations: obs, surfacesHash:
|
|
800
|
+
return { index, observations: obs, surfacesHash: chunkMZ25RAQX_cjs.surfacesHash(index) };
|
|
736
801
|
}
|
|
737
802
|
const surfaces = active.map((e) => manifestOf(e.surface));
|
|
738
803
|
return {
|
|
739
804
|
surfaces,
|
|
740
805
|
observations: obs,
|
|
741
|
-
surfacesHash:
|
|
806
|
+
surfacesHash: chunkMZ25RAQX_cjs.surfacesHash(surfaces)
|
|
742
807
|
};
|
|
743
808
|
}
|
|
744
809
|
function snapshot() {
|
|
745
810
|
const page = capture();
|
|
746
811
|
const offered = form === "index" ? { index: page.index } : { surfaces: page.surfaces };
|
|
747
|
-
const offeredBytes =
|
|
748
|
-
const fitted =
|
|
812
|
+
const offeredBytes = chunkMZ25RAQX_cjs.jsonBytes(offered);
|
|
813
|
+
const fitted = chunkMZ25RAQX_cjs.fitObservations(
|
|
749
814
|
page.observations,
|
|
750
815
|
offeredBytes >= snapshotBytes ? snapshotBytes : snapshotBytes - offeredBytes
|
|
751
816
|
);
|
|
@@ -857,7 +922,7 @@ function createSurfaceRuntime(options = {}) {
|
|
|
857
922
|
};
|
|
858
923
|
},
|
|
859
924
|
grantApproval(grant) {
|
|
860
|
-
if (!grant || typeof grant.approvalId !== "string" || !grant.approvalId || typeof grant.argsHash !== "string" || !
|
|
925
|
+
if (!grant || typeof grant.approvalId !== "string" || !grant.approvalId || typeof grant.argsHash !== "string" || !chunkMZ25RAQX_cjs.ARGS_HASH_PATTERN.test(grant.argsHash) || !Number.isFinite(grant.expiresAt)) {
|
|
861
926
|
throw new Error(
|
|
862
927
|
"[OUI] grantApproval needs an approvalId, an args hash and an expiry"
|
|
863
928
|
);
|
|
@@ -906,6 +971,53 @@ function toJsonSafe(value) {
|
|
|
906
971
|
return String(value);
|
|
907
972
|
}
|
|
908
973
|
}
|
|
974
|
+
async function resolveOne(resolver, id, input) {
|
|
975
|
+
const got = await resolver.resolve(id, input.as);
|
|
976
|
+
const refuse = (name, type) => new Error(
|
|
977
|
+
`"${name}" is ${type || "of no type"}; this takes ${input.mediaTypes.join(", ")}.`
|
|
978
|
+
);
|
|
979
|
+
if (typeof got === "string") {
|
|
980
|
+
if (input.as === "file")
|
|
981
|
+
throw new Error(
|
|
982
|
+
"The page's file area gave text where a file was expected."
|
|
983
|
+
);
|
|
984
|
+
if (input.mediaTypes?.length)
|
|
985
|
+
throw new Error(
|
|
986
|
+
"The page's file area gave the file's text without its type, so it cannot be checked against what this takes."
|
|
987
|
+
);
|
|
988
|
+
return got;
|
|
989
|
+
}
|
|
990
|
+
if (typeof Blob !== "undefined" && got instanceof Blob) {
|
|
991
|
+
const name = got.name ?? id;
|
|
992
|
+
if (!chunkMZ25RAQX_cjs.acceptsMediaType(input, got.type)) throw refuse(name, got.type);
|
|
993
|
+
return input.as === "text" ? await got.text() : got;
|
|
994
|
+
}
|
|
995
|
+
if (got && typeof got === "object" && typeof got.text === "string") {
|
|
996
|
+
const text = got;
|
|
997
|
+
if (input.as === "file")
|
|
998
|
+
throw new Error(
|
|
999
|
+
"The page's file area gave text where a file was expected."
|
|
1000
|
+
);
|
|
1001
|
+
if (!chunkMZ25RAQX_cjs.acceptsMediaType(input, text.mediaType ?? ""))
|
|
1002
|
+
throw refuse(text.name ?? id, text.mediaType);
|
|
1003
|
+
return text.text;
|
|
1004
|
+
}
|
|
1005
|
+
throw new Error("The page's file area gave nothing that can be used.");
|
|
1006
|
+
}
|
|
1007
|
+
async function mapBounded(items, limit, fn) {
|
|
1008
|
+
const out = new Array(items.length);
|
|
1009
|
+
let next = 0;
|
|
1010
|
+
const worker = async () => {
|
|
1011
|
+
while (next < items.length) {
|
|
1012
|
+
const index = next++;
|
|
1013
|
+
out[index] = await fn(items[index]);
|
|
1014
|
+
}
|
|
1015
|
+
};
|
|
1016
|
+
await Promise.all(
|
|
1017
|
+
Array.from({ length: Math.min(limit, items.length) }, worker)
|
|
1018
|
+
);
|
|
1019
|
+
return out;
|
|
1020
|
+
}
|
|
909
1021
|
|
|
910
1022
|
// src/core/accept-turn.ts
|
|
911
1023
|
function acceptCurrentTurn(currentTurn) {
|
|
@@ -917,9 +1029,10 @@ function acceptCurrentTurn(currentTurn) {
|
|
|
917
1029
|
};
|
|
918
1030
|
}
|
|
919
1031
|
|
|
1032
|
+
exports.ATTACHMENT_LIST_MAX = ATTACHMENT_LIST_MAX;
|
|
920
1033
|
exports.acceptCurrentTurn = acceptCurrentTurn;
|
|
921
1034
|
exports.createOUI = createOUI;
|
|
922
1035
|
exports.createSurfaceRuntime = createSurfaceRuntime;
|
|
923
1036
|
exports.defineSurface = defineSurface;
|
|
924
|
-
//# sourceMappingURL=chunk-
|
|
925
|
-
//# sourceMappingURL=chunk-
|
|
1037
|
+
//# sourceMappingURL=chunk-LCH3H5ZH.cjs.map
|
|
1038
|
+
//# sourceMappingURL=chunk-LCH3H5ZH.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/core/brand.ts","../src/core/define-surface.ts","../src/core/create-oui.ts","../src/core/surface-runtime.ts","../src/core/accept-turn.ts"],"names":["OUI_RUNTIME_SURFACE","createWebSocketTransport","surfaceIndex","argsHash","misplacedAttachmentInputs","attachmentIdsIn","attachmentInputs","isAttachmentId","requiresApproval","jsonBytes","fitObservations","OUI_DESCRIBE_ACTION","OUI_READ_ACTION","atPointer","frame","surfacesHash","ARGS_HASH_PATTERN","acceptsMediaType"],"mappings":"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","file":"chunk-LCH3H5ZH.cjs","sourcesContent":["/**\n * Nominal branding for values OUI must construct itself.\n *\n * Structural typing means any object with the right shape satisfies an\n * interface. That is how Closure Studio ended up hand-rolling OUI's transport:\n * `SocketLike` was importable, `OUITransport` was a plain interface, so an\n * integrator could satisfy every type without ever calling OUI. The result was\n * a second implementation of the wire — hardcoded namespace, re-declared\n * payload types on the server, and a dead `action:result` mapping alongside the\n * observation channel that already carried results.\n *\n * A unique symbol cannot be produced outside this module. Branding the types\n * OUI owns turns \"you should use our constructor\" into \"you cannot compile\n * without it\".\n */\n\ndeclare const OUI_BRAND: unique symbol;\n\n/** Marks a value as constructed by OUI itself. */\nexport interface OUIBranded<TKind extends string> {\n readonly [OUI_BRAND]: TKind;\n}\n\n/**\n * Attach the brand at runtime. The property does not exist at runtime — the\n * symbol is declare-only — so this is a type-level assertion with no cost.\n */\nexport function brand<TKind extends string, T>(\n value: T,\n): T & OUIBranded<TKind> {\n return value as T & OUIBranded<TKind>;\n}\n","import type {\n OUISurface,\n OUIAction,\n OUIObservation,\n OUIActivation,\n OUIActionPolling,\n JSONSchema,\n OUIEffectKind,\n} from \"../spec/index.js\";\nimport { OUI_RUNTIME_SURFACE } from \"../spec/index-form.js\";\nimport { brand, type OUIBranded } from \"./brand.js\";\n\n/**\n * Configuration for defining an OUI surface with handlers.\n * This is the \"integration file\" an app provides — it declares both\n * the schema (what the agent sees) and the implementation (what executes).\n */\nexport interface SurfaceDefinition<TContext = unknown> {\n id: string;\n name: string;\n description: string;\n version?: string;\n activation?: OUIActivation;\n actions: ActionDefinition<TContext>[];\n observations?: ObservationDefinition[];\n metadata?: Record<string, unknown>;\n}\n\n/**\n * Polling config with an optional resolve handler.\n * The spec's OUIActionPolling is the manifest shape (no functions).\n * The core extends it with the resolve implementation for the runtime.\n */\nexport interface ActionPollingConfig<\n TContext = unknown,\n> extends OUIActionPolling {\n /**\n * Called on each poll interval. Receives the dispatch result from the handler\n * plus the current context. Return { done: true, data } to stop polling,\n * or { done: false, data } to continue.\n *\n * Work that ended in failure returns { done: true, data, error }: the final\n * result is then a failure (§7.3.3) carrying `error`, with `data` kept, so\n * the agent never records failed work as a success.\n */\n resolve?: (\n dispatchResult: unknown,\n context: TContext,\n ) => Promise<{\n done: boolean;\n data: unknown;\n error?: { code: string; message: string };\n }>;\n}\n\n/**\n * An action definition includes both the schema (for the agent) and\n * the handler (for execution). This is the single source of truth —\n * no separate YAML, no separate listener, no drift possible.\n */\nexport interface ActionDefinition<TContext = unknown> {\n id: string;\n description: string;\n /** Its name as a person reads it, for a confirmation the user approves. */\n title?: string;\n /** What using it does; a `transaction` runs only on the user's approval of the exact request. */\n effect?: OUIEffectKind;\n input: JSONSchema;\n output?: JSONSchema;\n /** Destructive: it runs only on the user's approval of the exact request, unless it only reads. */\n confirm?: boolean;\n async?: boolean;\n\n /**\n * Polling/subscription config for async actions.\n * After the handler returns, the OUI runtime starts polling or subscribing\n * and pushes observation updates until the operation completes.\n * Extends the spec's OUIActionPolling with an optional resolve handler.\n */\n polling?: ActionPollingConfig<TContext>;\n\n usage?: string;\n preconditions?: string;\n estimatedDuration?: string;\n tags?: string[];\n\n /**\n * The handler that executes when the agent invokes this action.\n * Receives typed params and a context object (app-specific state/utilities).\n * Returns a result that the agent sees as the tool output.\n */\n handler: (\n params: Record<string, unknown>,\n context: TContext,\n ) => Promise<ActionHandlerResult>;\n}\n\nexport interface ActionHandlerResult {\n success: boolean;\n data?: unknown;\n error?: { code: string; message: string; details?: unknown };\n /** For async actions: metadata passed to the polling resolver */\n dispatchMeta?: Record<string, unknown>;\n}\n\nexport interface ObservationDefinition {\n id: string;\n description: string;\n schema: JSONSchema;\n /** Function that returns the current observation value */\n getValue?: () => unknown;\n}\n\n/**\n * Define an OUI surface — the single entry point for integrating\n * an application feature with the OUI protocol.\n *\n * This function validates the definition and returns a typed surface\n * object that can be registered with an agent runtime or transport layer.\n *\n * @example\n * ```typescript\n * const mySurface = defineSurface({\n * id: 'my-feature',\n * name: 'My Feature',\n * description: 'Does something cool',\n * actions: [\n * {\n * id: 'do_thing',\n * description: 'Does the thing',\n * input: { type: 'object', properties: { name: { type: 'string' } }, required: ['name'] },\n * handler: async (params) => {\n * const result = await doTheThing(params.name);\n * return { success: true, data: result };\n * },\n * },\n * ],\n * });\n * ```\n */\nexport function defineSurface<\n TContext = unknown,\n const TId extends string = string,\n>(\n definition: SurfaceDefinition<TContext> & { id: TId },\n): DefinedSurface<TContext> & { id: TId } {\n // The runtime answers this id itself (§7.3.10).\n if (definition.id === OUI_RUNTIME_SURFACE) {\n throw new Error(\n `[OUI] \"${OUI_RUNTIME_SURFACE}\" is the surface runtime's own id: give the surface another`,\n );\n }\n\n // Validate: no duplicate action IDs\n const actionIds = new Set<string>();\n for (const action of definition.actions) {\n if (actionIds.has(action.id)) {\n throw new Error(\n `[OUI] Duplicate action ID \"${action.id}\" in surface \"${definition.id}\"`,\n );\n }\n actionIds.add(action.id);\n }\n\n // Validate: no duplicate observation IDs\n if (definition.observations) {\n const obsIds = new Set<string>();\n for (const obs of definition.observations) {\n if (obsIds.has(obs.id)) {\n throw new Error(\n `[OUI] Duplicate observation ID \"${obs.id}\" in surface \"${definition.id}\"`,\n );\n }\n obsIds.add(obs.id);\n }\n }\n\n return brand<\"surface\", unknown>({\n ...definition,\n\n /** Extract the manifest (schema only, no handlers) for transmission to the agent runtime */\n toManifest(): OUISurface {\n return {\n id: definition.id,\n name: definition.name,\n description: definition.description,\n version: definition.version,\n activation: definition.activation,\n actions: definition.actions.map(actionToManifest),\n observations: definition.observations?.map(obsToManifest),\n metadata: definition.metadata,\n };\n },\n\n /** Execute an action by ID with the given params and context */\n async executeAction(\n actionId: string,\n params: Record<string, unknown>,\n context: TContext,\n ): Promise<ActionHandlerResult> {\n const action = definition.actions.find((a) => a.id === actionId);\n if (!action) {\n return {\n success: false,\n error: {\n code: \"ACTION_NOT_FOUND\",\n message: `Action \"${actionId}\" not found on surface \"${definition.id}\"`,\n },\n };\n }\n try {\n return await action.handler(params, context);\n } catch (err) {\n return {\n success: false,\n error: {\n code: \"ACTION_EXECUTION_ERROR\",\n message: err instanceof Error ? err.message : String(err),\n },\n };\n }\n },\n\n /** Get all action IDs */\n getActionIds(): string[] {\n return definition.actions.map((a) => a.id);\n },\n\n /** Get the polling config for an action (if async) */\n getPollingConfig(actionId: string): OUIActionPolling | undefined {\n const action = definition.actions.find((a) => a.id === actionId);\n return action?.polling;\n },\n }) as DefinedSurface<TContext> & { id: TId };\n}\n\n/** A fully defined surface with both manifest extraction and execution capabilities */\n/**\n * Branded so it can only come from `defineSurface`.\n *\n * Without the brand a plain object literal satisfies this interface\n * structurally, which is how an integrator can assemble a surface that never\n * ran defineSurface's duplicate-id checks and never produced a real manifest.\n */\nexport interface DefinedSurface<TContext = unknown>\n extends SurfaceDefinition<TContext>, OUIBranded<\"surface\"> {\n toManifest(): OUISurface;\n executeAction(\n actionId: string,\n params: Record<string, unknown>,\n context: TContext,\n ): Promise<ActionHandlerResult>;\n getActionIds(): string[];\n /** Get the polling config for an action (if async) */\n getPollingConfig(actionId: string): OUIActionPolling | undefined;\n}\n\n// ─── Internal helpers ────────────────────────────────────────────────────────\n\nfunction actionToManifest<T>(action: ActionDefinition<T>): OUIAction {\n return {\n id: action.id,\n description: action.description,\n ...(action.title !== undefined ? { title: action.title } : {}),\n ...(action.effect !== undefined ? { effect: action.effect } : {}),\n input: action.input,\n output: action.output,\n confirm: action.confirm,\n async: action.async,\n polling: action.polling,\n usage: action.usage,\n preconditions: action.preconditions,\n estimatedDuration: action.estimatedDuration,\n tags: action.tags,\n };\n}\n\nfunction obsToManifest(obs: ObservationDefinition): OUIObservation {\n return {\n id: obs.id,\n description: obs.description,\n schema: obs.schema,\n };\n}\n","/**\n * createOUI — a fixed set of surfaces announced over one socket.\n *\n * For a client whose surfaces come and go (a React app, where a page's\n * surfaces mount with the page), use `createSurfaceRuntime` instead: it keeps\n * the client's own record of what is mounted and answers every request.\n *\n * WHY THIS EXISTS\n *\n * OUI shipped a correct protocol and a correct transport, and its first\n * integrator used neither. studio-ui imported only the `SocketLike` TYPE from\n * oui-spec and rebuilt the wire by hand: a literal map of protocol types to\n * socket names, `oui:` hardcoded so the configurable namespace was unreachable,\n * payload interfaces re-declared on the server, and an `action:result` channel\n * mapped but never sent — duplicating the observation channel that already\n * carries results.\n *\n * Nothing was wrong with the spec. Nothing enforced it. Structural typing meant\n * every hand-rolled piece type-checked, and both ends agreed only by the\n * coincidence of matching string literals. Rename one and the other keeps\n * compiling and silently stops receiving.\n *\n * So the requirements are gated here:\n *\n * OUI owns the wire. The integrator provides a socket; it cannot provide a\n * transport, because `OUITransport` values are branded and only this module\n * brands them.\n *\n * OUI owns the result path. Every dispatch carries a requestId and is\n * answered on OUI's result channel. An integrator cannot add a parallel\n * channel because it cannot construct a transport to add one to.\n *\n * The integrator owns content. Surfaces, action schemas, observation schemas\n * and handlers all arrive through `defineSurface`, whose output is branded —\n * so a plain object shaped like a surface will not compile.\n *\n * Violations fail at compile time with a message naming the offending id.\n */\nimport type { OUITransport, OUITransportConfig } from \"../transport/types.js\";\nimport type { SocketLike } from \"../transport/websocket.js\";\nimport { createWebSocketTransport } from \"../transport/websocket.js\";\nimport type { DefinedSurface } from \"./define-surface.js\";\nimport { brand, type OUIBranded } from \"./brand.js\";\nimport type { OUIConfigError, ValidateSurfaceIds } from \"./validate.js\";\nimport type { OUISurface } from \"../spec/index.js\";\n\n/** A transport OUI constructed. Integrators cannot produce one. */\nexport type OwnedTransport = OUITransport & OUIBranded<\"transport\">;\n\n/** Surface ids as literal types, for the duplicate check. */\ntype SurfaceIds<T extends readonly DefinedSurface<never>[]> = {\n [K in keyof T]: T[K][\"id\"];\n};\n\nexport interface OUIConfig<TSurfaces extends readonly DefinedSurface<never>[]> {\n /**\n * The socket OUI will speak over. The integrator owns the connection —\n * auth, reconnection, lifecycle — and OUI owns what travels on it.\n */\n socket: SocketLike;\n\n /**\n * Surfaces produced by `defineSurface`. A plain object with the same shape\n * will not compile: DefinedSurface is branded.\n */\n surfaces: TSurfaces;\n\n /**\n * Wire configuration. `namespace` defaults to 'oui' and is the supported way\n * to change the event prefix — hardcoding it at the call site is what made\n * this option unreachable in the first integration.\n */\n transport?: Omit<OUITransportConfig, \"namespace\"> & { namespace?: string };\n}\n\n/** A live OUI instance. */\nexport interface OUIInstance {\n /** The transport OUI owns. Exposed for wiring, not for reimplementation. */\n readonly transport: OwnedTransport;\n\n /** Manifests for every registered surface, as the agent sees them. */\n readonly manifests: readonly OUISurface[];\n\n /** Register every surface and connect. */\n start(): Promise<void>;\n\n /**\n * Deregister every surface and detach OUI from the socket. The socket stays\n * connected: the integrator owns it, and other code may share it.\n */\n stop(): void;\n\n /** Look up a registered surface by id. */\n getSurface(id: string): DefinedSurface<never> | undefined;\n}\n\n/**\n * Instantiate OUI.\n *\n * `const` on the type parameter captures surface ids as literal types, which is\n * what allows duplicate detection to name the offending id rather than failing\n * with an unassignable-to-never error.\n */\nexport function createOUI<\n const TSurfaces extends readonly DefinedSurface<never>[],\n>(\n config: OUIConfig<TSurfaces> & ValidateSurfaceIds<SurfaceIds<TSurfaces>>,\n): OUIInstance {\n const {\n socket,\n surfaces,\n transport: transportConfig,\n } = config as OUIConfig<TSurfaces>;\n\n // Defensive, not decorative: the compile-time checks only bind when a caller\n // passes literals. A surface list assembled at runtime, or JS with no types\n // at all, reaches here unchecked.\n if (!socket) {\n throw new Error(\n \"[OUI] createOUI requires a socket. OUI owns the wire; the integrator owns the connection.\",\n );\n }\n if (!Array.isArray(surfaces) || surfaces.length === 0) {\n throw new Error(\"[OUI] createOUI requires at least one surface.\");\n }\n\n const seen = new Set<string>();\n for (const surface of surfaces) {\n if (seen.has(surface.id)) {\n throw new Error(\n `[OUI] Duplicate surface id \"${surface.id}\". Registration is keyed by id, so the second would replace the first.`,\n );\n }\n seen.add(surface.id);\n }\n\n const transport = brand<\"transport\", OUITransport>(\n createWebSocketTransport(socket, transportConfig),\n );\n\n const byId = new Map(surfaces.map((s) => [s.id, s] as const));\n\n return {\n transport,\n manifests: surfaces.map((s) => s.toManifest()),\n\n async start() {\n await transport.connect();\n for (const surface of surfaces) {\n transport.registerSurface(surface.toManifest());\n }\n },\n\n stop() {\n for (const surface of surfaces) {\n transport.deregisterSurface(surface.id);\n }\n transport.dispose();\n },\n\n getSurface(id) {\n return byId.get(id);\n },\n };\n}\n\n/** Re-exported so integrators can name the error type in tests. */\nexport type { OUIConfigError };\n","/**\n * The client-side surface runtime.\n *\n * Holds the surfaces a client has mounted, answers every action request with a\n * result, and produces the snapshot an agent runtime works from.\n *\n * WHY THIS EXISTS\n *\n * The first integration kept no client-side record of what was mounted. Each\n * surface hook registered itself with a server-side registry and listened for\n * dispatches on its own. Three things followed:\n *\n * - The registry was the only record of what the client could do, and it lost\n * entries: a dead socket's cleanup removed a live tab's registration, and the\n * browser never registered again. The agent then had no UI tools at all.\n * - Nothing answered a dispatch. The agent was told an action succeeded before\n * the client had run it, and never saw the page an action led to.\n * - Every hook listened independently, through two paths, so one dispatch ran\n * twice and nothing de-duplicated it.\n *\n * Here the client is the record. `snapshot()` is what the client can do right\n * now, and every request is run once, waited on until the UI settles, and\n * answered with its result and the snapshot after it.\n */\nimport type {\n OUIAction,\n OUIActionRequest,\n OUIActionResult,\n OUIApprovalGrant,\n OUIFit,\n OUIIndexSnapshot,\n OUIResultDelivery,\n OUISurface,\n OUISurfaceIndex,\n OUISurfaceSnapshot,\n OUIObservationSnapshot,\n JSONSchema,\n} from \"../spec/index.js\";\nimport {\n ARGS_HASH_PATTERN,\n argsHash,\n requiresApproval,\n} from \"../spec/approval.js\";\nimport { surfacesHash } from \"../spec/surfaces-hash.js\";\nimport {\n acceptsMediaType,\n attachmentIdsIn,\n attachmentInputs,\n isAttachmentId,\n misplacedAttachmentInputs,\n type OUIAttachmentInput,\n} from \"../spec/attachments.js\";\nimport {\n jsonBytes,\n OUI_DESCRIBE_ACTION,\n OUI_READ_ACTION,\n OUI_RUNTIME_SURFACE,\n surfaceIndex,\n} from \"../spec/index-form.js\";\nimport { atPointer, fitObservations } from \"../spec/fit.js\";\nimport type { OUITransport, OUITransportConfig } from \"../transport/types.js\";\nimport {\n createWebSocketTransport,\n type SocketLike,\n} from \"../transport/websocket.js\";\nimport type {\n ActionHandlerResult,\n ActionPollingConfig,\n DefinedSurface,\n} from \"./define-surface.js\";\n\n// ─── Options ─────────────────────────────────────────────────────────────────\n\nexport interface SettleOptions {\n /**\n * The UI counts as settled once nothing has mounted, unmounted or changed an\n * observation for this long, and no hold is open. Default 250 ms.\n */\n quietMs?: number;\n /** Give up waiting after this long and answer with `settled: false`. Default 5000 ms. */\n timeoutMs?: number;\n}\n\nexport interface SurfaceRuntimeOptions {\n /** The socket to answer requests on. Can be set or replaced later with `attach`. */\n socket?: SocketLike | null;\n\n /** Wire configuration for the transport the runtime builds on the socket. */\n transport?: OUITransportConfig;\n\n /**\n * Also announce registrations and observations over the transport, for agent\n * runtimes that keep a server-side registry. Default true.\n *\n * An agent runtime that takes the client's snapshot instead (sent with each\n * turn, and returned on every result) has no use for them: set false.\n */\n announce?: boolean;\n\n settle?: SettleOptions;\n\n /** How many answered request ids to remember, for de-duplication. Default 500. */\n dedupeWindow?: number;\n\n /**\n * Decides whether a request that arrived on the socket may run at all. A\n * refused request is not run: its sender gets a receipt saying it was\n * received and not accepted, and the refusal is logged.\n *\n * The server should be the only sender of action requests, but a client can\n * also check that a request is one it expects: for example, only for the\n * turn its agent is running now (the request's `turnId`), so a request sent\n * late by a stopped turn does not run. Requests passed to `execute` directly are\n * not checked; they come from the application itself.\n */\n accept?: (request: OUIActionRequest) => boolean;\n\n /**\n * What a snapshot and an answer say of the mounted surfaces (§7.3.8):\n * - `\"index\"`: each action as an index entry. The agent runtime fetches a\n * definition when it needs one (`oui.describe`). Use it with an agent\n * runtime that reads the index form.\n * - `\"full\"` (the default until 1.0): each action's whole definition, as\n * every earlier version sent. A page's definitions can outweigh what a\n * frame may carry; then its answers are refused and arrive trimmed.\n */\n form?: \"index\" | \"full\";\n\n /** The most bytes of JSON a frame carries; what does not fit is shortened and said so (§7.3.9). */\n budgets?: {\n /** One answer. Default 480 KB: under the 512 KB a relay commonly caps a frame at. */\n answerBytes?: number;\n /** One snapshot, as sent with a turn. Default 256 KB. */\n snapshotBytes?: number;\n };\n\n /**\n * A request sent again while its answer is on the way is not answered again\n * (§7.3.7): every copy of a large answer queues on the one socket, ahead of\n * the next request's answer. Only once the answer has gone this long without\n * the receiver acknowledging it — lost, or a receiver that does not\n * acknowledge — is a repeat answered again. Default 8000 ms.\n */\n reanswerAfterMs?: number;\n\n /**\n * The host's file area, for actions whose input takes a file the person\n * attached (`format: \"oui-attachment\"`, §7.3.11). The agent sends the\n * attachment's id; before the handler runs, the runtime resolves it to what\n * the input declares (`as`): a `File`, or the file's text. The host checks\n * the file is the person's. Without it, such an action is refused.\n */\n attachments?: AttachmentResolver;\n}\n\n/** A file's text as a host resolves it, with what the file is, so its type can be checked (§7.3.11). */\nexport interface AttachmentText {\n name: string;\n mediaType: string;\n text: string;\n}\n\n/** How a client turns an attachment's id into what an action takes (§7.3.11). */\nexport interface AttachmentResolver {\n /**\n * The file, as a `File`, or as its text with its name and type. A `File`\n * for an input that takes text is read as text once its type is checked.\n * A bare string is taken only by an input that accepts any type: there is\n * nothing to check it against. Rejects with an `Error` whose message says\n * why (it is not the person's, it was removed, it is still being checked),\n * which the agent is told.\n */\n resolve(\n id: string,\n as: \"file\" | \"text\",\n ): Promise<File | AttachmentText | string>;\n}\n\n/** The most files one list input takes (§7.3.11). */\nexport const ATTACHMENT_LIST_MAX = 20;\n/** How many files a runtime resolves at once. */\nconst ATTACHMENT_RESOLVE_CONCURRENCY = 4;\n\n// ─── Public types ────────────────────────────────────────────────────────────\n\nexport interface MountedSurface {\n readonly surfaceId: string;\n /** Record an observation value. A no-op once unmounted. */\n pushObservation(observationId: string, value: unknown): void;\n /** Remove this mount. Other mounts of the same surface id are unaffected. */\n unmount(): void;\n}\n\n/** The form a runtime sends its surfaces in (§7.3.8). */\nexport type SurfaceForm = \"full\" | \"index\";\n\nexport interface SurfaceRuntime<F extends SurfaceForm = \"full\"> {\n /**\n * Mount a surface. `getContext` is read when an action runs, so handlers see\n * the latest state rather than the state at mount time.\n *\n * Mounting the same surface id twice is allowed (React StrictMode does it on\n * every mount); the most recent mount serves its actions.\n */\n mount<TContext>(\n surface: DefinedSurface<TContext>,\n getContext: () => TContext,\n ): MountedSurface;\n\n /** Answer requests arriving on this socket (null detaches). */\n attach(socket: SocketLike | null): void;\n\n /** What the client can do right now. */\n snapshot(): F extends \"index\" ? OUIIndexSnapshot : OUISurfaceSnapshot;\n\n /**\n * Run a request once and resolve with its result. A request id seen before\n * resolves with the first result instead of running again.\n */\n execute(request: OUIActionRequest): Promise<OUIActionResult>;\n\n /**\n * Keep the UI unsettled until the returned function is called. For work an\n * action starts that mounting and unmounting cannot show, such as a route's\n * code still loading or a page fetching the data it will display.\n */\n hold(): () => void;\n\n /**\n * Record that the user approved one request, here, through their own\n * confirmation (the agent runtime's approval store answered it to this tab).\n * An action that needs approval — a `transaction`, or a destructive write —\n * runs only on a request whose `approval` matches an unused, unexpired grant\n * for exactly its params. Each grant admits one request.\n */\n grantApproval(grant: OUIApprovalGrant): void;\n\n /** Called whenever the snapshot changes. */\n subscribe(listener: () => void): () => void;\n\n /** Stop polling, detach from the socket and forget every mount. */\n dispose(): void;\n}\n\n// ─── Implementation ──────────────────────────────────────────────────────────\n\ninterface Entry {\n key: number;\n surface: DefinedSurface<unknown>;\n getContext: () => unknown;\n}\n\nconst DEFAULT_QUIET_MS = 250;\nconst DEFAULT_SETTLE_TIMEOUT_MS = 5000;\nconst DEFAULT_DEDUPE_WINDOW = 500;\nconst DEFAULT_REANSWER_AFTER_MS = 8000;\nconst SETTLE_TICK_MS = 50;\nconst DEFAULT_ANSWER_BYTES = 480 * 1024;\nconst DEFAULT_SNAPSHOT_BYTES = 256 * 1024;\n/** What an answer keeps for the page's observations whatever its `data` weighs. */\nconst OBSERVATION_FLOOR_BYTES = 16 * 1024;\n/** Rows `oui.read` returns of a list when the request names no limit. */\nconst DEFAULT_READ_ROWS = 50;\n\nexport function createSurfaceRuntime(\n options: SurfaceRuntimeOptions & { form: \"index\" },\n): SurfaceRuntime<\"index\">;\nexport function createSurfaceRuntime(\n options?: SurfaceRuntimeOptions & { form?: \"full\" },\n): SurfaceRuntime<\"full\">;\nexport function createSurfaceRuntime(\n options: SurfaceRuntimeOptions = {},\n): SurfaceRuntime<SurfaceForm> {\n const announce = options.announce ?? true;\n const quietMs = options.settle?.quietMs ?? DEFAULT_QUIET_MS;\n const settleTimeoutMs =\n options.settle?.timeoutMs ?? DEFAULT_SETTLE_TIMEOUT_MS;\n const dedupeWindow = options.dedupeWindow ?? DEFAULT_DEDUPE_WINDOW;\n const reanswerAfterMs = options.reanswerAfterMs ?? DEFAULT_REANSWER_AFTER_MS;\n const form: SurfaceForm = options.form ?? \"full\";\n const answerBytes = options.budgets?.answerBytes ?? DEFAULT_ANSWER_BYTES;\n const snapshotBytes =\n options.budgets?.snapshotBytes ?? DEFAULT_SNAPSHOT_BYTES;\n // A defined surface never changes, so its manifest and index are made once.\n const manifests = new WeakMap<object, OUISurface>();\n const indexes = new WeakMap<object, OUISurfaceIndex>();\n const manifestOf = (surface: DefinedSurface<unknown>): OUISurface => {\n let manifest = manifests.get(surface);\n if (!manifest)\n manifests.set(\n surface,\n (manifest = toJsonSafe(surface.toManifest()) as OUISurface),\n );\n return manifest;\n };\n const indexOf = (surface: DefinedSurface<unknown>): OUISurfaceIndex => {\n let index = indexes.get(surface);\n if (!index)\n indexes.set(surface, (index = surfaceIndex(manifestOf(surface))));\n return index;\n };\n\n let nextKey = 1;\n const entries: Entry[] = [];\n const observations = new Map<string, Map<string, unknown>>();\n const serializedObservations = new Map<string, string>();\n const holds = new Set<number>();\n let nextHold = 1;\n const results = new Map<string, Promise<OUIActionResult>>();\n const pollers = new Map<string, ReturnType<typeof setInterval>>();\n // How each running poll answers its request if it has to stop early.\n const abandon = new Map<\n string,\n (error: { code: string; message: string }) => void\n >();\n const listeners = new Set<() => void>();\n // Resolves once a request's first result has been handed to the transport.\n const acks = new Map<\n string,\n { promise: Promise<void>; resolve: () => void }\n >();\n function ackFor(requestId: string) {\n let ack = acks.get(requestId);\n if (!ack) {\n let resolve!: () => void;\n const promise = new Promise<void>((r) => (resolve = r));\n ack = { promise, resolve };\n acks.set(requestId, ack);\n }\n return ack;\n }\n function acknowledged(requestId: string): Promise<void> {\n return ackFor(requestId).promise;\n }\n // How each request's first answer is getting to the agent runtime: still\n // being worked out, sent (when), or acknowledged as received. A repeat of the\n // request is answered again only when the answer may have been lost (§7.3.7).\n const delivery = new Map<\n string,\n { state: \"running\" | \"sent\" | \"received\"; at: number }\n >();\n // The surfaces hash each request's first answer reported: an async action's\n // final answer repeats its surfaces only if they changed since then, since\n // the agent runtime waited for that first answer before waiting for this one.\n const answeredHash = new Map<string, string>();\n let lastChangeAt = Date.now();\n // Approvals the user gave in this tab, by approval id, until used or expired.\n const grants = new Map<string, OUIApprovalGrant>();\n\n /**\n * Why a request for an action that needs approval may not run, or null when\n * it may — in which case its grant is used up.\n */\n async function approvalRefusal(\n request: OUIActionRequest,\n ): Promise<string | null> {\n const approval = request.approval;\n if (!approval)\n return \"it needs the user's approval, and the request carries none\";\n let hash: string;\n try {\n hash = await argsHash(request.params ?? {});\n } catch (err) {\n return `its params cannot be checked against an approval: ${err instanceof Error ? err.message : String(err)}`;\n }\n // Checked and used up with no await in between, so one grant admits one request.\n const grant = grants.get(approval.approvalId);\n if (!grant) return \"this tab holds no unused approval for it\";\n if (Date.now() >= grant.expiresAt) {\n grants.delete(approval.approvalId);\n return \"its approval has expired\";\n }\n if (approval.argsHash !== grant.argsHash || hash !== grant.argsHash) {\n return \"its params are not the ones the user approved\";\n }\n grants.delete(approval.approvalId);\n return null;\n }\n\n let socket: SocketLike | null = null;\n let transport: OUITransport | null = null;\n let detachTransport: Array<() => void> = [];\n\n /**\n * `settles: false` for changes that are not the UI reacting to an action,\n * such as an async job's progress: those notify listeners but do not keep\n * an action's result waiting.\n */\n function changed(settles = true) {\n if (settles) lastChangeAt = Date.now();\n for (const l of [...listeners]) l();\n }\n\n function activeFor(surfaceId: string): Entry | undefined {\n for (let i = entries.length - 1; i >= 0; i--) {\n if (entries[i].surface.id === surfaceId) return entries[i];\n }\n return undefined;\n }\n\n /** Active entries, one per surface id, in the order each id was first mounted. */\n function activeEntries(): Entry[] {\n const seen = new Set<string>();\n const out: Entry[] = [];\n for (const e of entries) {\n if (seen.has(e.surface.id)) continue;\n seen.add(e.surface.id);\n out.push(activeFor(e.surface.id)!);\n }\n return out;\n }\n\n function announceSurface(entry: Entry) {\n if (!announce || !transport) return;\n transport.registerSurface(entry.surface.toManifest());\n const obs = observations.get(entry.surface.id);\n if (obs) {\n for (const [observationId, value] of obs) {\n transport.pushObservation({\n surfaceId: entry.surface.id,\n observationId,\n value,\n timestamp: Date.now(),\n });\n }\n }\n }\n\n function announceAll() {\n for (const e of activeEntries()) announceSurface(e);\n }\n\n function setObservation(\n surfaceId: string,\n observationId: string,\n value: unknown,\n settles = true,\n ) {\n const key = `${surfaceId}\\u0000${observationId}`;\n let serialized: string;\n try {\n serialized = JSON.stringify(value) ?? \"undefined\";\n } catch {\n serialized = String(value);\n }\n if (serializedObservations.get(key) === serialized) return;\n serializedObservations.set(key, serialized);\n\n let obs = observations.get(surfaceId);\n if (!obs) {\n obs = new Map();\n observations.set(surfaceId, obs);\n }\n obs.set(observationId, toJsonSafe(value));\n\n if (announce && transport) {\n transport.pushObservation({\n surfaceId,\n observationId,\n value,\n timestamp: Date.now(),\n });\n }\n changed(settles);\n }\n\n function forgetSurface(surfaceId: string) {\n observations.delete(surfaceId);\n for (const key of [...serializedObservations.keys()]) {\n if (key.startsWith(`${surfaceId}\\u0000`))\n serializedObservations.delete(key);\n }\n for (const [key, timer] of pollers) {\n if (key.startsWith(`${surfaceId}\\u0000`)) {\n clearInterval(timer);\n pollers.delete(key);\n // The request still gets its final answer: a poll that stops\n // without one leaves the agent waiting forever.\n abandon.get(key)?.({\n code: \"SURFACE_NOT_MOUNTED\",\n message:\n `Surface \"${surfaceId}\" left the page before its action finished, ` +\n \"so it is no longer being followed. Check what the page shows \" +\n \"before trying again.\",\n });\n abandon.delete(key);\n }\n }\n }\n\n // ─── Polling (async actions) ──────────────────────────────────────────────\n\n /**\n * Polls an async action to completion, publishing progress as an observation\n * and, when it ends, the request's final result (OUI spec §7.3: an async\n * action is acknowledged, then answered once more when it finishes).\n */\n function startPolling(\n requestId: string,\n surfaceId: string,\n actionId: string,\n polling: ActionPollingConfig<unknown>,\n dispatchResult: unknown,\n ) {\n const finish = async (\n success: boolean,\n data: unknown,\n error?: { code: string; message: string },\n ) => {\n // The acknowledgment goes first: a job can finish before the UI settles.\n await acknowledged(requestId);\n answer(\n frame(\n {\n requestId,\n success,\n ...(data !== undefined ? { data: toJsonSafe(data) } : {}),\n ...(error ? { error } : {}),\n interim: false,\n timestamp: Date.now(),\n },\n answeredHash.get(requestId),\n ),\n );\n acks.delete(requestId);\n answeredHash.delete(requestId);\n };\n\n // The observation id is the one surfaces have always published under.\n const observationId = `${surfaceId}:${actionId}:status`;\n const pollerKey = `${surfaceId}\\u0000${actionId}`;\n\n if (polling.subscribe) {\n setObservation(\n surfaceId,\n observationId,\n { status: \"dispatched\", dispatchResult, interim: true },\n false,\n );\n return;\n }\n if (!polling.resolve) {\n setObservation(\n surfaceId,\n observationId,\n { status: \"dispatched\", dispatchResult, interim: false },\n false,\n );\n return;\n }\n\n const existing = pollers.get(pollerKey);\n if (existing) {\n clearInterval(existing);\n pollers.delete(pollerKey);\n abandon.get(pollerKey)?.({\n code: \"SUPERSEDED\",\n message:\n `\"${actionId}\" was started again before this run finished, ` +\n \"so only the newer run is being followed.\",\n });\n abandon.delete(pollerKey);\n }\n\n setObservation(\n surfaceId,\n observationId,\n { status: \"polling\", dispatchResult, interim: true },\n false,\n );\n\n const maxAttempts = polling.maxAttempts ?? Infinity;\n const maxDuration = polling.maxDurationMs ?? Infinity;\n const startedAt = Date.now();\n let attempts = 0;\n\n const timer = setInterval(async () => {\n attempts++;\n if (attempts > maxAttempts || Date.now() - startedAt > maxDuration) {\n clearInterval(timer);\n pollers.delete(pollerKey);\n abandon.delete(pollerKey);\n setObservation(\n surfaceId,\n observationId,\n { status: \"timeout\", dispatchResult, interim: false },\n false,\n );\n void finish(false, undefined, {\n code: \"TIMEOUT\",\n message: `\"${actionId}\" did not finish within its polling limits.`,\n });\n return;\n }\n const entry = activeFor(surfaceId);\n if (!entry) {\n // forgetSurface normally gets here first; answer anyway.\n clearInterval(timer);\n pollers.delete(pollerKey);\n const gone = abandon.get(pollerKey);\n abandon.delete(pollerKey);\n gone?.({\n code: \"SURFACE_NOT_MOUNTED\",\n message:\n `Surface \"${surfaceId}\" left the page before \"${actionId}\" ` +\n \"finished, so it is no longer being followed. Check what the \" +\n \"page shows before trying again.\",\n });\n return;\n }\n // The surface may have remounted without this action (a control that is\n // disabled while its job runs, say). The job is still running, so keep\n // following it with the polling it started with.\n const action = entry.surface.actions.find((a) => a.id === actionId);\n const resolve = action?.polling?.resolve ?? polling.resolve;\n if (!resolve) return;\n try {\n const r = await resolve(dispatchResult, entry.getContext());\n setObservation(\n surfaceId,\n observationId,\n {\n ...(r.data as Record<string, unknown>),\n interim: !r.done,\n },\n false,\n );\n if (r.done) {\n clearInterval(timer);\n pollers.delete(pollerKey);\n abandon.delete(pollerKey);\n // Work that failed ends as a failure, with what it reported.\n void finish(!r.error, r.data, r.error);\n }\n } catch (err) {\n // A transient failure is reported, not fatal: keep polling.\n setObservation(\n surfaceId,\n observationId,\n { status: \"poll_error\", error: String(err), interim: true },\n false,\n );\n }\n }, polling.intervalMs);\n\n pollers.set(pollerKey, timer);\n abandon.set(pollerKey, (error) => void finish(false, undefined, error));\n }\n\n // ─── Settling ─────────────────────────────────────────────────────────────\n\n /**\n * Wait until the page has been quiet for `quietMs` since `since`, with no\n * hold open; false when `settleTimeoutMs` passes first.\n *\n * `since` is when the handler RETURNED, not when the request arrived. A\n * handler that awaits its own work — a save, a restore over the network —\n * and only then changes the page returns later than `quietMs` after it\n * started; measured from the start, the page had already \"been quiet\" for\n * the whole of that wait, so the answer was taken at once, before the UI had\n * rendered the change the handler had just made. The result said the\n * restore had worked and the observations beside it still showed the page\n * before it (dev, 2026-10-03).\n */\n async function waitUntilSettled(since: number): Promise<boolean> {\n const deadline = since + settleTimeoutMs;\n for (;;) {\n const now = Date.now();\n const quietFor = now - Math.max(since, lastChangeAt);\n if (holds.size === 0 && quietFor >= quietMs) return true;\n if (now >= deadline) return false;\n await sleep(Math.min(SETTLE_TICK_MS, deadline - now));\n }\n }\n\n // ─── Execution ────────────────────────────────────────────────────────────\n\n /**\n * The params with each attachment id the action takes resolved to the file\n * or its text (§7.3.11). The approval was checked against the ids: an\n * approval is of the exact request, and binds the file by its id.\n */\n async function withAttachments(\n action: { input?: JSONSchema } | undefined,\n params: Record<string, unknown>,\n ): Promise<\n | { resolved: Record<string, unknown> }\n | { error: { code: string; message: string } }\n > {\n // A file input anywhere a file is neither checked nor resolved: the action is not run.\n const misplaced = misplacedAttachmentInputs(action?.input);\n if (misplaced.length > 0) {\n return {\n error: {\n code: \"ATTACHMENT_INPUT_UNSUPPORTED\",\n message:\n `This action declares an attached file at ${misplaced.join(\", \")}, where none can be taken: ` +\n \"a file is a property of the input, or an item of a list property.\",\n },\n };\n }\n const wanted = attachmentIdsIn(action?.input, params);\n if (wanted.length === 0) return { resolved: params };\n const resolver = options.attachments;\n if (!resolver) {\n return {\n error: {\n code: \"ATTACHMENTS_UNSUPPORTED\",\n message:\n \"This page cannot take attached files: it was not given a way to open them.\",\n },\n };\n }\n const resolved: Record<string, unknown> = { ...params };\n // One resolution per file and form, however often the params name it.\n const once = new Map<string, Promise<unknown>>();\n for (const { path, input } of attachmentInputs(action?.input)) {\n const value = params[path[0]];\n const one = (id: unknown): Promise<unknown> => {\n if (!isAttachmentId(id))\n return Promise.reject(\n new Error(`\"${String(id)}\" is not an attachment's id.`),\n );\n const key = `${input.as}:${id}`;\n if (!once.has(key)) once.set(key, resolveOne(resolver, id, input));\n return once.get(key)!;\n };\n try {\n if (path.length === 2) {\n if (Array.isArray(value)) {\n if (value.length > ATTACHMENT_LIST_MAX)\n throw new Error(\n `it names ${value.length} files; a list takes at most ${ATTACHMENT_LIST_MAX}.`,\n );\n resolved[path[0]] = await mapBounded(\n value,\n ATTACHMENT_RESOLVE_CONCURRENCY,\n one,\n );\n }\n } else if (value !== undefined) {\n resolved[path[0]] = await one(value);\n }\n } catch (err) {\n return {\n error: {\n code: \"ATTACHMENT_UNAVAILABLE\",\n message: `${path[0]}: ${err instanceof Error ? err.message : String(err)}`,\n },\n };\n }\n }\n return { resolved };\n }\n\n async function run(request: OUIActionRequest): Promise<OUIActionResult> {\n const startedAt = Date.now();\n if (request.surfaceId === OUI_RUNTIME_SURFACE)\n return builtin(request, startedAt);\n const entry = activeFor(request.surfaceId);\n\n let result: ActionHandlerResult;\n let interim = false;\n if (!entry) {\n const mounted = activeEntries().map((e) => e.surface.id);\n result = {\n success: false,\n error: {\n code: \"SURFACE_NOT_MOUNTED\",\n message:\n `Surface \"${request.surfaceId}\" is not on screen. ` +\n `Mounted surfaces: ${mounted.length ? mounted.join(\", \") : \"none\"}.`,\n },\n };\n } else {\n const declared = entry.surface.actions.find(\n (a) => a.id === request.actionId,\n );\n const refusal =\n declared && requiresApproval(declared.effect, declared.confirm)\n ? await approvalRefusal(request)\n : null;\n // executeAction turns a thrown handler into ACTION_EXECUTION_ERROR.\n result = refusal\n ? {\n success: false,\n error: {\n code: \"APPROVAL_REQUIRED\",\n message: `\"${request.actionId}\" was not run: ${refusal}.`,\n },\n }\n : await withAttachments(declared, request.params ?? {}).then(\n (params) =>\n \"error\" in params\n ? { success: false, error: params.error }\n : entry.surface.executeAction(\n request.actionId,\n params.resolved,\n entry.getContext(),\n ),\n );\n if (result.success) {\n const action = entry.surface.actions.find(\n (a) => a.id === request.actionId,\n );\n if (action?.polling) {\n interim = true;\n startPolling(\n request.requestId,\n entry.surface.id,\n action.id,\n action.polling,\n result.data ?? result.dispatchMeta,\n );\n }\n }\n }\n\n // From now: the handler has returned, and what it changed is still to render.\n const settled = await waitUntilSettled(Date.now());\n const answered = frame(\n {\n requestId: request.requestId,\n success: result.success,\n ...(result.data !== undefined ? { data: toJsonSafe(result.data) } : {}),\n ...(result.error\n ? { error: toJsonSafe(result.error) as OUIActionResult[\"error\"] }\n : {}),\n ...(interim ? { interim: true } : {}),\n durationMs: Date.now() - startedAt,\n timestamp: Date.now(),\n settled,\n },\n request.knownSurfaces,\n );\n if (interim) answeredHash.set(request.requestId, answered.surfacesHash!);\n return answered;\n }\n\n /**\n * An outcome as the answer that carries it: with what the page offers, only\n * when the agent runtime does not already hold it (§7.3.4), and the page's\n * observations, all within the answer's byte budget (§7.3.9). The action's\n * own `data` is kept whole unless it alone outweighs the frame; the\n * observations take what is left, and say where they were cut.\n */\n function frame(\n outcome: OUIActionResult,\n knownSurfaces: string | undefined,\n ): OUIActionResult {\n const page = capture();\n const out: OUIActionResult = {\n ...outcome,\n ...(page.surfacesHash !== knownSurfaces\n ? form === \"index\"\n ? { index: page.index }\n : { surfaces: page.surfaces }\n : {}),\n surfacesHash: page.surfacesHash,\n };\n const fit: OUIFit = {};\n // Definitions that alone outweigh the frame are refused and then left out\n // (§7.3.6): the rest is fitted as the answer that will then be sent.\n const carried =\n jsonBytes(out.index ?? out.surfaces) >= answerBytes\n ? { ...out, index: undefined, surfaces: undefined }\n : out;\n const dataLimit =\n answerBytes -\n jsonBytes({ ...carried, data: undefined }) -\n OBSERVATION_FLOOR_BYTES;\n const dataBytes = jsonBytes(out.data);\n if (dataBytes > Math.max(0, dataLimit)) {\n delete out.data;\n fit.data = { bytes: dataBytes, limit: Math.max(0, dataLimit) };\n }\n const fitted = fitObservations(\n page.observations,\n Math.max(\n 0,\n answerBytes -\n jsonBytes(\n out.data === undefined ? { ...carried, data: undefined } : carried,\n ),\n ),\n );\n out.observations = fitted.observations;\n if (fitted.cuts.length) fit.observations = fitted.cuts;\n if (fit.data || fit.observations) out.fit = fit;\n return out;\n }\n\n // ─── The runtime's own actions (§7.3.10) ─────────────────────────────────────\n\n /**\n * `oui.describe` and `oui.read`: answered here, at once. They read what the\n * client holds and change nothing, so there is nothing to settle, and their\n * answer carries their data and the surfaces hash only.\n */\n function builtin(\n request: OUIActionRequest,\n startedAt: number,\n ): OUIActionResult {\n const done = (\n body: Pick<OUIActionResult, \"success\" | \"data\" | \"error\">,\n ): OUIActionResult => ({\n requestId: request.requestId,\n ...body,\n durationMs: Date.now() - startedAt,\n timestamp: Date.now(),\n surfacesHash: capture().surfacesHash,\n settled: true,\n });\n const refuse = (code: string, message: string) =>\n done({ success: false, error: { code, message } });\n const params = request.params ?? {};\n\n if (request.actionId === OUI_DESCRIBE_ACTION) {\n const asked = params.actions;\n if (\n !Array.isArray(asked) ||\n asked.length === 0 ||\n !asked.every(\n (a) =>\n a &&\n typeof a === \"object\" &&\n typeof (a as Record<string, unknown>).surface === \"string\" &&\n typeof (a as Record<string, unknown>).action === \"string\",\n )\n ) {\n return refuse(\n \"INVALID_PARAMS\",\n '\"describe\" takes actions: [{ surface, action }], at least one',\n );\n }\n const definitions: Array<{ surface: string; action: OUIAction }> = [];\n const missing: Array<{ surface: string; action: string }> = [];\n const deferred: Array<{ surface: string; action: string }> = [];\n let bytes = 0;\n for (const { surface, action } of asked as Array<{\n surface: string;\n action: string;\n }>) {\n const entry = activeFor(surface);\n const definition =\n entry &&\n manifestOf(entry.surface).actions.find((a) => a.id === action);\n if (!definition) {\n missing.push({ surface, action });\n continue;\n }\n const size = jsonBytes(definition);\n // One definition always goes, however large: the rest wait for the next request.\n if (\n definitions.length > 0 &&\n bytes + size > answerBytes - OBSERVATION_FLOOR_BYTES\n ) {\n deferred.push({ surface, action });\n continue;\n }\n bytes += size;\n definitions.push({ surface, action: definition });\n }\n return done({\n success: true,\n data: {\n definitions,\n ...(missing.length ? { missing } : {}),\n ...(deferred.length ? { deferred } : {}),\n },\n });\n }\n\n if (request.actionId === OUI_READ_ACTION) {\n const { surface, observation } = params as Record<string, unknown>;\n const path = params.path === undefined ? \"\" : params.path;\n const offset = params.offset === undefined ? 0 : params.offset;\n const limit =\n params.limit === undefined ? DEFAULT_READ_ROWS : params.limit;\n if (\n typeof surface !== \"string\" ||\n typeof observation !== \"string\" ||\n typeof path !== \"string\"\n ) {\n return refuse(\n \"INVALID_PARAMS\",\n '\"read\" takes surface, observation and, to read part of the value, path',\n );\n }\n if (\n !Number.isInteger(offset) ||\n (offset as number) < 0 ||\n !Number.isInteger(limit) ||\n (limit as number) < 1\n ) {\n return refuse(\n \"INVALID_PARAMS\",\n '\"read\" takes offset (0 or more) and limit (1 or more) as whole numbers',\n );\n }\n const values = observations.get(surface);\n if (!values || !values.has(observation)) {\n const known = values ? [...values.keys()] : [];\n return refuse(\n \"NOT_FOUND\",\n values\n ? `Surface \"${surface}\" reports no observation \"${observation}\". It reports: ${known.join(\", \") || \"none\"}.`\n : `Surface \"${surface}\" is not on screen, or reports nothing.`,\n );\n }\n let value: unknown;\n try {\n value = atPointer(values.get(observation), path);\n } catch (err) {\n return refuse(\n \"INVALID_PARAMS\",\n err instanceof Error ? err.message : String(err),\n );\n }\n if (value === undefined) {\n return refuse(\n \"NOT_FOUND\",\n `Nothing is at \"${path}\" in ${surface}.${observation}.`,\n );\n }\n const room = answerBytes - OBSERVATION_FLOOR_BYTES;\n if (Array.isArray(value)) {\n const total = value.length;\n let rows = value.slice(\n offset as number,\n (offset as number) + (limit as number),\n );\n // A page of rows that outweighs the frame is halved until it fits; one row always goes.\n while (rows.length > 1 && jsonBytes(rows) > room)\n rows = rows.slice(0, Math.ceil(rows.length / 2));\n const next = (offset as number) + rows.length;\n return done({\n success: true,\n data: {\n rows,\n total,\n offset,\n ...(next < total ? { more: true, next } : {}),\n },\n });\n }\n const fitted = fitObservations(\n { [surface]: { [observation]: value } },\n room,\n );\n // Cuts are reported relative to the observation, as every other cut is.\n const cuts = fitted.cuts.map((c) => ({ ...c, path: `${path}${c.path}` }));\n return done({\n success: true,\n data: {\n value: fitted.observations[surface][observation],\n ...(cuts.length ? { fit: { observations: cuts } } : {}),\n },\n });\n }\n\n return refuse(\n \"ACTION_NOT_FOUND\",\n `The runtime answers \"${OUI_DESCRIBE_ACTION}\" and \"${OUI_READ_ACTION}\"; it has no \"${request.actionId}\".`,\n );\n }\n\n // ─── Answering ────────────────────────────────────────────────────────────\n\n /**\n * Send an answer, and if the receiving side refuses it, send it again\n * trimmed, saying why (§7.3.6): first without what the page offers, then\n * without the page's observations too, then without the action's data. What\n * the page shows is given up after what it offers: an agent that still sees\n * the page can carry on, and one that does not must stop. An answer that is\n * refused and not sent again leaves the agent waiting until its deadline,\n * then reporting an action that ran as one that did not answer.\n */\n function answer(result: OUIActionResult, onReceived?: () => void) {\n const offered = form === \"index\" ? \"index\" : \"surfaces\";\n const steps: Array<OUIResultDelivery[\"omitted\"]> = [\n [offered],\n [offered, \"observations\"],\n [offered, \"observations\", \"data\"],\n ];\n const send = (frame: OUIActionResult, step: number) => {\n transport?.sendResult(frame, (ack) => {\n if (ack.ok) {\n onReceived?.();\n return;\n }\n const omitted = steps[step];\n if (!omitted) {\n console.warn(\n `[OUI] The answer to ${result.requestId} was refused even trimmed: ${ack.reason}`,\n );\n return;\n }\n console.warn(\n `[OUI] The answer to ${result.requestId} was refused (${ack.reason}); sending it without ${omitted.join(\", \")}`,\n );\n send(trimmed(result, ack.reason, omitted), step + 1);\n });\n };\n send(result, 0);\n }\n\n function execute(request: OUIActionRequest): Promise<OUIActionResult> {\n const seen = results.get(request.requestId);\n if (seen) return seen;\n\n const pending = run(request);\n results.set(request.requestId, pending);\n while (results.size > dedupeWindow) {\n const oldest = results.keys().next().value as string;\n results.delete(oldest);\n delivery.delete(oldest);\n }\n return pending;\n }\n\n // ─── Snapshot ─────────────────────────────────────────────────────────────\n\n /** What is mounted, in the runtime's form, with every observation whole. */\n function capture(): {\n surfaces?: OUISurface[];\n index?: OUISurfaceIndex[];\n observations: OUIObservationSnapshot;\n surfacesHash: string;\n } {\n const active = activeEntries();\n const obs: OUIObservationSnapshot = {};\n for (const e of active) {\n const values = observations.get(e.surface.id);\n if (values && values.size > 0)\n obs[e.surface.id] = Object.fromEntries(values);\n }\n if (form === \"index\") {\n const index = active.map((e) => indexOf(e.surface));\n return { index, observations: obs, surfacesHash: surfacesHash(index) };\n }\n const surfaces = active.map((e) => manifestOf(e.surface));\n return {\n surfaces,\n observations: obs,\n surfacesHash: surfacesHash(surfaces),\n };\n }\n\n function snapshot(): OUISurfaceSnapshot | OUIIndexSnapshot {\n const page = capture();\n const offered =\n form === \"index\" ? { index: page.index! } : { surfaces: page.surfaces! };\n // Definitions that alone outweigh the snapshot cannot be shortened here:\n // the observations are then fitted to the whole budget, not to none of it.\n const offeredBytes = jsonBytes(offered);\n const fitted = fitObservations(\n page.observations,\n offeredBytes >= snapshotBytes\n ? snapshotBytes\n : snapshotBytes - offeredBytes,\n );\n return {\n ...offered,\n observations: fitted.observations,\n surfacesHash: page.surfacesHash,\n ...(fitted.cuts.length ? { fit: { observations: fitted.cuts } } : {}),\n };\n }\n\n // ─── Transport ────────────────────────────────────────────────────────────\n\n function attach(next: SocketLike | null) {\n if (next === socket) return;\n for (const off of detachTransport) off();\n detachTransport = [];\n transport?.dispose();\n transport = null;\n socket = next;\n if (!next) return;\n\n const t = createWebSocketTransport(next, options.transport);\n transport = t;\n\n detachTransport.push(\n t.onAction((request, receipt) => {\n if (options.accept && !options.accept(request)) {\n console.warn(\n `[OUI] Refused a request the client does not accept: ${request.surfaceId}.${request.actionId} (${request.requestId})`,\n );\n receipt?.({\n ok: false,\n reason: \"this client does not accept requests now\",\n });\n return;\n }\n // Received: the sender need not send it again (§7.3.7).\n receipt?.({ ok: true });\n const id = request.requestId;\n const prior = delivery.get(id);\n // A repeat while the answer is being worked out, or is on its way, or\n // has arrived, gets no second copy: copies of a large answer queue on\n // the one socket ahead of the next request's answer.\n if (prior && prior.state !== \"sent\") return;\n if (prior && Date.now() - prior.at < reanswerAfterMs) return;\n if (!prior) delivery.set(id, { state: \"running\", at: Date.now() });\n void execute(request).then((result) => {\n // Answer on whichever transport is live when the result is ready: a\n // reconnect in between keeps the same socket, so this still reaches\n // the runtime that asked.\n if (results.has(id))\n delivery.set(id, { state: \"sent\", at: Date.now() });\n answer(result, () => {\n if (results.has(id))\n delivery.set(id, { state: \"received\", at: Date.now() });\n });\n const ack = ackFor(id);\n ack.resolve();\n // Keep the gate only while a final result may still follow.\n if (!result.interim) acks.delete(id);\n });\n }),\n );\n\n if (announce) {\n // A server-side registry forgets a socket's surfaces when it drops, so\n // every (re)connection announces them again.\n detachTransport.push(\n t.onConnectionChange((connected) => {\n if (connected) announceAll();\n }),\n );\n if (t.connected) announceAll();\n }\n }\n\n if (options.socket) attach(options.socket);\n\n // ─── Mounting ─────────────────────────────────────────────────────────────\n\n function mount<TContext>(\n surface: DefinedSurface<TContext>,\n getContext: () => TContext,\n ): MountedSurface {\n const entry: Entry = {\n key: nextKey++,\n surface: surface as unknown as DefinedSurface<unknown>,\n getContext: getContext as () => unknown,\n };\n entries.push(entry);\n announceSurface(entry);\n changed();\n\n let mounted = true;\n return {\n surfaceId: surface.id,\n pushObservation(observationId, value) {\n // Only the mount serving the surface speaks for it.\n if (!mounted || activeFor(surface.id) !== entry) return;\n setObservation(surface.id, observationId, value);\n },\n unmount() {\n if (!mounted) return;\n mounted = false;\n const i = entries.indexOf(entry);\n if (i >= 0) entries.splice(i, 1);\n const replacement = activeFor(surface.id);\n if (replacement) {\n announceSurface(replacement);\n } else {\n forgetSurface(surface.id);\n if (announce && transport) transport.deregisterSurface(surface.id);\n }\n changed();\n },\n };\n }\n\n return {\n mount,\n attach,\n snapshot: snapshot as SurfaceRuntime<SurfaceForm>[\"snapshot\"],\n execute,\n hold() {\n const id = nextHold++;\n holds.add(id);\n changed();\n let released = false;\n return () => {\n if (released) return;\n released = true;\n holds.delete(id);\n changed();\n };\n },\n grantApproval(grant) {\n if (\n !grant ||\n typeof grant.approvalId !== \"string\" ||\n !grant.approvalId ||\n typeof grant.argsHash !== \"string\" ||\n !ARGS_HASH_PATTERN.test(grant.argsHash) ||\n !Number.isFinite(grant.expiresAt)\n ) {\n throw new Error(\n \"[OUI] grantApproval needs an approvalId, an args hash and an expiry\",\n );\n }\n const now = Date.now();\n for (const [id, g] of grants) if (now >= g.expiresAt) grants.delete(id);\n grants.set(grant.approvalId, { ...grant });\n },\n subscribe(listener) {\n listeners.add(listener);\n return () => {\n listeners.delete(listener);\n };\n },\n dispose() {\n for (const timer of pollers.values()) clearInterval(timer);\n pollers.clear();\n abandon.clear();\n attach(null);\n entries.length = 0;\n observations.clear();\n serializedObservations.clear();\n holds.clear();\n listeners.clear();\n acks.clear();\n answeredHash.clear();\n delivery.clear();\n grants.clear();\n },\n };\n}\n\n// ─── Helpers ─────────────────────────────────────────────────────────────────\n\n/** `result` without the fields `omitted` names, saying so and why (§7.3.6). */\nfunction trimmed(\n result: OUIActionResult,\n reason: string,\n omitted: OUIResultDelivery[\"omitted\"],\n): OUIActionResult {\n const out: OUIActionResult = { ...result };\n for (const field of omitted) delete out[field];\n out.delivery = { trimmed: true, reason, omitted: [...omitted] };\n return out;\n}\n\nfunction sleep(ms: number): Promise<void> {\n return new Promise((resolve) => setTimeout(resolve, ms));\n}\n\n/**\n * Results and observations cross a wire as JSON. A handler returning something\n * that is not (a DOM node, a class instance with cycles) must not take the\n * result down with it.\n */\nfunction toJsonSafe(value: unknown): unknown {\n if (value === undefined) return undefined;\n try {\n return JSON.parse(JSON.stringify(value));\n } catch {\n return String(value);\n }\n}\n\n/** What an attachment input is given, once its type is checked against what it accepts (§7.3.11). */\nasync function resolveOne(\n resolver: AttachmentResolver,\n id: string,\n input: OUIAttachmentInput,\n): Promise<File | string> {\n const got = await resolver.resolve(id, input.as);\n const refuse = (name: string, type: string) =>\n new Error(\n `\"${name}\" is ${type || \"of no type\"}; this takes ${input.mediaTypes!.join(\", \")}.`,\n );\n if (typeof got === \"string\") {\n if (input.as === \"file\")\n throw new Error(\n \"The page's file area gave text where a file was expected.\",\n );\n // Text with nothing to say what it is: only an input that takes any type takes it.\n if (input.mediaTypes?.length)\n throw new Error(\n \"The page's file area gave the file's text without its type, so it cannot be checked against what this takes.\",\n );\n return got;\n }\n if (typeof Blob !== \"undefined\" && got instanceof Blob) {\n const name = (got as File).name ?? id;\n if (!acceptsMediaType(input, got.type)) throw refuse(name, got.type);\n return input.as === \"text\" ? await got.text() : (got as File);\n }\n if (\n got &&\n typeof got === \"object\" &&\n typeof (got as AttachmentText).text === \"string\"\n ) {\n const text = got as AttachmentText;\n if (input.as === \"file\")\n throw new Error(\n \"The page's file area gave text where a file was expected.\",\n );\n if (!acceptsMediaType(input, text.mediaType ?? \"\"))\n throw refuse(text.name ?? id, text.mediaType);\n return text.text;\n }\n throw new Error(\"The page's file area gave nothing that can be used.\");\n}\n\n/** `fn` over `items`, at most `limit` at a time, in order. */\nasync function mapBounded<T, R>(\n items: readonly T[],\n limit: number,\n fn: (item: T) => Promise<R>,\n): Promise<R[]> {\n const out: R[] = new Array(items.length);\n let next = 0;\n const worker = async () => {\n while (next < items.length) {\n const index = next++;\n out[index] = await fn(items[index]);\n }\n };\n await Promise.all(\n Array.from({ length: Math.min(limit, items.length) }, worker),\n );\n return out;\n}\n","import type { OUIActionRequest } from \"../spec/types.js\";\n\n/**\n * An `accept` rule for a client whose agent works in turns, one at a time\n * (§7.3.1): a request runs only for the turn the client is running now.\n *\n * - A request that names its turn (`turnId`) is accepted when that is the\n * client's current turn. A request sent late by a turn the person stopped,\n * or that a newer message superseded, names a turn that is no longer\n * current, and is refused: it does not run under the newer instruction.\n * - A request that names no turn comes from an agent runtime that does not\n * send one (an older worker, during a rollout). It is accepted while a turn\n * is in progress, which is the rule a client had before requests named\n * their turn. It is never refused only for naming none.\n *\n * `currentTurn` returns the id of the turn the client is running, or null\n * when it runs none.\n */\nexport function acceptCurrentTurn(\n currentTurn: () => string | null,\n): (request: OUIActionRequest) => boolean {\n return (request) => {\n const current = currentTurn();\n if (current === null) return false;\n if (request.turnId === undefined) return true;\n return request.turnId === current;\n };\n}\n"]}
|