@zackbart/connecta 0.29.0 → 0.31.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.
Files changed (116) hide show
  1. package/CHANGELOG.md +99 -0
  2. package/README.md +126 -134
  3. package/bin/connecta.mjs +13 -2
  4. package/bin/version.mjs +1 -1
  5. package/dist/argument-redaction.js +230 -0
  6. package/dist/auth-elicitation.js +14 -9
  7. package/dist/authorization-handoff.js +111 -0
  8. package/dist/call-recovery.js +25 -0
  9. package/dist/catalog-cache.js +2 -2
  10. package/dist/catalog-service.js +103 -63
  11. package/dist/config-schema.d.ts +14 -7
  12. package/dist/config-schema.js +29 -10
  13. package/dist/config.d.ts +2 -0
  14. package/dist/config.js +12 -7
  15. package/dist/connectors/guarded-fetch.d.ts +9 -1
  16. package/dist/connectors/guarded-fetch.js +17 -5
  17. package/dist/connectors/negotiation-cache.js +1 -1
  18. package/dist/downstream-input-context.js +9 -0
  19. package/dist/downstream-input.js +13 -11
  20. package/dist/errors.d.ts +38 -12
  21. package/dist/errors.js +19 -9
  22. package/dist/execute.js +375 -43
  23. package/dist/executor-result.js +11 -9
  24. package/dist/executors/quickjs-child.js +12 -5
  25. package/dist/executors/quickjs-protocol.js +5 -6
  26. package/dist/executors/quickjs-runtime.js +6 -1
  27. package/dist/executors/quickjs.js +20 -4
  28. package/dist/guest-runtime.js +52 -2
  29. package/dist/guest-types.d.ts +47 -5
  30. package/dist/index.d.ts +1 -1
  31. package/dist/invocation.js +72 -14
  32. package/dist/meta-output.js +0 -15
  33. package/dist/meta-tools.js +166 -95
  34. package/dist/oauth-handoff.js +88 -11
  35. package/dist/operator-ui/generated.js +2 -2
  36. package/dist/operator-ui/view.d.ts +9 -0
  37. package/dist/operator-ui/view.js +11 -0
  38. package/dist/program-result.js +5 -0
  39. package/dist/program-writes.js +7 -48
  40. package/dist/provider.d.ts +8 -6
  41. package/dist/provider.js +3 -4
  42. package/dist/providers/_shared/google/workspace.d.ts +1 -1
  43. package/dist/providers/_shared/request-token.js +83 -0
  44. package/dist/providers/_shared/rest/dispatch.js +41 -0
  45. package/dist/providers/_shared/rest/operation-index.d.ts +133 -0
  46. package/dist/providers/_shared/rest/operation-index.js +527 -0
  47. package/dist/providers/_shared/rest/tools.d.ts +141 -0
  48. package/dist/providers/_shared/rest/tools.js +569 -0
  49. package/dist/providers/_shared/rest/value-safety.d.ts +151 -0
  50. package/dist/providers/_shared/rest/value-safety.js +580 -0
  51. package/dist/providers/cloudflare/graphql.js +385 -0
  52. package/dist/providers/cloudflare/index.d.ts +47 -51
  53. package/dist/providers/cloudflare/index.js +188 -1997
  54. package/dist/providers/cloudflare/openapi.generated.js +3347 -0
  55. package/dist/providers/cloudflare/rest.d.ts +37 -0
  56. package/dist/providers/cloudflare/rest.js +1056 -0
  57. package/dist/providers/cloudflare/skill.generated.js +7 -4
  58. package/dist/providers/cloudflare/value-safety.js +1247 -0
  59. package/dist/providers/infisical/index.d.ts +7 -0
  60. package/dist/providers/infisical/index.js +713 -0
  61. package/dist/providers/infisical/skill.generated.js +8 -0
  62. package/dist/providers/notion/index.d.ts +35 -31
  63. package/dist/providers/notion/index.js +60 -1499
  64. package/dist/providers/notion/openapi.generated.js +75 -0
  65. package/dist/providers/notion/rest.d.ts +24 -0
  66. package/dist/providers/notion/rest.js +1067 -0
  67. package/dist/providers/notion/skill.generated.js +5 -4
  68. package/dist/providers/notion/value-safety.js +31 -0
  69. package/dist/providers/stripe/index.d.ts +26 -20
  70. package/dist/providers/stripe/index.js +103 -130
  71. package/dist/providers/stripe/openapi.generated.js +649 -0
  72. package/dist/providers/stripe/rest.d.ts +14 -0
  73. package/dist/providers/stripe/rest.js +395 -0
  74. package/dist/providers/stripe/skill.generated.js +7 -5
  75. package/dist/providers/stripe/value-safety.js +705 -0
  76. package/dist/providers/vercel/index.d.ts +31 -22
  77. package/dist/providers/vercel/index.js +96 -853
  78. package/dist/providers/vercel/openapi.generated.js +456 -0
  79. package/dist/providers/vercel/rest.d.ts +20 -0
  80. package/dist/providers/vercel/rest.js +1002 -0
  81. package/dist/providers/vercel/skill.generated.js +4 -5
  82. package/dist/providers/vercel/value-safety.js +328 -0
  83. package/dist/registry.d.ts +8 -6
  84. package/dist/registry.js +134 -61
  85. package/dist/resource-read.js +4 -1
  86. package/dist/routes/mcp.js +11 -2
  87. package/dist/sent-secrets.d.ts +54 -13
  88. package/dist/sent-secrets.js +770 -231
  89. package/dist/skills.js +26 -16
  90. package/dist/sqlite.js +21 -6
  91. package/dist/storage/keys.js +20 -5
  92. package/dist/storage/memory.js +9 -4
  93. package/dist/storage/sql.js +18 -9
  94. package/dist/types.d.ts +17 -3
  95. package/dist/usage-guide.js +49 -40
  96. package/dist/version.d.ts +1 -1
  97. package/dist/version.js +1 -1
  98. package/dist/worker.js +2 -1
  99. package/dist/write-outcome.js +47 -0
  100. package/documentation/README.md +64 -0
  101. package/documentation/architecture.md +241 -97
  102. package/documentation/auth.md +138 -5
  103. package/documentation/code-mode.md +224 -107
  104. package/documentation/deploying.md +146 -0
  105. package/documentation/integrating.md +170 -0
  106. package/documentation/meta-tools.md +142 -30
  107. package/documentation/operating.md +135 -0
  108. package/documentation/operator-tests.md +4 -0
  109. package/documentation/operator-ui.md +132 -0
  110. package/documentation/provider-auth-migration.md +307 -0
  111. package/documentation/provider-migration-0.29.md +22 -5
  112. package/examples/worker/README.md +9 -2
  113. package/package.json +9 -2
  114. package/templates/node/README.md +9 -2
  115. package/templates/node/package.json +1 -1
  116. package/dist/providers/vercel/mcp-ownership.js +0 -212
@@ -11,6 +11,26 @@ a third executor is implementable from this document alone.
11
11
  [`meta-tools.md`](./meta-tools.md) owns the top-level tool contract, and clause
12
12
  identifiers (`A1`, `E3`, …) are stable and cited by [Verification](#verification).
13
13
 
14
+ ## Task routes
15
+
16
+ For normal endpoint work, start with [Operating an endpoint](./operating.md).
17
+ Use this reference for exact guest behavior or executor implementation.
18
+ [Agent index](./README.md) routes other work.
19
+
20
+ | Task | Sections |
21
+ | -------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------ |
22
+ | Wire a shipped or custom executor | [Deploy-time capability](#deploy-time-capability), [executor requirements](#what-an-executor-must-implement), [exceptions](#executor-exceptions) |
23
+ | Write a portable program | [Program form](#the-program), [addresses](#addressing), [guest functions](#the-surface) |
24
+ | Discover and call tools | [Search](#connectasearch), [describe](#connectadescribe), [call](#connectacall), [parallel calls](#parallel-calls) |
25
+ | Page results, load skills or read resources | [Result and skill](#connectaresult-and-connectaskill), [read](#connectaread), [projection](#results-and-projection) |
26
+ | Emit incremental output | [emit](#connectaemit), [emitted output](#emitted-output) |
27
+ | Handle errors, writes, or cancellation | [Errors](#errors), [retries](#retry-semantics), [limits](#cancellation-and-limits), [writes](#writes), [activity](#activity) |
28
+ | Change the contract or check executor parity | [Verification](#verification), then the tests indexed by clause |
29
+
30
+ Clause IDs remain stable, including retired IDs. Check current behavior against
31
+ source and the verification table; do not reuse a retired clause to introduce
32
+ new behavior.
33
+
14
34
  ## Deploy-time capability
15
35
 
16
36
  The `executor` passed to `createConnecta()` is required. `tools/list` is exactly
@@ -333,11 +353,27 @@ const { data: run, format } = await connecta.call("ci.get_run", { runId: 42 });
333
353
  **S5.** Takes a canonical address, optional arguments, and optional
334
354
  `{ timeoutMs }`; the object form is `{ address, args?, timeoutMs? }`. A malformed
335
355
  signature fails with `invalid_args` and both exact signatures, before discovery.
336
- Returns `{ data, format: "json" | "text" }`. MCP `toolResult` or
356
+ Normally returns `{ data, format: "json" | "text" }`. Oversized values may return
357
+ a `format: "paged"` handle for `connecta.result`, as described in `L6` below.
358
+ MCP `toolResult` or
337
359
  `structuredContent` is JSON; all-text content is JSON when it parses, otherwise
338
360
  text. API string values are text, other API values are JSON. Check `format`
339
361
  before treating `data` as an object. A downstream `isError` throws.
340
362
 
363
+ An inline MCP result containing image, audio, resource, or resource_link blocks
364
+ also exposes `content?: GuestNativeBlock[]`, even when `data` comes from
365
+ `structuredContent` or `toolResult`. `data` keeps its existing shape.
366
+ `connecta.emit(result)` forwards all native blocks; iterating `result.content`
367
+ and calling `connecta.emit(block)` forwards selected blocks. Both forward the
368
+ host-retained originals, so guest edits do not change native output. Results
369
+ over the 1 MiB inline cap return paging handles without native content; page
370
+ and reduce them as described in `L6`. If only the native presentation is too
371
+ large or its transfer fails, `data` stays intact and `contentResult` carries
372
+ its paging handle or an unavailable-paging notice for presentation that exceeds
373
+ bounded traversal limits or is cyclic. When a result ID exists,
374
+ `connecta.result(result.contentResult)` pages the original MCP envelope;
375
+ `emit(result)` refuses with `result_too_large`.
376
+
341
377
  **S6.** Every call goes through the same catalog, fail-closed read-only
342
378
  predicate, admission, credential containment, timeout classification, health
343
379
  accounting, and activity recording as an ordinary meta-tool call. The predicate
@@ -348,11 +384,14 @@ it can reach.
348
384
 
349
385
  ### connecta.result and connecta.skill
350
386
 
351
- `await connecta.result(id, { offset?, maxBytes? })` reads a stashed direct-call
352
- result bound to the admitted subject, principal, endpoint/pool, request origin,
387
+ `await connecta.result(handleOrId, { page?, offset?, maxBytes? })` reads a stashed direct-call
388
+ or program-call result bound to the admitted subject, principal, endpoint/pool, request origin,
353
389
  connector, and tool. It returns
354
390
  `{ resultId, offset, bytes, totalBytes, hasMore, nextOffset?, format: "text", text }`.
355
- Offsets and sizes are UTF-8 bytes; the page cap is the original call's inline cap.
391
+ Offsets and sizes are UTF-8 bytes. Pages obey the original call's inline cap
392
+ and a 32 KiB bridge ceiling. `page` is zero-based and mutually exclusive with
393
+ `offset`; keep `maxBytes` fixed while incrementing pages. Nominal page windows
394
+ are at least four bytes wide and align both edges to UTF-8 boundaries.
356
395
  Follow `nextOffset`, reassemble inside the program, and return a reduced value.
357
396
  Before returning a page, the host rechecks current authentication, connector/tool
358
397
  grants, pool membership, and endpoint trust against both the original and current
@@ -465,7 +504,9 @@ or upward proxy to programs. Native upward skill resources are separate
465
504
  ### connecta.emit
466
505
 
467
506
  ```js
468
- await connecta.emit({ type: "image", data: shot.data, mimeType: "image/png" });
507
+ const badge = await connecta.call("assets.get_badge_image", {});
508
+ connecta.emit(badge);
509
+ // Or: for (const block of badge.content ?? []) connecta.emit(block);
469
510
  ```
470
511
 
471
512
  The rich-output channel, delivered after the JSON envelope on success. Its
@@ -477,17 +518,17 @@ clauses are [Emitted output](#emitted-output) (`M1`–`M10`).
477
518
  caught or uncaught. Host-call budget exhaustion ends the host run and blocks host
478
519
  access (`L4`); Workers guest computation may continue briefly until teardown (`X3`).
479
520
 
480
- | Channel | Shape | Typed? |
481
- | ------------------------------------------------------------------------- | ----------------------------------------------------------- | ------ |
482
- | A caught Connecta host failure | `Error` with `message`, `code`, `retryable`, and `details` | yes |
483
- | An uncaught **tool, resource or discovery** failure, as the model sees it | `{ error: { code, message, retryable, … } }` with `isError` | yes |
484
- | Program or execution failure (`E5`, `E6`, a bridge bound in `L6`) | `{ error: { code, message, retryable, details? } }` | yes |
521
+ | Channel | Shape | Typed? |
522
+ | ------------------------------------------------------------------------- | ------------------------------------------------------------------ | ------ |
523
+ | A caught Connecta host failure | `Error` with `message`, `code`, `retryable`, `data`, and `details` | yes |
524
+ | An uncaught **tool, resource or discovery** failure, as the model sees it | `{ error: { code, message, retryable, … } }` with `isError` | yes |
525
+ | Program or execution failure (`E5`, `E6`, a bridge bound in `L6`) | `{ error: { code, message, retryable, details? } }` | yes |
485
526
 
486
527
  Both executor bridges rebuild typed host rejections as guest Errors and retain
487
528
  their identity in executor-owned state (`X11`). `message` stays human text, capped at 2,000
488
529
  JSON-serialized characters including quotes and an `…` marker when clipped.
489
- `code` and `retryable` are the stable branch fields; `details` carries the host
490
- classification and fits 3,700 serialized characters. Optional recovery metadata
530
+ `code` and `retryable` are the stable branch fields; `data` and `details` carry the same host
531
+ classification, which fits 3,700 serialized characters. Optional recovery metadata
491
532
  that would exceed that bound is omitted whole, preserving `code`, `message`,
492
533
  `retryable`, and `retryAfterMs`, because a clipped recovery address or argument
493
534
  describes a different call. This covers `call`, `read`, `search`, `describe`, `result`, `skill`, `emit`, and
@@ -497,6 +538,17 @@ HTTP(S) origin of at most 253 UTF-8 bytes, and `details.code`, a validated
497
538
  network errno, undici transport code, or `timeout` of at most 32 bytes; neither
498
539
  enters activity.
499
540
 
541
+ On hosts without URL elicitation, `connecta.call` auth failures carry `recovery`,
542
+ `nextAction`, and the handoff in `error.data`, also exposed as `error.details`.
543
+ An OAuth handoff includes `authorizationUrl` and `instructions`; operator
544
+ credential recovery includes `operatorUrl`, declared credential fields, and
545
+ instructions. `connecta.search` catalog errors and `connecta.describe`
546
+ `errorDetails` carry the same fields. When an auth error includes a handoff, give
547
+ it to the user or operator. One program run reuses one handoff per connector,
548
+ including concurrent call and catalog errors. Errors never request a forced
549
+ restart. Use `authorize_connector` for an explicit connection or a fresh link.
550
+ URL-elicitation hosts retain their existing flow.
551
+
500
552
  **E2.** The taxonomy: `retryable` is what connecta reports, `Y3` what a program
501
553
  may do. A provider maps each downstream failure to the code that tells the
502
554
  caller what to do next, and never invents a cause it was not told.
@@ -533,8 +585,9 @@ and let the failure reach the model.
533
585
  program unless the pool is trusted (`W12`). It is refused with
534
586
  `destructive_tool_requires_approval` before validation and before anything is
535
587
  sent, `nextAction` carrying its canonical address to `call_destructive_tool`
536
- plus the original arguments when they fit the 512-byte echo budget — whole or
537
- not at all, since a clipped copy is a different call. The host's prompt on that
588
+ and a schema-filtered snapshot within the 512-byte echo budget. `argsRedacted`
589
+ marks partial or withheld arguments; use the original arguments if this flag is
590
+ set or `args` is absent. Snapshots are never clipped. The host's prompt on that
538
591
  call is the approval, and the only one: generated code can neither mint the
539
592
  capability nor approve its own write, and the model's short `reason` grants no
540
593
  authority and never goes downstream.
@@ -606,33 +659,45 @@ fields. Program-authored projection saved bytes; host heuristics could drop
606
659
  deliberately returned fields. Helpers need [#222](https://github.com/zackbart/connecta/issues/222)
607
660
  evidence that programs fail to project.
608
661
 
609
- **R2.** The boundary is 24,000 serialized characters (~6k tokens). A value over
610
- it is replaced by exactly one envelope:
611
-
612
- ```json
613
- {
614
- "truncated": true,
615
- "preview": "…",
616
- "totalChars": 5242880,
617
- "hint": "filter/map/slice data inside execute_code and return only what you need"
618
- }
619
- ```
620
-
621
- The envelope is itself bounded as serialized, so `totalChars` is always the true
622
- size of what the program returned and truncation happens exactly once no matter
623
- how many hops the value takes.
624
-
625
- **R3.** Truncation is a _successful_ result: the program ran but returned too
626
- much. Run a program that returns less; that is why the envelope says so.
627
-
628
- **R4 (verdict: no result paging for programs).** Program results have no
629
- `connecta.result` handle. A program can shrink its return; paging would reward
630
- unprojected data.
631
-
632
- For non-repeatable writes, inspect and reduce the full result before return,
633
- or page a direct `call_destructive_tool` result on a trusted endpoint with
634
- `connecta.result`. Sampling a
635
- program result may discard the only copy.
662
+ **R2.** The boundary is 24,000 serialized characters (~6k tokens), shared with
663
+ emitted text. An oversized return is stashed as compact JSON through the same
664
+ result store as direct calls. The returned notice carries `truncated`, `resultId`,
665
+ `totalBytes`, `hint`, `nextOffset: 0`, and an executable `nextAction` that pages
666
+ with `connecta.result`. It also retains `totalChars` and a bounded `preview`.
667
+ The recovery action and hint precede the preview, so clients that spill results
668
+ after the first 2,000 characters retain the handle and the instruction.
669
+ Small returns pass through unchanged; Connecta does not select fields.
670
+
671
+ **R3.** Truncation is a _successful_ result. The program completed and its full
672
+ return can be read without running it again. Prefer filtering or reducing reads
673
+ before returning them. If the run completed a write, the notice opens with
674
+ "This write already ran: do not call it again to see its result."
675
+ This warning uses host accounting for writes completed in this run. Paging an
676
+ earlier write result does not count as a new write.
677
+
678
+ **R4.** Program returns share direct-call stash envelopes, 15-minute expiry,
679
+ aggregate capacity charges, and credential redaction before persistence.
680
+ Their pages bind the admitted subject, principal, endpoint/pool, origin, and
681
+ all contributing tool calls, resource and skill reads, and catalog metadata.
682
+ Downstream skill and resource dependencies require a whole-connector grant.
683
+ Local guides and catalog dependencies require visibility of the contributing connector or tool, even
684
+ when the metadata describes a write on a read-only endpoint.
685
+ Caught call failures retain that connector visibility when catalog loading or
686
+ tool resolution fails. Recovery messages listing configured connectors or
687
+ local guides retain visibility of those contributors too.
688
+ Each page rechecks current auth,
689
+ grants, pool membership, and trust. Reading a stash inside a program carries
690
+ its dependencies forward to any new return stash. The page cap is the smallest
691
+ of the deployment cap and contributing connectors' effective `maxResultBytes`.
692
+ Read-only endpoints cannot page write results. A UUID is a handle, never a grant.
693
+
694
+ If paging is unavailable because the stash is full, storage fails, or text
695
+ cannot round-trip as UTF-8, the successful return keeps the existing bounded
696
+ `{ truncated, preview, totalChars, hint }` fallback. Its hint explains that
697
+ paging is unavailable and retains the instruction to filter/map/slice. A write's
698
+ hint still says it already ran. Never rerun a write to recover its output.
699
+ JSON serialization preserves lone surrogates as escapes, so ordinary
700
+ JSON-returning programs can page them losslessly.
636
701
 
637
702
  **R5.** `console.log`, `console.warn`, and `console.error` are captured in call
638
703
  order and returned as one `logs` string, capped at 4,000 characters with a
@@ -665,17 +730,37 @@ request; it is not activity, a session, or a stream.
665
730
 
666
731
  ## Emitted output
667
732
 
668
- Images accept only `image/png`, `image/jpeg`, `image/gif`, or `image/webp`
733
+ Guest-authored images accept only `image/png`, `image/jpeg`, `image/gif`, or `image/webp`
669
734
  and nonempty canonical base64. Whitespace, URL-safe alphabets, bad padding,
670
735
  and nonzero pad bits are rejected before collection. Size budgets still apply.
671
736
 
672
737
  MCP-native output a return value cannot carry: base64 is not projectable, so a
673
- block that survives intake uncapped (`S5`) must not die at the `R2` exit guard.
738
+ block that fits the inline call limit (`S5`, `L6`) can use the separate
739
+ emission transport budget instead of the `R2` return guard.
674
740
  The earlier alternatives are in [decision history](https://github.com/zackbart/connecta/blob/main/decisions/0001-ethos-verdict-table.md)
675
741
  ([#267](https://github.com/zackbart/connecta/issues/267),
676
742
  [#270](https://github.com/zackbart/connecta/issues/270)).
677
743
 
678
- **M1.** `connecta.emit(block)` accepts exactly one block: `{ type: "text",
744
+ **M1.** `connecta.emit(result)` accepts a rich result from this program's
745
+ `connecta.call` and forwards its original native content blocks, including
746
+ resources, resource links, annotations and `_meta`. `connecta.emit(block)` also
747
+ accepts individual entries of that result's `content`. The trusted guest
748
+ prelude maps these objects to opaque request-local references; the host checks
749
+ those references and emits owned deep snapshots of retained native blocks taken
750
+ before result paging can yield. Oversized structured data returns its paging
751
+ handle before native presentation is inspected. Presentation traversal stops at
752
+ 64 levels, 32,768 values, or the larger of the default and configured emission
753
+ byte budgets. Only envelopes within the 1 MiB inline cap retain block snapshots.
754
+ Cycles, non-JSON values, and traversal limits refuse presentation with an
755
+ unavailable-paging notice; structured data remains usable. That notice has no
756
+ result ID and reports `totalBytes: 0` because traversal could not measure a
757
+ complete JSON value.
758
+ Connector mutations after retention cannot change guest output, accepted blocks,
759
+ or their byte and text charges, including nested resource fields and metadata.
760
+ Copies and guest-authored blocks keep the strict validation below. No program
761
+ can mint a native URI.
762
+
763
+ Guest-authored `connecta.emit(block)` accepts exactly one block: `{ type: "text",
679
764
  text }` or `{ type: "image" | "audio", data /* base64 */, mimeType }`, every
680
765
  field a string, no extra fields, no `annotations`, no `_meta`, no sugar forms.
681
766
  An invalid block throws catchably and nothing is accepted — rejected, not
@@ -692,6 +777,8 @@ presentation, not a second data channel.
692
777
  serialized block size reduces the return budget, and oversized text fails with
693
778
  `result_too_large`. Image/audio blocks use the separate transport budget and
694
779
  reach the model as real MCP media content, including when `emit` is not awaited.
780
+ Native embedded resource text also shares the result cap; resource blobs count
781
+ against the serialized-byte emission budget.
695
782
  The trusted runner waits for emission acknowledgments before returning success.
696
783
  An unobserved emission failure fails the run; an awaited failure remains catchable.
697
784
  Rejections propagated through `then` or `finally` can be caught later in that
@@ -703,7 +790,8 @@ chain. A separate unhandled branch still fails the run.
703
790
  **M5.** Two budgets (`ConnectaConfig.execute.maxEmittedBytes` /
704
791
  `.maxEmittedBlocks`, defaults 4,000,000 serialized bytes and 32 blocks) fail
705
792
  loudly at the `emit` call, naming the budget and the room remaining; nothing is
706
- partially accepted and prior blocks stand. Accepted and rejected emission attempts
793
+ partially accepted and prior blocks stand. Forwarding a whole native result
794
+ checks every block before accepting any of them. Accepted and rejected emission attempts
707
795
  also have a terminal limit of four times the configured block cap (at least 128),
708
796
  which bounds retained host failures and guest acknowledgement state without
709
797
  discarding an older error identity. No result stash for emitted blocks: the program
@@ -712,14 +800,15 @@ bound, not a context bound — emitted media reaches the model as media, not
712
800
  base64 text.
713
801
 
714
802
  **M6.** No provenance is claimed: every emitted block is program output, trusted
715
- exactly as much as the return value. Preservation is re-emission of the raw
716
- downstream block, so `S5`'s uncapped fallthrough is contract.
803
+ exactly as much as the return value. Native forwarding preserves the raw
804
+ downstream block through a host-issued reference, within `S5`, `L6` and `M5`.
717
805
 
718
806
  **M7.** `emit` alone spends no host-call budget (`L4`); `search`, `describe`,
719
807
  `call`, `read`, `result`, and `skill` share it. Text also observes `R2`.
720
808
 
721
- **M8.** `emit` is a provider function; blocks cross the guest boundary once as
722
- an argument. `ExecuteResult` remains compatible with upstream codemode's types;
809
+ **M8.** `emit` is a provider function. Guest-authored blocks cross as arguments;
810
+ native blocks cross once as call output and emissions send only their references.
811
+ Native call output uses the same bounded stash transfers as `L6`. `ExecuteResult` remains compatible with upstream codemode's types;
723
812
  construction requires the Worker adapter or explicit custom opt-in. Any executor
724
813
  that bridges provider calls gets emission for free.
725
814
 
@@ -834,13 +923,34 @@ the Dynamic Worker inherits the platform isolate's limits (`X2`). A third
834
923
  executor must bound all three somehow — this is the clause that makes untrusted
835
924
  code safe to run at all.
836
925
 
837
- **L6.** A host call's serialized arguments and its serialized result are each
838
- bounded — QuickJS caps both at 256 KiB (`X10`) — and exceeding either fails that
839
- call, not the execution, so a program can catch it and ask for less. The failure
840
- is executor-owned untyped text, not a Connecta host failure (`E1`). An
841
- over-bound _result_ names the address the program called rather than only the
842
- generic bridge function; an over-bound _argument_ payload is refused before it
843
- is parsed, so it names no address at all.
926
+ **L6.** QuickJS bounds each serialized host-call message at 256 KiB. Full guest
927
+ returns cross bounded 65,536-character IPC chunks, with a 64 MiB aggregate
928
+ transport ceiling. The parent retains the completed value until it can apply
929
+ the result stash policy; the 1 MiB per-message IPC ceiling stays in force. Oversized
930
+ `connecta.call` results use the existing direct-call stash before crossing that
931
+ bridge. The trusted guest initializer reconstructs values up to 1 MiB from
932
+ bounded pages, retaining JSON versus text format and every payload code point,
933
+ including U+FEFF at page starts. Larger values return a
934
+ `{ format: "paged", valueFormat, resultId, totalBytes, truncated: true, hint }`
935
+ handle. Pass the handle or its `resultId` to `connecta.result` and reduce the
936
+ pages before returning them. Automatic transfers spend no additional host-call
937
+ budget; explicit paging does. This policy is shared by QuickJS, Worker and custom
938
+ executors that run provider preludes.
939
+ Oversized raw text containing unpaired UTF-16 surrogates returns a handle without
940
+ `resultId`, with a notice that it cannot be paged as text. This preserves the
941
+ UTF-8 byte-offset contract without silently replacing code units. The completed
942
+ call stays successful, including write accounting; JSON-wrapped strings still
943
+ round-trip losslessly.
944
+
945
+ Stashes retain their existing bindings, 15-minute expiry, per-connector page
946
+ caps and aggregate capacity charges on memory, SQLite and D1. Capacity exhaustion
947
+ or a storage failure returns a successful notice without a `resultId`. A failed
948
+ automatic reconstruction retains the handle. Neither result path reissues the
949
+ call or changes a completed write into a failed or unknown write. Guest returns use the same store when they exceed the presentation cap (`R2`–`R4`).
950
+
951
+ Over-bound arguments and other unpaged bridge results still fail catchably with
952
+ executor-owned text. An over-bound result names the called address; an argument
953
+ payload is refused before parsing and names no address.
844
954
 
845
955
  **L7.** Executions are admitted, not queued indefinitely: bounded concurrency
846
956
  plus a bounded queue with a wait timeout. Overload is a retryable
@@ -948,6 +1058,15 @@ transport failure leaves the outcome unknown.
948
1058
  addition to the host-call budget. It is checked after argument validation and
949
1059
  before admission, so an over-budget write spends no permit.
950
1060
 
1061
+ Program `uncertainCall` and `uncertainCalls` use the same schema-filtered argument
1062
+ snapshots as direct calls, even when guest code catches the failure. `argsRedacted: true`
1063
+ means sensitive fields were omitted or the entire echo was withheld because
1064
+ sensitivity could not be resolved. `argsOmitted: true` means no `args` is present,
1065
+ including echoes above the byte budget. These fields identify targets for
1066
+ reconciliation. Any new call must use the original arguments when its echo is
1067
+ partial or absent. A returned `writes` count cannot make a run safe to repeat.
1068
+ See [argument echo rules](./meta-tools.md#echo-budgets) for supported schema shapes.
1069
+
951
1070
  **W12.** `trusted` endpoints annotate `execute_code` as a write and permit
952
1071
  program writes. `read-only` endpoints annotate it as read-only and refuse
953
1072
  program writes before validation, with `call_destructive_tool` as the recovery.
@@ -1025,7 +1144,7 @@ reasonable demand on a platform sandbox.
1025
1144
  values through a tagged envelope, so a `Uint8Array` may survive there. `P3` is
1026
1145
  the contract: JSON-serializable values, or the program is Workers-only.
1027
1146
 
1028
- **X8. Unknown properties.** The guest namespace exposes only the six documented
1147
+ **X8. Unknown properties.** The guest namespace exposes only the seven documented
1029
1148
  functions. Unknown and inherited members are absent on both executors; calling
1030
1149
  one is a guest `TypeError` under `E6`. Engine message text is not contract.
1031
1150
 
@@ -1037,13 +1156,11 @@ Normalizing that would spend real CPU on every program to improve the error
1037
1156
  message of a program that is already wrong. `P3` is the contract: neither
1038
1157
  behavior returns the value.
1039
1158
 
1040
- **X10. Per-host-call payload bound.** `L6`'s 256 KiB ceiling on a host call's
1041
- arguments and result is QuickJS's, enforced at its IPC boundary. The Dynamic
1042
- Worker has no documented equivalent; Workers RPC limits apply and connecta adds
1043
- none, because that boundary is an isolate-to-isolate call rather than a
1044
- `process.send` with a hard ceiling. A program returning a quarter-megabyte from
1045
- one tool call therefore fails on Node and may succeed on Workers — reduce inside
1046
- the program either way (`R1`).
1159
+ **X10. Per-host-call payload bound.** QuickJS enforces `L6`'s 256 KiB message
1160
+ ceiling at its IPC boundary. The Dynamic Worker uses Workers RPC limits.
1161
+ Connecta's shared program result policy keeps call results and result pages
1162
+ within the QuickJS message ceiling on every executor. It does not raise the
1163
+ argument limit or the guest's heap, CPU, execution, or returned-result limits.
1047
1164
 
1048
1165
  **X12** described a paused sandbox and left with pausing
1049
1166
  ([#672](https://github.com/zackbart/connecta/issues/672)); the id stays retired.
@@ -1076,49 +1193,49 @@ Titles name clauses; executor-independent clauses run in both arms.
1076
1193
  `test/codemode-compat.test.ts` pins upstream shape compatibility, minified upstream
1077
1194
  rejection, and branded adapter acceptance across module copies.
1078
1195
 
1079
- | Clauses | Test |
1080
- | ----------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
1081
- | `P1`, `P5` | both guest-contract executors (TypeScript syntax, trailing terminators, wrapper recovery), `test/program-source.test.ts` (which semicolons and wrappers are recovered), `test/quickjs-executor.node.test.ts` (`normalizeCode`) |
1082
- | `P2`, `X5` | `test/guest-api-contract.test.ts` (Dynamic globals plus loader-only filesystem, HTTP, environment, egress, DNS, and local `data:` boundaries), `test/guest-api-contract-quickjs.node.test.ts` (exact absent globals and blocked imports), `test/quickjs-child-stderr.node.test.ts` (a child-process environment holding only `TZ=UTC`), `test/deployment-shapes.node.test.ts` (loader-only Worker construction) |
1083
- | `P3`, `X9` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` |
1084
- | `P4` | `test/guest-api-contract.test.ts` (no cross-run leakage), `test/execute.test.ts` (one catalog load per connector per execution) |
1085
- | `A1`, `A2` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (canonical addressing), `test/server.test.ts` (bounded live connector inventory) |
1086
- | `S1`, `S1a`, `S2` | `test/guest-api-contract.test.ts` (flat page, connector guides, schema keys, unfiltered browse), `test/execute.test.ts` (guide pagination/partial/no-match behavior and `$ref`/`allOf`), `test/meta-tools-search.test.ts` (mixed complete/partial ranking, stable pagination, the two safety classes), `test/typescript-signatures.test.ts` (the TypeScript format over provider and pathological schemas, search/describe parity, observed labeling), `test/typescript-signatures-parse.node.test.ts` (every rendering parses) |
1087
- | `S3` | `test/guest-api-contract.test.ts` (typed uncaught bound), `test/execute.test.ts` (count limits, fan-out bound) |
1088
- | `S4` | both guest-contract executors (ordered mixed describe results with unknown-address, unknown-tool suggestion, and catalog-failure details), `test/meta-tools-search.test.ts` (top-level routing, no-suggestion, catalog-failure, and hostile-input bounds) |
1089
- | `S5`, `S6` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (`unwrapMcpResult`, fail-closed annotations, activity parity) |
1090
- | `S7` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (parallel calls and shared admission) |
1091
- | `S8`, `E1`, `X11` | both guest-contract executors (caught call, discovery, utility, removed-function, and forgery cases; typed promise rejections), `test/quickjs-executor.node.test.ts` (oversized messages, private transport, forged outcomes) |
1092
- | `S9` | `test/result-shapes.test.ts` (value exclusion, bounds, merging, LRU and time expiry, runtime isolation, read-only admission, declared precedence, definition invalidation, unwrapped MCP results, discovery provenance, copy isolation, failure isolation) |
1093
- | `S10` | `test/resource-read.test.ts` (qualified routing, whole-connector grants, personal credentials, redaction, admission, timeout, cancellation and downstream MCP reads), both guest-contract executors (successful resource reads and caught/uncaught typed failures) |
1094
- | `E2`, `E8` | `test/guest-api-contract.test.ts` (code → `retryable`, caught, parallel, and uncaught validation recovery, a conflict's bounded `current`), `test/meta-tools-call.test.ts` (direct, destructive, provider fallback), `test/validate.test.ts` (bounded payload-free findings), `test/errors.test.ts` |
1095
- | `E3`, `E4` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (`auth_required`, destructive reroute), `test/program-writes.test.ts` (the refusal's `nextAction`, nothing sent, a caught refusal) |
1096
- | `E5` | `test/guest-api-contract.test.ts` (execution-failure channel, in-flight `cancelled`), `test/execute.test.ts` (admission), `test/executor-admission.test.ts`, `test/quickjs-executor.node.test.ts` (mid-run shutdown) |
1097
- | `E6`, `X8` | `test/guest-api-contract.test.ts` (unknown and inherited members, retained error identities), `test/quickjs-executor.node.test.ts` |
1098
- | `E7` | `test/guest-api-contract.test.ts` (refusals about a `503`-named connector), `test/errors.test.ts` |
1099
- | `R1`, `R2`, `R3` | `test/guest-api-contract.test.ts` (pass-through, truncation is success, envelope fits the cap and is idempotent) |
1100
- | `R4`, `M6`, `M9` | verdicts; `R2`'s guard, `M1`'s strict typing, and `M2`'s collect-then-deliver are their enforcement |
1101
- | `R5` | `test/guest-api-contract.test.ts`, `test/quickjs-log-limits.node.test.ts` |
1102
- | `R6`–`R8` | `test/guest-api-contract.test.ts` (normal result keys), `test/execute.test.ts` (opt-in operation aggregates, failure paths, payload exclusion) |
1103
- | `Y1`, `Y2`, `Y3` | `test/guest-api-contract.test.ts` (one attempt per call, retryable flags by code) |
1104
- | `Y4` | `test/meta-tools-call.test.ts`, `test/call-admission.test.ts` (one attempt, retry hints, caller reissue) |
1105
- | `L1`, `L2` | `test/guest-api-contract.test.ts` (in-flight call fails `cancelled`), `test/execute.test.ts` (cancels outstanding host calls, discovery included, and refuses discovery after the run; a cancelled wedged executor, or one whose `acquire()` ignores the signal, returns promptly and releases its lease) |
1106
- | `L3`, `X1` | `test/guest-api-contract.test.ts` (short-deadline executors), `test/execute.test.ts` (the watchdog ends a never-settling executor, frees the default pool, spares a slow run, and falls back from an unusable value) |
1107
- | `L4`, `L8` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (shared discovery/call budgets and terminal catch-and-continue loops and queued-write cancellation on both executors), `test/worker-budget-response.node.test.ts` (native handle disposal and admission recovery across completed HTTP responses) |
1108
- | `L5`, `L7`, `X2` | `test/quickjs-executor.node.test.ts` (CPU, heap), `test/execute.test.ts` and `test/executor-admission.test.ts` (bounded admission and queue) |
1109
- | `L6`, `X10` | `test/quickjs-executor.node.test.ts` (bridge and IPC bounds for arguments and result; the address in the over-bound message), `test/quickjs-child-stderr.node.test.ts` (outer reply serialization failure settles the call) |
1110
- | `V1`–`V4` | `test/guest-api-contract.test.ts` (dispatched calls, every refusal class including an address no connector owns, the friction each derives, no event for the execution itself), `test/activity.test.ts` (the shared code → friction table, the identity clamp, the one-attempt floor), `test/operator-view.test.ts`, `test/sql-storage-contract.ts`, run by `test/d1-storage.node.test.ts` and `test/sqlite-storage.node.test.ts` (historical pause and approval rows still render and round-trip) |
1111
- | `V5`, `W9` | `test/program-writes.test.ts` (an unawaited trusted-pool write finished and recorded, its unknown outcome reported, counts on a failed program, the classification table), `test/invocation-pipeline.test.ts` (the gate after validation, an unrecorded refusal) |
1112
- | `W10`, `W12` | `test/program-writes.test.ts` (a trusted-pool write runs and every other write keeps `E4`, the write budget, pool trust and override precedence, `call_tool` still refusing, search and describe verdicts, construction refusals), `test/operator-ui-model.test.ts`, `test/browser/operator-ui.spec.ts` (the badge) |
1113
- | `M1` | `test/guest-api-contract.test.ts` (invalid emits throw catchably, accept nothing), `test/execute-emit.test.ts` (every rejected shape) |
1114
- | `M2`, `M3` | `test/guest-api-contract.test.ts` (delivery order, truncated return plus delivered blocks), `test/execute-emit.test.ts` (envelope, `structuredContent`, byte-for-byte no-emit path) |
1115
- | `M4` | `test/guest-api-contract.test.ts` (discard is visible), `test/execute-emit.test.ts` (structured and plain paths), `test/quickjs-executor.node.test.ts` (mid-run shutdown) |
1116
- | `M5`, `M7` | `test/execute-emit.test.ts` (both budgets fail the crossing block; host-call budget untouched) |
1117
- | `M8` | two arms passing one case table, `test/codemode-compat.test.ts` |
1118
- | `M10` | `test/execute-emit.test.ts` (aggregate present, numbers only, absent when nothing emitted) |
1119
- | `X4` | `test/guest-api-contract.test.ts` (string logs only), `test/quickjs-executor.node.test.ts` (logs before cancellation), `test/quickjs-child-stderr.node.test.ts` (crash, shutdown, deadline, IPC failure, bounded parent retention), `test/quickjs-log-limits.node.test.ts` (unchanged successful logs) |
1120
- | `X3`, `X6` | `test/quickjs-executor.node.test.ts` (cancels a running child, never-settling await), `test/execute.test.ts` (a wedged executor stops being awaited) |
1121
- | `X7` | `P3`'s tests; the Workers superset is deliberately unused |
1196
+ | Clauses | Test |
1197
+ | ---------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
1198
+ | `P1`, `P5` | both guest-contract executors (TypeScript syntax, trailing terminators, wrapper recovery), `test/program-source.test.ts` (which semicolons and wrappers are recovered), `test/quickjs-executor.node.test.ts` (`normalizeCode`) |
1199
+ | `P2`, `X5` | `test/guest-api-contract.test.ts` (Dynamic globals plus loader-only filesystem, HTTP, environment, egress, DNS, and local `data:` boundaries), `test/guest-api-contract-quickjs.node.test.ts` (exact absent globals and blocked imports), `test/quickjs-child-stderr.node.test.ts` (a child-process environment holding only `TZ=UTC`), `test/deployment-shapes.node.test.ts` (loader-only Worker construction) |
1200
+ | `P3`, `X9` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` |
1201
+ | `P4` | `test/guest-api-contract.test.ts` (no cross-run leakage), `test/execute.test.ts` (one catalog load per connector per execution) |
1202
+ | `A1`, `A2` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (canonical addressing), `test/server.test.ts` (bounded live connector inventory) |
1203
+ | `S1`, `S1a`, `S2` | `test/guest-api-contract.test.ts` (flat page, connector guides, schema keys, unfiltered browse), `test/execute.test.ts` (guide pagination/partial/no-match behavior and `$ref`/`allOf`), `test/meta-tools-search.test.ts` (mixed complete/partial ranking, stable pagination, the two safety classes), `test/typescript-signatures.test.ts` (the TypeScript format over provider and pathological schemas, search/describe parity, observed labeling), `test/typescript-signatures-parse.node.test.ts` (every rendering parses) |
1204
+ | `S3` | `test/guest-api-contract.test.ts` (typed uncaught bound), `test/execute.test.ts` (count limits, fan-out bound) |
1205
+ | `S4` | both guest-contract executors (ordered mixed describe results with unknown-address, unknown-tool suggestion, and catalog-failure details), `test/meta-tools-search.test.ts` (top-level routing, no-suggestion, catalog-failure, and hostile-input bounds) |
1206
+ | `S5`, `S6` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (`unwrapMcpResult`, fail-closed annotations, activity parity) |
1207
+ | `S7` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (parallel calls and shared admission) |
1208
+ | `S8`, `E1`, `X11` | both guest-contract executors (caught call, discovery, utility, removed-function, and forgery cases; typed promise rejections), `test/quickjs-executor.node.test.ts` (oversized messages, private transport, forged outcomes) |
1209
+ | `S9` | `test/result-shapes.test.ts` (value exclusion, bounds, merging, LRU and time expiry, runtime isolation, read-only admission, declared precedence, definition invalidation, unwrapped MCP results, discovery provenance, copy isolation, failure isolation) |
1210
+ | `S10` | `test/resource-read.test.ts` (qualified routing, whole-connector grants, personal credentials, redaction, admission, timeout, cancellation and downstream MCP reads), both guest-contract executors (successful resource reads and caught/uncaught typed failures) |
1211
+ | `E2`, `E8` | `test/guest-api-contract.test.ts` (code → `retryable`, caught, parallel, and uncaught validation recovery, a conflict's bounded `current`), `test/meta-tools-call.test.ts` (direct, destructive, provider fallback), `test/validate.test.ts` (bounded payload-free findings), `test/errors.test.ts` |
1212
+ | `E3`, `E4` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (`auth_required`, destructive reroute), `test/program-writes.test.ts` (the refusal's `nextAction`, nothing sent, a caught refusal) |
1213
+ | `E5` | `test/guest-api-contract.test.ts` (execution-failure channel, in-flight `cancelled`), `test/execute.test.ts` (admission), `test/executor-admission.test.ts`, `test/quickjs-executor.node.test.ts` (mid-run shutdown) |
1214
+ | `E6`, `X8` | `test/guest-api-contract.test.ts` (unknown and inherited members, retained error identities), `test/quickjs-executor.node.test.ts` |
1215
+ | `E7` | `test/guest-api-contract.test.ts` (refusals about a `503`-named connector), `test/errors.test.ts` |
1216
+ | `R1`, `R2`, `R3`, `R4` | `test/guest-api-contract.test.ts` and `test/guest-api-contract-quickjs.node.test.ts` (small pass-through, shared return paging and unavailable fallback, no repeated writes, live authority), `test/program-result-cases.ts` (reconstruction, redaction, notice survives a 2,000-character spill) |
1217
+ | `M6`, `M9` | verdicts; `R2`'s guard, `M1`'s strict typing, and `M2`'s collect-then-deliver are their enforcement |
1218
+ | `R5` | `test/guest-api-contract.test.ts`, `test/quickjs-log-limits.node.test.ts` |
1219
+ | `R6`–`R8` | `test/guest-api-contract.test.ts` (normal result keys), `test/execute.test.ts` (opt-in operation aggregates, failure paths, payload exclusion) |
1220
+ | `Y1`, `Y2`, `Y3` | `test/guest-api-contract.test.ts` (one attempt per call, retryable flags by code) |
1221
+ | `Y4` | `test/meta-tools-call.test.ts`, `test/call-admission.test.ts` (one attempt, retry hints, caller reissue) |
1222
+ | `L1`, `L2` | `test/guest-api-contract.test.ts` (in-flight call fails `cancelled`), `test/execute.test.ts` (cancels outstanding host calls, discovery included, and refuses discovery after the run; a cancelled wedged executor, or one whose `acquire()` ignores the signal, returns promptly and releases its lease) |
1223
+ | `L3`, `X1` | `test/guest-api-contract.test.ts` (short-deadline executors), `test/execute.test.ts` (the watchdog ends a never-settling executor, frees the default pool, spares a slow run, and falls back from an unusable value) |
1224
+ | `L4`, `L8` | `test/guest-api-contract.test.ts`, `test/execute.test.ts` (shared discovery/call budgets and terminal catch-and-continue loops and queued-write cancellation on both executors), `test/worker-budget-response.node.test.ts` (native handle disposal and admission recovery across completed HTTP responses) |
1225
+ | `L5`, `L7`, `X2` | `test/quickjs-executor.node.test.ts` (CPU, heap), `test/execute.test.ts` and `test/executor-admission.test.ts` (bounded admission and queue) |
1226
+ | `L6`, `X10` | `test/guest-api-contract-quickjs.node.test.ts` and `test/guest-api-contract.test.ts` (whole oversized reads and one-write pageable handles), `test/sqlite-storage.node.test.ts` and `test/d1-storage.node.test.ts` (shared stash transfers), `test/quickjs-executor.node.test.ts` (bridge and IPC bounds for arguments and result; the address in the over-bound message), `test/quickjs-child-stderr.node.test.ts` (outer reply serialization failure settles the call) |
1227
+ | `V1`–`V4` | `test/guest-api-contract.test.ts` (dispatched calls, every refusal class including an address no connector owns, the friction each derives, no event for the execution itself), `test/activity.test.ts` (the shared code → friction table, the identity clamp, the one-attempt floor), `test/operator-view.test.ts`, `test/sql-storage-contract.ts`, run by `test/d1-storage.node.test.ts` and `test/sqlite-storage.node.test.ts` (historical pause and approval rows still render and round-trip) |
1228
+ | `V5`, `W9` | `test/program-writes.test.ts` (an unawaited trusted-pool write finished and recorded, its unknown outcome reported, counts on a failed program, the classification table), `test/invocation-pipeline.test.ts` (the gate after validation, an unrecorded refusal) |
1229
+ | `W10`, `W12` | `test/program-writes.test.ts` (a trusted-pool write runs and every other write keeps `E4`, the write budget, pool trust and override precedence, `call_tool` still refusing, search and describe verdicts, construction refusals), `test/operator-ui-model.test.ts`, `test/browser/operator-ui.spec.ts` (the badge) |
1230
+ | `M1` | `test/guest-api-contract.test.ts` (invalid emits throw catchably, accept nothing), `test/execute-emit.test.ts` (rejected shapes, bounded native snapshots, paging before metadata traversal, and cyclic presentation refusal) |
1231
+ | `M2`, `M3` | `test/guest-api-contract.test.ts` (delivery order, truncated return plus delivered blocks), `test/execute-emit.test.ts` (envelope, `structuredContent`, byte-for-byte no-emit path) |
1232
+ | `M4` | `test/guest-api-contract.test.ts` (discard is visible), `test/execute-emit.test.ts` (structured and plain paths), `test/quickjs-executor.node.test.ts` (mid-run shutdown) |
1233
+ | `M5`, `M7` | `test/execute-emit.test.ts` (both budgets fail the crossing block; host-call budget untouched) |
1234
+ | `M8` | two arms passing one case table, `test/codemode-compat.test.ts` |
1235
+ | `M10` | `test/execute-emit.test.ts` (aggregate present, numbers only, absent when nothing emitted) |
1236
+ | `X4` | `test/guest-api-contract.test.ts` (string logs only), `test/quickjs-executor.node.test.ts` (logs before cancellation), `test/quickjs-child-stderr.node.test.ts` (crash, shutdown, deadline, IPC failure, bounded parent retention), `test/quickjs-log-limits.node.test.ts` (unchanged successful logs) |
1237
+ | `X3`, `X6` | `test/quickjs-executor.node.test.ts` (cancels a running child, never-settling await), `test/execute.test.ts` (a wedged executor stops being awaited) |
1238
+ | `X7` | `P3`'s tests; the Workers superset is deliberately unused |
1122
1239
 
1123
1240
  The surface itself is checked by `test/server.test.ts` (the exact six-tool list),
1124
1241
  `test/code-first-surface.test.ts` (construction, executor, removed tools, copy, and size),