@zackbart/connecta 0.35.0 → 0.36.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +97 -0
- package/README.md +8 -4
- package/bin/version.mjs +1 -1
- package/dist/auth/downstream-oauth.js +71 -79
- package/dist/auth/static-oauth.js +104 -26
- package/dist/connectors/api-connector.d.ts +17 -0
- package/dist/connectors/api-connector.js +3 -1
- package/dist/http/client.js +1 -1
- package/dist/http/hatch-paging.js +2 -2
- package/dist/http/paging.js +3 -89
- package/dist/http/provider.js +1 -2
- package/dist/http/services.js +1 -1
- package/dist/http/tools.js +1 -27
- package/dist/operator-ui/contract.d.ts +1 -0
- package/dist/operator-ui/generated.js +4 -4
- package/dist/program-writes.js +0 -1
- package/dist/providers/_shared/google/kit.js +29 -139
- package/dist/providers/_shared/rest/kit.js +4 -404
- package/dist/providers/_shared/sensitive-fields.js +0 -16
- package/dist/providers/breeze/api.js +2 -2
- package/dist/providers/ccb/api.js +1 -1
- package/dist/providers/cloudflare/api.js +8 -8
- package/dist/providers/cloudflare/lib/config.d.ts +2 -1
- package/dist/providers/docs/api.js +1 -1
- package/dist/providers/docs/tools.js +1 -2
- package/dist/providers/drive/api.js +2 -2
- package/dist/providers/drive/lib/hatch.js +1 -1
- package/dist/providers/drive/tools.js +1 -1
- package/dist/providers/forms/api.js +1 -1
- package/dist/providers/forms/lib/hatch.js +1 -1
- package/dist/providers/forms/tools.js +2 -3
- package/dist/providers/github/api.js +1 -1
- package/dist/providers/github/lib/discovery.js +2 -2
- package/dist/providers/gmail/api.js +1 -1
- package/dist/providers/gmail/tools.js +2 -2
- package/dist/providers/granola/api.js +155 -0
- package/dist/providers/granola/index.d.ts +10 -0
- package/dist/providers/granola/index.js +68 -0
- package/dist/providers/granola/openapi.generated.js +30 -0
- package/dist/providers/granola/safety.js +37 -0
- package/dist/providers/granola/skill.generated.js +5 -0
- package/dist/providers/granola/tools.js +2 -0
- package/dist/providers/overflow/api.js +26 -26
- package/dist/providers/planning-center/api.js +4 -4
- package/dist/providers/planning-center/lib/constants.d.ts +1 -1
- package/dist/providers/planning-center/lib/json-api.js +2 -2
- package/dist/providers/quickbooks/api.js +299 -0
- package/dist/providers/quickbooks/index.d.ts +13 -0
- package/dist/providers/quickbooks/index.js +93 -0
- package/dist/providers/quickbooks/lib/query.js +118 -0
- package/dist/providers/quickbooks/lib/writes.js +168 -0
- package/dist/providers/quickbooks/safety.js +222 -0
- package/dist/providers/quickbooks/skill.generated.js +5 -0
- package/dist/providers/quickbooks/tools.js +117 -0
- package/dist/providers/sheets/api.js +1 -1
- package/dist/providers/sheets/lib/hatch.js +2 -2
- package/dist/providers/sheets/lib/requests.js +1 -1
- package/dist/providers/sheets/tools.js +1 -2
- package/dist/providers/slides/api.js +1 -1
- package/dist/providers/slides/tools.js +2 -2
- package/dist/providers/stripe/api.js +7 -7
- package/dist/providers/tithely/api.js +2 -2
- package/dist/providers/vercel/api.js +12 -12
- package/dist/providers/vercel/index.js +1 -2
- package/dist/providers/vercel/lib/pin.js +1 -1
- package/dist/routes/mcp.js +1 -1
- package/dist/routes/oauth.js +3 -0
- package/dist/runtime/admission.js +0 -12
- package/dist/runtime/call.js +0 -4
- package/dist/skills.js +0 -1
- package/dist/storage/keys.js +2 -3
- package/dist/types.d.ts +2 -0
- package/dist/ui.d.ts +1 -1
- package/dist/ui.js +0 -1
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/documentation/README.md +1 -0
- package/documentation/architecture.md +249 -366
- package/documentation/auth.md +56 -19
- package/documentation/code-mode.md +6 -6
- package/documentation/integrating.md +1 -1
- package/documentation/meta-tools.md +6 -3
- package/documentation/operator-tests.md +11 -2
- package/documentation/operator-ui.md +17 -5
- package/documentation/providers.md +492 -0
- package/package.json +12 -9
- package/templates/node/package.json +1 -1
- package/dist/operator-ui/agents.d.ts +0 -75
- package/dist/operator-ui/agents.js +0 -114
- package/dist/operator-ui/config-summary.js +0 -566
- package/dist/operator-ui/connection-map.js +0 -378
- package/dist/operator-ui/endpoints.js +0 -212
- package/dist/operator-ui/fix-prompts.d.ts +0 -18
- package/dist/operator-ui/fix-prompts.js +0 -79
- package/dist/operator-ui/health.js +0 -52
- package/dist/operator-ui/member-page.js +0 -97
- package/dist/operator-ui/overview.js +0 -126
- package/dist/operator-ui/setup-commands.js +0 -47
- package/dist/operator-ui/view.d.ts +0 -378
- package/dist/operator-ui/view.js +0 -631
- package/dist/providers/_shared/rest/dispatch.js +0 -21
- package/dist/providers/_shared/rest/tools.js +0 -592
|
@@ -426,7 +426,7 @@ client. A raw Worker stream established the runtime behavior; a custom auth
|
|
|
426
426
|
provider returning a synthetic streaming 401 exercised Connecta's real admission
|
|
427
427
|
wrapper. Each case had its own Connecta instance with one request permit and no
|
|
428
428
|
queue. Health checks and subsequent MCP requests confirmed the same isolate ID.
|
|
429
|
-
The [recorded observations](https://github.com/zackbart/connecta/blob/
|
|
429
|
+
The [recorded observations](https://github.com/zackbart/connecta/blob/1ab92695f2636f904274d900ce209553358ff1f3/scripts/probes/worker-disconnect-2026-09-25.json)
|
|
430
430
|
contain all twelve cases, including served flags and client-end timing.
|
|
431
431
|
|
|
432
432
|
| Response and flag | Raw stream abort / cancel | Connecta source abort / cancel | Admission after response; next request |
|
|
@@ -486,23 +486,23 @@ MCP requests still rejected a competing request with 503 before the deadline;
|
|
|
486
486
|
the first MCP request after the deadline returned all eight tools with 200 in
|
|
487
487
|
the original isolate. Admission then reported zero active requests. Without the
|
|
488
488
|
flag, the source still recorded no abort or cancellation, so recovery did not
|
|
489
|
-
rely on runtime cleanup. The [recovery observations](https://github.com/zackbart/connecta/blob/
|
|
489
|
+
rely on runtime cleanup. The [recovery observations](https://github.com/zackbart/connecta/blob/1ab92695f2636f904274d900ce209553358ff1f3/scripts/probes/worker-disconnect-recovered-2026-09-25.json)
|
|
490
490
|
also retain two inconclusive queue-handoff cases: concurrent client connections
|
|
491
491
|
reached different isolates and could not establish an abandoned queued waiter.
|
|
492
|
-
A [second trial using HTTP/2](https://github.com/zackbart/connecta/blob/
|
|
492
|
+
A [second trial using HTTP/2](https://github.com/zackbart/connecta/blob/1ab92695f2636f904274d900ce209553358ff1f3/scripts/probes/worker-disconnect-h2-2026-09-25.json)
|
|
493
493
|
repeated the twelve passing core cases and verified queued cancellation with
|
|
494
494
|
request signals enabled. Even on one HTTP/2 connection, the no-signal queue case
|
|
495
495
|
crossed isolates and remained inconclusive. The Node and workerd regression
|
|
496
496
|
suites cover expired waiters, orphaned handoffs, and identity-safe late release
|
|
497
497
|
deterministically.
|
|
498
498
|
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
499
|
+
The [historical probe source](https://github.com/zackbart/connecta/blob/1ab92695f2636f904274d900ce209553358ff1f3/scripts/probes/worker-disconnect.mjs)
|
|
500
|
+
and observations are retained in Git history, outside the current checkout and
|
|
501
|
+
npm package. The probe deployed a disposable Worker containing only synthetic
|
|
502
|
+
data, verified the served configuration, saved observations, and deleted the
|
|
503
|
+
Worker in `finally`. It used no `waitUntil`, which would change the lifetime
|
|
504
|
+
being measured. The production runtime build number was not exposed by the
|
|
505
|
+
deployment; these findings are tied to the date and flags above.
|
|
506
506
|
|
|
507
507
|
### Production Access bypass for agent endpoints
|
|
508
508
|
|
|
@@ -763,9 +763,9 @@ adoption, OAuth handoff ownership, single-use connect links, every downstream
|
|
|
763
763
|
OAuth grant write and consent claim, the result stash, and initialization of the cursor signing key.
|
|
764
764
|
|
|
765
765
|
Every key is built in `src/storage/keys.ts`, which lists each family with its
|
|
766
|
-
scope, version, codec, and TTL policy
|
|
767
|
-
|
|
768
|
-
|
|
766
|
+
scope, version, codec, and TTL policy. Deployed-consumer persistence journeys
|
|
767
|
+
check actual owner isolation in the physical database; key probes retain NUL
|
|
768
|
+
refusal. Core hands
|
|
769
769
|
subsystems namespaced views: `conn:<id>:` per connector, `principal:<key>:` per
|
|
770
770
|
personal registry, `results:` and `subject:<key>:` for result paging.
|
|
771
771
|
|
|
@@ -1266,20 +1266,16 @@ removed. Legacy hosted selectors fail at construction with the generic migration
|
|
|
1266
1266
|
path. GitHub retains its scope-enforced App identity and exposes a bounded repository-read and release-write hatch plus local scope discovery, scoped data search and guarded merge.
|
|
1267
1267
|
|
|
1268
1268
|
[Decision 0011](https://github.com/zackbart/connecta/blob/main/decisions/0011-provider-standard.md)
|
|
1269
|
-
records the provider standard
|
|
1269
|
+
records the provider standard implemented by every maintained provider. It fixes
|
|
1270
1270
|
one folder layout per kind and fixed evidence names. `drift.json` gets a
|
|
1271
1271
|
generated block and the guide a generated Conventions section, and every
|
|
1272
|
-
`api()` surface gets one agent-facing shape.
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
refuses a provider past step 1 that breaks the `drift.json` rules, or one past
|
|
1280
|
-
step 2 that breaks the guide rules: `drift.json` version 2's `generated` block
|
|
1281
|
-
(operations from the kit's `ProviderKitFacts` and evidence digests), and a guide's `## Conventions`, rendered
|
|
1282
|
-
from the definition's declarations into `skill.generated.ts`.
|
|
1272
|
+
`api()` surface gets one agent-facing shape. Every maintained provider meets the
|
|
1273
|
+
standard without a migration exemption. `test/provider-standard.node.test.ts`
|
|
1274
|
+
holds every provider folder to it, and `test/provider-conventions.test.ts`
|
|
1275
|
+
checks the surface rules on Node. `providers:generate` refuses drift (D) and
|
|
1276
|
+
guide (G) violations before writing. It derives `drift.json` version 2's
|
|
1277
|
+
`generated` block from kit operations and evidence digests, and the guide's
|
|
1278
|
+
`## Conventions` from definition declarations into `skill.generated.ts`.
|
|
1283
1279
|
The generator requires `fixtures.ts` to export `createAuthored()` with a
|
|
1284
1280
|
nonempty offline `staticTools` catalog. Its input/output schemas derive one
|
|
1285
1281
|
paging convention, including `get_*`, hatch search and details, excluding
|
|
@@ -1291,8 +1287,9 @@ reports a nonzero explicit refusal count with singular/plural wording and
|
|
|
1291
1287
|
points to the actual prefixed details tool with method/path lookup; it never
|
|
1292
1288
|
embeds the refusal table. Unreviewed operations remain refused.
|
|
1293
1289
|
`ProviderContext.usageGuide` selects a guide's `<!-- when: <key> -->` blocks
|
|
1294
|
-
with the definition's `blocks`.
|
|
1295
|
-
|
|
1290
|
+
with the definition's `blocks`. Maintained drift records use version 2;
|
|
1291
|
+
`providers:check` retains version-1 endpoint/manual record parsing for historical
|
|
1292
|
+
reports, while OpenAPI generation and checks use `evidence/openapi.json`. It reports a manifest operation no endpoint row records at the provider's level,
|
|
1296
1293
|
and lists manual checks last verified more than 180 days ago. Its offline
|
|
1297
1294
|
record validator, `scripts/drift-validate.mjs`, also gates `providers:generate`
|
|
1298
1295
|
and the standard suite, so a record they accept is one `providers:check` reads.
|
|
@@ -1324,14 +1321,15 @@ A composition moves only by explicit review of its source pins/documents;
|
|
|
1324
1321
|
`--record` and `--file` cannot replace it. `providers:check` compares the actual
|
|
1325
1322
|
public documents independently; it never fetches a synthetic combined URL.
|
|
1326
1323
|
|
|
1327
|
-
The
|
|
1324
|
+
The indexed hatch (`src/http/hatch.ts`) serves
|
|
1328
1325
|
`<vendor>_api_search`, `_api_details`, `_api_read`, and `_api_write` over an
|
|
1329
1326
|
`OperationIndex` that `pnpm run providers:spec` compiles offline from the
|
|
1330
|
-
provider's pin (`evidence/openapi.json
|
|
1331
|
-
into `openapi.generated.ts`. A `vendored: true` pin compiles
|
|
1332
|
-
conversion in `evidence/openapi.document.json
|
|
1333
|
-
|
|
1334
|
-
|
|
1327
|
+
provider's pin (`evidence/openapi.json`)
|
|
1328
|
+
into `openapi.generated.ts`. A `vendored: true` pin compiles offline from
|
|
1329
|
+
the reviewed conversion in `evidence/openapi.document.json`, or derives a
|
|
1330
|
+
deterministic Discovery conversion from its pinned original as described below.
|
|
1331
|
+
The generated header records the converted document's digest beside the pin's,
|
|
1332
|
+
so offline freshness sees a changed conversion.
|
|
1335
1333
|
Each call is matched to an operation and checked against its parameters before
|
|
1336
1334
|
transport. Resolved path parameters are validated before authentication or dispatch,
|
|
1337
1335
|
including pinned enums and numeric bounds. Number path values must decode to canonical finite ASCII decimals without
|
|
@@ -1340,16 +1338,26 @@ canonical ASCII decimal safe integers: `0`, positive decimals without leading
|
|
|
1340
1338
|
zeros, or negative decimals without leading zeros. `-0`, leading `+`, whitespace,
|
|
1341
1339
|
exponents, decimal points and non-ASCII digits are refused. Negative integers
|
|
1342
1340
|
remain valid when the pin has no minimum excluding them. String-valued ids keep
|
|
1343
|
-
their declared string contract
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
value-safety table (required;
|
|
1347
|
-
|
|
1348
|
-
|
|
1349
|
-
|
|
1350
|
-
|
|
1351
|
-
|
|
1352
|
-
|
|
1341
|
+
their declared string contract. `_api_read` admits only operations with explicit
|
|
1342
|
+
reviewed read verdicts, including GET/HEAD and read-only POSTs where declared;
|
|
1343
|
+
classification is per tool name. Providers declare a confined kit connection,
|
|
1344
|
+
a value-safety table (required;
|
|
1345
|
+
see below), and any framing, scope, paging or refusal hooks through the hatch
|
|
1346
|
+
binding. The connection owns authentication, transport, failure mapping and
|
|
1347
|
+
result safety. An index's `slashParams` can admit an encoded `/` in a reviewed
|
|
1348
|
+
final key segment. Current hatch admission, paging, privacy and one-send
|
|
1349
|
+
outcomes are exercised by the required `eval:outcomes` tasks against stateful
|
|
1350
|
+
vendors and HTTP MCP deployments. `test/provider-hostile-response.node.test.ts`
|
|
1351
|
+
commits real HTTP writes before returning HTML, malformed JSON or an oversized
|
|
1352
|
+
acknowledgement, then reconciles vendor state with exactly one physical send.
|
|
1353
|
+
`test/provider-privacy-journey.node.test.ts` checks credential echoes over HTTP.
|
|
1354
|
+
Focused provider suites retain MIME/draft restrictions, revision conflicts,
|
|
1355
|
+
CCB routing, Planning Center product exclusions and deployment pins. Native
|
|
1356
|
+
HTTP framing, cursor and request-lifetime fault probes remain in the HTTP suites.
|
|
1357
|
+
The catalog-wide status sweep and its argument roster, catalog/ranking copies
|
|
1358
|
+
and unused paging strategy tests are retired under #1072. Provider workflows
|
|
1359
|
+
belong in the existing shared outcomes; a new tool requires no failure-matrix row.
|
|
1360
|
+
No legacy REST tool adapter remains.
|
|
1353
1361
|
Large documents opt into generator options that drop restated operation ids
|
|
1354
1362
|
and plain path parameters and cap one operation's details (`opBudget`).
|
|
1355
1363
|
`numericBounds: true` preserves documented numeric minimum/maximum constraints
|
|
@@ -1364,11 +1372,10 @@ levels, 256 paths or 200 characters per path; overflow or an unresolved
|
|
|
1364
1372
|
reference omits that operation's whole response-field contract. Explicitly open
|
|
1365
1373
|
roots (including root-array items) also leave fields absent. Empty,
|
|
1366
1374
|
schemaless and non-JSON responses declare no fields. Request shrinking and
|
|
1367
|
-
endpoint contract digests do not depend on this metadata.
|
|
1368
|
-
retain their catalog and discovery behavior until each provider's step 2.
|
|
1375
|
+
endpoint contract digests do not depend on this metadata.
|
|
1369
1376
|
Fields remain optional additive metadata, so a previously compiled
|
|
1370
1377
|
index without the source bytes remains usable without inventing a response
|
|
1371
|
-
contract. Vercel's
|
|
1378
|
+
contract. Vercel's pin includes response metadata from the reviewed public
|
|
1372
1379
|
document; operations without declared response properties still refuse fields. Breeze's pin declares no response
|
|
1373
1380
|
properties. GitHub's immutable official OpenAPI pin supplies its complete index and response fields; a reviewed repository allowlist controls dispatch. Natural queries with reviewed matches scope discovery to those matches and named-only operations; explicit paths and unmatched queries retain full-pin refusal discovery.
|
|
1374
1381
|
`check:providers-generated` checks each index header against its source record
|
|
@@ -1406,7 +1413,7 @@ UTF-16 code units; full reconstruction must match its recorded exact length.
|
|
|
1406
1413
|
These physical decode checks do not change request validation, schema traversal,
|
|
1407
1414
|
search, refusal, result or discovery budgets. Generation and offline roundtrip
|
|
1408
1415
|
tests must preserve every pinned logical contract; storage changes never accept
|
|
1409
|
-
new upstream evidence
|
|
1416
|
+
new upstream evidence. The compaction suites cover exact strings,
|
|
1410
1417
|
native Web Crypto identity, malformed references, lazy decoding, mutation
|
|
1411
1418
|
semantics and every maintained provider.
|
|
1412
1419
|
|
|
@@ -1427,14 +1434,12 @@ every vendor ships one reviewed table through one mechanism
|
|
|
1427
1434
|
signing, webhooks, drains, transfer, claim, and invite codes). It is the
|
|
1428
1435
|
union of the detectors Cloudflare and Vercel shipped first, and
|
|
1429
1436
|
deliberately over-inclusive. `providers:spec` writes
|
|
1430
|
-
`evidence/value-safety.json`
|
|
1431
|
-
provider's step 1) when the source record sets
|
|
1437
|
+
`evidence/value-safety.json` when the source record sets
|
|
1432
1438
|
`options.valueSafety` (vendor `operationWords`; Stripe's `expansions: false`
|
|
1433
1439
|
skips id-or-object expansions, which are their own operations' candidates),
|
|
1434
1440
|
stamped with the pinned digest, the detector format, and its options. The
|
|
1435
1441
|
file is test evidence and never ships.
|
|
1436
|
-
2. **One reviewed verdict per candidate**, in the vendor's `safety.ts
|
|
1437
|
-
(`value-safety.ts` until its step 1):
|
|
1442
|
+
2. **One reviewed verdict per candidate**, in the vendor's `safety.ts`:
|
|
1438
1443
|
`refuse` (the generic tools refuse it before transport, naming the
|
|
1439
1444
|
operation and the reason), `redact` (reviewed field paths), or `safe`, each
|
|
1440
1445
|
with a reason. Paths are dot paths into the data a tool returns: a list on
|
|
@@ -1455,8 +1460,8 @@ every vendor ships one reviewed table through one mechanism
|
|
|
1455
1460
|
otherwise. `providers:spec` derives the binding fields from the pinned
|
|
1456
1461
|
schema, and the harness fails until the condition lists each one. Argument-dependent refusals (Stripe expansions,
|
|
1457
1462
|
Vercel `decrypt`) stay in the vendor's `refuse` hook.
|
|
1458
|
-
3. **Redaction on every success body**, in
|
|
1459
|
-
before cursors and `
|
|
1463
|
+
3. **Redaction on every success body**, in the kit connection after `result`
|
|
1464
|
+
and before cursors and `fields`, so named tools, HEAD data, and uploads pass
|
|
1460
1465
|
through it too: the operation's reviewed paths, then the key-name
|
|
1461
1466
|
heuristic as defense in depth. The heuristic is the union of the former
|
|
1462
1467
|
vendor engines: a credential word anywhere in a non-metadata name removes
|
|
@@ -1619,14 +1624,13 @@ response schema can return (through `options.valueSafety.dataRoot` for an
|
|
|
1619
1624
|
envelope such as Cloudflare's `result`), and every resource rule path
|
|
1620
1625
|
something the resource's schema can return. It stamps the paths that resolve
|
|
1621
1626
|
into the candidates file and fails on the rest, unless the table's `absent`
|
|
1622
|
-
field
|
|
1627
|
+
field acknowledges
|
|
1623
1628
|
them with a reason (shared verdicts applied to operations whose schema lacks a
|
|
1624
1629
|
path, or fields a schema leaves undeclared; such paths still apply at
|
|
1625
1630
|
runtime).
|
|
1626
1631
|
|
|
1627
1632
|
`test/fixtures/value-safety.ts` is the shared harness each vendor's
|
|
1628
|
-
`
|
|
1629
|
-
runs; `reviewProblems` is pure, and
|
|
1633
|
+
`provider.safety.node.test.ts` runs; `reviewProblems` is pure, and
|
|
1630
1634
|
`test/value-safety-harness.node.test.ts` proves wrong paths fail it. It fails
|
|
1631
1635
|
on candidates from another pin, format, or option set; an unreviewed
|
|
1632
1636
|
candidate; a verdict for an operation the index lacks; a table path the stamp
|
|
@@ -1653,232 +1657,116 @@ There are no hosted review maps, pins, drift comparisons or review UI fields.
|
|
|
1653
1657
|
Catalog refresh activity still compares successive accepted catalog fingerprints
|
|
1654
1658
|
and reports only added, removed and changed counts in the caller's partition.
|
|
1655
1659
|
|
|
1656
|
-
####
|
|
1657
|
-
|
|
1658
|
-
|
|
1659
|
-
|
|
1660
|
-
|
|
1661
|
-
|
|
1662
|
-
|
|
1663
|
-
|
|
1664
|
-
|
|
1665
|
-
|
|
1666
|
-
|
|
1667
|
-
|
|
1668
|
-
|
|
1669
|
-
|
|
1670
|
-
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
|
|
1674
|
-
|
|
1675
|
-
|
|
1676
|
-
|
|
1677
|
-
- The
|
|
1678
|
-
|
|
1679
|
-
and
|
|
1680
|
-
|
|
1681
|
-
|
|
1682
|
-
|
|
1683
|
-
|
|
1684
|
-
|
|
1685
|
-
|
|
1686
|
-
|
|
1687
|
-
|
|
1688
|
-
|
|
1689
|
-
|
|
1690
|
-
|
|
1691
|
-
|
|
1692
|
-
|
|
1693
|
-
|
|
1694
|
-
|
|
1695
|
-
|
|
1696
|
-
|
|
1697
|
-
|
|
1698
|
-
|
|
1699
|
-
|
|
1700
|
-
|
|
1701
|
-
|
|
1702
|
-
|
|
1703
|
-
|
|
1704
|
-
|
|
1705
|
-
|
|
1706
|
-
|
|
1707
|
-
|
|
1708
|
-
|
|
1709
|
-
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
|
|
1713
|
-
|
|
1714
|
-
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
|
|
1721
|
-
|
|
1722
|
-
-
|
|
1723
|
-
|
|
1724
|
-
|
|
1725
|
-
|
|
1726
|
-
`
|
|
1727
|
-
|
|
1728
|
-
|
|
1729
|
-
|
|
1730
|
-
|
|
1731
|
-
|
|
1732
|
-
|
|
1733
|
-
|
|
1734
|
-
|
|
1735
|
-
|
|
1736
|
-
|
|
1737
|
-
|
|
1738
|
-
-
|
|
1739
|
-
|
|
1740
|
-
|
|
1741
|
-
|
|
1742
|
-
|
|
1743
|
-
|
|
1744
|
-
|
|
1745
|
-
|
|
1746
|
-
|
|
1747
|
-
|
|
1748
|
-
|
|
1749
|
-
|
|
1750
|
-
|
|
1751
|
-
|
|
1752
|
-
|
|
1753
|
-
|
|
1754
|
-
-
|
|
1755
|
-
|
|
1756
|
-
|
|
1757
|
-
|
|
1758
|
-
|
|
1759
|
-
|
|
1760
|
-
|
|
1761
|
-
|
|
1762
|
-
|
|
1763
|
-
|
|
1764
|
-
|
|
1765
|
-
|
|
1766
|
-
Unsupported producer dependencies reject within the turn bound; teardown
|
|
1767
|
-
always clears timers and releases capture ownership, including after failed
|
|
1768
|
-
construction and overlapping capture rejection. The next capture must work.
|
|
1769
|
-
Each capture has an async-context epoch that closes before ownership is
|
|
1770
|
-
released, even when its native extension cap is exhausted. Controlled-source dispatchers reject closed
|
|
1771
|
-
continuations before touching another capture's state. Fake request entry,
|
|
1772
|
-
admission, response delivery, and serialization check their owning epoch,
|
|
1773
|
-
including after asynchronous body inspection. Late work cannot record into
|
|
1774
|
-
or receive a response from a later capture, which never waits for it.
|
|
1775
|
-
Closing also attaches rejection handlers to outstanding counted promises,
|
|
1776
|
-
consuming abandoned native body-read rejections without awaiting them.
|
|
1777
|
-
Source regressions explicitly assert either completion or bounded rejection
|
|
1778
|
-
followed by recovery. Crypto-delay probes at 11,000 and 100,000 host turns
|
|
1779
|
-
must complete with unchanged observations; producer-fed bodies need not.
|
|
1780
|
-
- The network answers in zero virtual time. Before advancing to the next
|
|
1781
|
-
timer, the loop requires eight quiet real event-loop turns and an audit.
|
|
1782
|
-
A row records nonzero `waitedMs`, the virtual time spent on provider
|
|
1783
|
-
timers. Elapsed-time readings count only those timers. A timer of 0 ms
|
|
1784
|
-
set outside a timer callback is due at once and stays in the current
|
|
1785
|
-
cohort. Unjoined timers at completion fail. Since `AbortSignal.timeout`
|
|
1786
|
-
cannot be cancelled, remaining signal deadlines fire during teardown, outside
|
|
1787
|
-
`waitedMs`; any resulting request or result mutation fails. Every successful
|
|
1788
|
-
drive and scenario boundary has zero outstanding controlled work and timers.
|
|
1789
|
-
- Auxiliary routes answer token exchanges and other requests that are not
|
|
1790
|
-
the tool's own, and are recorded by name with headers and body. A JWT in a
|
|
1791
|
-
header or field is recorded as its decoded header and claims, with
|
|
1792
|
-
`<signature>` for the per-run signature.
|
|
1793
|
-
- `setup` runs before each scenario; its requests must be identical in
|
|
1794
|
-
every scenario and are recorded once.
|
|
1795
|
-
- Determinism: a fresh fake clock per scenario (timers, `Date`, and
|
|
1796
|
-
`performance`, and Node `process.hrtime`/`hrtime.bigint`, starting at
|
|
1797
|
-
2026-01-02T03:04:05Z), counted
|
|
1798
|
-
`crypto.randomUUID`, and fixed `crypto.getRandomValues` and `Math.random`,
|
|
1799
|
-
all restarted per scenario. `create(scenario)` receives a slug unique in
|
|
1800
|
-
the process: the scenario name plus a per-capture suffix the goldens never
|
|
1801
|
-
show. Load-time hrtime dispatchers also control Effect wall and monotonic
|
|
1802
|
-
nanoseconds on the virtual clock. Default-date Intl formatting also reads
|
|
1803
|
-
the virtual wall clock.
|
|
1804
|
-
A process-wide cache (Google's delegated tokens) never carries
|
|
1805
|
-
over from an earlier scenario or capture.
|
|
1806
|
-
- Secrets: every credential field and secret becomes `<secret:field>`, with
|
|
1807
|
-
HTTP Basic shown decoded. Before that placeholdering, the harness fails
|
|
1808
|
-
the capture if any secret reaches a caller-visible result (INV-5). The
|
|
1809
|
-
guard decodes the result itself: JSON escapes, percent escapes in either
|
|
1810
|
-
hex case, and base64 or base64url at any alignment, up to three layers
|
|
1811
|
-
deep. It also finds any start of a secret that reaches 12 characters past
|
|
1812
|
-
its public framing, so a truncated echo is a leak. Framing is a PEM armor
|
|
1813
|
-
line and the DER structure that opens every key of its type (tags,
|
|
1814
|
-
lengths, version, algorithm identifier), which guides and example keys
|
|
1815
|
-
print. A later fragment, a shorter one in any encoding, or a secret with
|
|
1816
|
-
its case changed is not detected. A base64 run is decoded only from 11
|
|
1817
|
-
characters (8 bytes), shorter than the base64 of any start the guard
|
|
1818
|
-
looks for.
|
|
1819
|
-
- The echo call carries every secret not listed in `unsent` in each
|
|
1820
|
-
encoding redaction covers: raw, percent-encoded with upper- and lowercase
|
|
1821
|
-
hex, base64, unpadded base64url, and `\uXXXX` escapes with upper- and
|
|
1822
|
-
lowercase hex, plus the base64 of each `basic` pair. Every sent secret
|
|
1823
|
-
contains `/`, `+`, and `=`, so its percent and base64url forms differ from
|
|
1824
|
-
its raw and base64 forms. The `401 echo` case echoes the raw secrets only
|
|
1825
|
-
unless the spec sets `errorEcho: "all"`: a provider that caps a vendor
|
|
1826
|
-
message before redaction sees it would leak the start of a longer form its
|
|
1827
|
-
cut goes through. The Google Workspace specs set it, since Google redacts a
|
|
1828
|
-
message whole before cutting it to 500 characters. Their `401 echo` carries
|
|
1829
|
-
`errorEchoForms`: every form above, the `Bearer` and `token` framings, and
|
|
1830
|
-
an HTTP Basic pair holding the token as header, base64 and base64url.
|
|
1831
|
-
|
|
1832
|
-
Object keys keep the order the provider produced. A migration changes the
|
|
1833
|
-
provider, never the spec or harness.
|
|
1834
|
-
|
|
1835
|
-
`test/goldens.test.ts` compares every provider on Node and workerd. It fails
|
|
1836
|
-
if a provider folder is neither covered nor listed as remote-MCP-only, a tool
|
|
1837
|
-
has no call, or a golden file is missing or extra. Ordinary checks never write.
|
|
1838
|
-
Node compares forward and reverse observations byte for byte; workerd compares
|
|
1839
|
-
canonical observations. Each order starts a fresh module graph. Workers projection
|
|
1840
|
-
removes variants only at harness observation positions, never from vendor fields
|
|
1841
|
-
or schemas. Fixture updates retain both orders.
|
|
1842
|
-
There are no characterization tiers, path classifiers, or planning-only runs.
|
|
1843
|
-
|
|
1844
|
-
`test/goldens-harness.test.ts` keeps the source and mutation guards on Node:
|
|
1845
|
-
replaced Authorization headers, changed auxiliary/login bytes, writes sent
|
|
1846
|
-
early or twice, and missing secret-encoding redaction must alter a capture or
|
|
1847
|
-
fail it. Mutation probes capture the affected call rather than repeating an
|
|
1848
|
-
entire provider catalog. Redaction negative controls use Forms, GitHub, Breeze
|
|
1849
|
-
and Tithe.ly to cover OAuth/Bearer, app-token, query-key and provider-kit lanes;
|
|
1850
|
-
the ordinary goldens still check every provider's complete secret echoes.
|
|
1851
|
-
The native-extension budget is checked directly at its 100-extension boundary,
|
|
1852
|
-
and a gated closed-epoch continuation must fail before entering the next
|
|
1853
|
-
capture's network. Genuine crypto completion, rejection, late dispatch and
|
|
1854
|
-
producer-fed stream probes retain their native settlement coverage without
|
|
1855
|
-
repeating a million-turn synthetic delay. Ordinary runs use one source-probe schedule. Nightly Node runs set
|
|
1856
|
-
`CONNECTA_GOLDENS_DETERMINISM=1` for an identical repeat, provider jitter seeds
|
|
1857
|
-
1 and 2, and the complete source-probe jitter matrix. Small native-source probes also run on
|
|
1858
|
-
workerd: `scheduler.wait`, CompressionStream, saved timers/microtasks and
|
|
1859
|
-
Effect scheduling, prebound crypto/clocks, module freshness, runner clocks,
|
|
1860
|
-
and Blob/TextDecoderStream promise settlement. Runtime-specific cases carry
|
|
1861
|
-
Vitest's `workers` tag; broad cases carry `node`, which the Workers project
|
|
1862
|
-
skips. Other mixed transport/auth/runtime suites use the same tags to retain
|
|
1863
|
-
native fetch, request/response streams, deadlines, signals, crypto and SDK
|
|
1864
|
-
settlement without duplicating their policy matrices. `vitest.config.ts`
|
|
1865
|
-
selects these files with globs that tolerate test-file deletion. Portable
|
|
1866
|
-
filenames alone do not enroll a new file in workerd.
|
|
1867
|
-
|
|
1868
|
-
Repository verification policy, CI requirements, and exact commands live in
|
|
1869
|
-
[AGENTS.md](https://github.com/zackbart/connecta/blob/main/AGENTS.md#verification).
|
|
1870
|
-
|
|
1871
|
-
JWT fixture specs import fixed, public throwaway RSA PEM keys, with an
|
|
1872
|
-
import/sign/verify self-test. This avoids expensive key generation on every
|
|
1873
|
-
fresh module evaluation without changing characterized JWT claims or bytes.
|
|
1874
|
-
The harness never caches evaluated module graphs. Global controls prohibit
|
|
1875
|
-
`it.concurrent`; parallelism must use isolated files/workers. Transformed code
|
|
1876
|
-
may be cached.
|
|
1877
|
-
|
|
1878
|
-
`pnpm run goldens:update [provider...]` rewrites the named goldens (all
|
|
1879
|
-
when none are named) on Node; it is not part of `check`. A PR
|
|
1880
|
-
that changes agent-facing output on purpose regenerates the affected goldens
|
|
1881
|
-
and says why in its description; any other golden diff is a regression.
|
|
1660
|
+
#### Behavioral evidence (contributor)
|
|
1661
|
+
|
|
1662
|
+
The characterization snapshot engine, provider JSON snapshots, source scheduler
|
|
1663
|
+
and its self-tests are retired under
|
|
1664
|
+
[#1072](https://github.com/zackbart/connecta/issues/1072). Provider changes no
|
|
1665
|
+
longer require golden enrollment, snapshot updates, byte equivalence or nightly
|
|
1666
|
+
capture determinism. Production invariants remain unchanged.
|
|
1667
|
+
|
|
1668
|
+
Use the existing stateful fixture vendors and published-edge deployment adapters:
|
|
1669
|
+
|
|
1670
|
+
- `pnpm run eval:outcomes` drives representative joins, retained paging, endpoint
|
|
1671
|
+
refusal, auth handoff, value safety and recovery after committed refunds,
|
|
1672
|
+
cancellations, DNS and environment updates, plus a single GitHub draft release
|
|
1673
|
+
and Google document partial creation and shared-drive permissions. Graders inspect
|
|
1674
|
+
independent downstream state and the physical mutation ledger, and reject
|
|
1675
|
+
wrong targets, duplicate writes, missing completion and interrupted trials.
|
|
1676
|
+
Every reference also rejects a fabricated correct answer without the work.
|
|
1677
|
+
Promoted read journeys reject erased MCP data even with the vendor ledger intact.
|
|
1678
|
+
- `pnpm run eval:smoke` boots the Node template, Node eval deployments and native
|
|
1679
|
+
Workers deployments, including the actual QuickBooks and Granola providers, then exercises
|
|
1680
|
+
MCP and the operator page.
|
|
1681
|
+
- The shared `granola-workspace-journey` outcome uses actual provider reads,
|
|
1682
|
+
independent fake meeting state and physical cursor/filter requests on both
|
|
1683
|
+
Node/SQLite/QuickJS and native Workers/D1. It covers transcript-too-large
|
|
1684
|
+
recovery, empty intermediate pages, selected fields, withheld photo/credential
|
|
1685
|
+
values and shared-vault reuse after application reconstruction. No-op,
|
|
1686
|
+
fabricated-read and erased-delivery controls must fail.
|
|
1687
|
+
- `test/identity-write-journey.node.test.ts` uses the existing Node deployment
|
|
1688
|
+
adapter, stateful MCP fake, SQLite vault and QuickJS to grade admitted human
|
|
1689
|
+
and machine identities, pool isolation, fail-closed discovery, endpoint and
|
|
1690
|
+
connector policy, physical mutation counts, ambiguous-write reconciliation,
|
|
1691
|
+
credential ownership and payload-free activity. Independent decoding checks
|
|
1692
|
+
returned private values and credential echoes; positive record facts must
|
|
1693
|
+
still arrive. An explicitly writable pool also exercises reopening a
|
|
1694
|
+
read-only deployment without bypassing connector policy.
|
|
1695
|
+
- `test/cancellation-journey.node.test.ts` observes a queued client's departure
|
|
1696
|
+
without another vendor send, and an active client's departure after the
|
|
1697
|
+
vendor commits. The vendor must see its held response socket close before
|
|
1698
|
+
releasing it; a later MCP read recovers the committed intent exactly once.
|
|
1699
|
+
`test/cancellation-faults.test.ts` keeps signal-less token-resolution,
|
|
1700
|
+
warmed-credential digest, stalled body-cleanup and abort/grant races on Node
|
|
1701
|
+
and workerd. These replace the universal Promise-method/seam/owner matrix
|
|
1702
|
+
and its enrollment self-test, plus migration-only runtime wrapper checks.
|
|
1703
|
+
- `test/browser/operator-flows.spec.ts` serves the actual operator shell and
|
|
1704
|
+
routes over TCP with file-backed SQLite. Sign-in, Settings provenance, OAuth
|
|
1705
|
+
connect/disconnect and credential save/test/replace/remove survive closing and
|
|
1706
|
+
reopening the app, database and vault. An independent SQL connection reads
|
|
1707
|
+
trigger counts: one save, one replacement, one removal, and no credential
|
|
1708
|
+
writes from reads or a rejected replacement. A real SQL trigger failure leaves the old
|
|
1709
|
+
credential usable after restart. MCP calls verify that those edits preserve
|
|
1710
|
+
the reader pool's actual read access and write refusal. Activity renders
|
|
1711
|
+
successful calls recorded before restart without either credential value.
|
|
1712
|
+
- The existing Node-template `eval:smoke` target constructs invalid config from
|
|
1713
|
+
published imports before any I/O and reuses a stored token after restarting
|
|
1714
|
+
the consumer process. Its Worker-fakes target saves a personal credential in
|
|
1715
|
+
Chromium, refuses another owner's use, saves that owner's invalid credential,
|
|
1716
|
+
then restarts workerd on the same D1 directory. Actual downstream records
|
|
1717
|
+
remain readable only to the correct owner. Direct SQL inspection finds two
|
|
1718
|
+
distinct durable encrypted rows and exactly one committed save for each.
|
|
1719
|
+
- Keep focused SQL batch/schema/retention rollback, clock-skew and absolute
|
|
1720
|
+
expiry, NUL/UTF-8 and literal-prefix, cross-connection claims, cancellation,
|
|
1721
|
+
corrupt-row and tracing-secrecy probes. Keep operator identity/slot fences,
|
|
1722
|
+
deadlines, CSRF, restricted-view projection and sink secrecy probes. These
|
|
1723
|
+
cover faults that a successful browser journey cannot reproduce. Retired
|
|
1724
|
+
evidence includes the key-prefix source scanner, config expected-object
|
|
1725
|
+
matrices, operator structure snapshots and native-composition sentinels.
|
|
1726
|
+
- `test/provider-privacy-journey.node.test.ts` sends credentials through real
|
|
1727
|
+
HTTP MCP and a maintained API provider. Unknown vendor fields and keys carry
|
|
1728
|
+
raw, escaped, percent-encoded, base64 and Basic echoes through direct calls,
|
|
1729
|
+
QuickJS programs, failure and recovery. The independent decoder in
|
|
1730
|
+
`test/helpers/secret-echoes.ts` checks the wire responses for secret fragments;
|
|
1731
|
+
it does not normalize them to placeholders or compare saved output.
|
|
1732
|
+
- `test/provider-hostile-response.node.test.ts` reconciles real HTTP mutations
|
|
1733
|
+
after HTML, malformed JSON and oversized acknowledgements with one physical
|
|
1734
|
+
send. It distinguishes Stripe's reviewed pre-execution 401 refusal, and checks
|
|
1735
|
+
read failure facts, secrecy and recovery through direct and QuickJS calls.
|
|
1736
|
+
`test/provider-failure-sweep.test.ts` retains only concrete auxiliary, composite,
|
|
1737
|
+
in-flight and untracked-call fault probes; no provider/tool argument roster or
|
|
1738
|
+
catalog/finalizer agreement sweep remains. Existing
|
|
1739
|
+
`test/sent-secrets.test.ts`, `test/sent-secret-output-boundary.test.ts`,
|
|
1740
|
+
`test/request-secret-redaction.test.ts` and `test/catalog-secret-redaction.test.ts`
|
|
1741
|
+
cover secrecy before projection, truncation, caching, paging and diagnostics.
|
|
1742
|
+
- `test/write-evidence.node.test.ts`, `test/remote-mcp-attempts.node.test.ts` and
|
|
1743
|
+
`test/oauth-credential-attempts.node.test.ts` inspect physical socket sends.
|
|
1744
|
+
Native transport parity, OAuth and write-provenance suites retain their
|
|
1745
|
+
workerd coverage. The shared throwaway RSA key in `test/fixtures/rsa.ts` is
|
|
1746
|
+
used by write-provenance and unknown-write-advice fixtures.
|
|
1747
|
+
- The request, catalog, auxiliary-call and renewal lifetime
|
|
1748
|
+
suites, plus `test/auth-admission-binding.test.ts`, exercise cancellation,
|
|
1749
|
+
held native work and garbage collection. These test actual request ownership;
|
|
1750
|
+
the retired capture scheduler's source guards were only harness constraints.
|
|
1751
|
+
|
|
1752
|
+
The remaining probes defend distinct reachable failures: auth admission and
|
|
1753
|
+
native scheduler ownership, grant/callback fencing and refresh coordination,
|
|
1754
|
+
SDK replay/redirect/SSE attempts, nested write provenance and refusal evidence,
|
|
1755
|
+
unawaited program drain and failed-program accounting, catalog drift and paging
|
|
1756
|
+
revocation, and hostile serializers, structural echoes, truncation and persisted
|
|
1757
|
+
pages. Broad scripted-executor policy/privacy cross-products and repeated
|
|
1758
|
+
post-401 result/error-shape tables are retired. Protocol claims link executable
|
|
1759
|
+
evidence files in `spec/coverage.json`; the invariant contracts above are defended
|
|
1760
|
+
by the actual behavior assertions in these journeys and focused probes.
|
|
1761
|
+
The required CI gate includes build/declarations, Node and Workers probes,
|
|
1762
|
+
outcomes, browser flows, installed consumers and Docker, audits and real Eve
|
|
1763
|
+
compatibility. Further contributor cleanup is tracked in #1072.
|
|
1764
|
+
|
|
1765
|
+
Add a compact fault journey only for a meaningful outcome those suites cannot
|
|
1766
|
+
observe. Reuse their fixtures and adapters; do not reintroduce a snapshot
|
|
1767
|
+
format, module loader or virtual scheduler. Workerd enrollment is for native
|
|
1768
|
+
fetch, streams, Web Crypto, lifetime and request-byte behavior, as listed in
|
|
1769
|
+
`vitest.config.ts`; pure logic runs on Node.
|
|
1882
1770
|
|
|
1883
1771
|
## Optional deployment modules
|
|
1884
1772
|
|
|
@@ -1996,9 +1884,9 @@ declarations; elsewhere it lives in an unexported function or in
|
|
|
1996
1884
|
(`ConnectorCallError`, `ExecutorAdmissionError`, `CallAdmissionError`) because
|
|
1997
1885
|
callers and tests check `instanceof`, `name`, and `message`.
|
|
1998
1886
|
|
|
1999
|
-
Effect callers skip the Promise and take the program: `admit`
|
|
2000
|
-
|
|
2001
|
-
|
|
1887
|
+
Effect callers skip the Promise and take the program: `admit` for executor
|
|
1888
|
+
admission (`src/runtime/admission.ts`), `admitCall` and `acquireCallScoped` for
|
|
1889
|
+
call admission, `closeScope` and `closeScopeOnExit`
|
|
2002
1890
|
for a connector scope, `withDeadlineEffect` where Promise code has
|
|
2003
1891
|
`withDeadline`. The build prunes every declaration no `exports` target reaches,
|
|
2004
1892
|
and `pnpm run check:declarations` fails if what remains names an Effect type.
|
|
@@ -2152,8 +2040,7 @@ never-settling evaluation/host calls, late rejection, execute-once ownership and
|
|
|
2152
2040
|
original acquisition errors in workerd. `test/quickjs-pool.node.test.ts` covers
|
|
2153
2041
|
readiness release, stale/malformed IPC, late host failures, backoff and bounded
|
|
2154
2042
|
kill. Real Worker and QuickJS guest contracts, the HTTP Worker budget/queued
|
|
2155
|
-
request fixture and native-output suites supply runtime parity evidence
|
|
2156
|
-
provider goldens do not execute a sandbox.
|
|
2043
|
+
request fixture and native-output suites supply runtime parity evidence.
|
|
2157
2044
|
|
|
2158
2045
|
### Native SQL storage (contributor)
|
|
2159
2046
|
|
|
@@ -2219,8 +2106,8 @@ published storage interfaces.
|
|
|
2219
2106
|
The synchronous state-file parser, validation, file read, and one atomic
|
|
2220
2107
|
SQLite import remain native synchronous leaves because `importStateFile` is a
|
|
2221
2108
|
published synchronous API. `openSqlite` retains file modes, WAL, busy timeout,
|
|
2222
|
-
and database ownership. `test/sql-effect-contract.ts`
|
|
2223
|
-
|
|
2109
|
+
and database ownership. `test/sql-effect-contract.ts` retains affected-row,
|
|
2110
|
+
50-claim, typed-failure, cancellation, and tracing probes on SQLite and native
|
|
2224
2111
|
D1. `test/kv-to-d1.test.ts` also reuses stores across separate workerd requests;
|
|
2225
2112
|
the existing SQL contracts prove rollback, database-clock TTL, encodings,
|
|
2226
2113
|
activity upgrades, and copy recovery.
|
|
@@ -2283,9 +2170,12 @@ An accepted write's blocked retry retains its original HTTP status; a slot
|
|
|
2283
2170
|
occupied by an auxiliary read instead names the separate write step needed.
|
|
2284
2171
|
Structured resend advice reaches output only when the core permits it. Generic
|
|
2285
2172
|
unknown writes retain the core's diagnostic wait; Q8 removes it. The mapping
|
|
2286
|
-
adds no Promise entry or lifetime owner.
|
|
2287
|
-
|
|
2288
|
-
|
|
2173
|
+
adds no Promise entry or lifetime owner. `provider-failure-sweep.test.ts`,
|
|
2174
|
+
`guarded-attempts.node.test.ts`, `call-services.test.ts` and the native
|
|
2175
|
+
transport suites exercise these contracts through invocation, physical sockets
|
|
2176
|
+
and request closure. `http-kit.test.ts` retains focused numeric/text fact,
|
|
2177
|
+
request-equivalence and bulk-capacity fault probes. The migration-era
|
|
2178
|
+
kit/core verdict comparison is retired under #1072. Maintained API providers use the kit through their
|
|
2289
2179
|
explicit provider subpaths; it stays off the root import graph and published
|
|
2290
2180
|
declarations expose Promises.
|
|
2291
2181
|
|
|
@@ -2364,15 +2254,13 @@ inventories, and stale fallback cannot authorize post-entry auth recovery.
|
|
|
2364
2254
|
### Contributor provider kit
|
|
2365
2255
|
|
|
2366
2256
|
Provider declarations use `src/http/vendor.ts` for HttpApi operations and
|
|
2367
|
-
`src/http/tools.ts` for list, get, read
|
|
2257
|
+
`src/http/tools.ts` for list, get, read and write builders.
|
|
2368
2258
|
`src/http/provider.ts` composes them with `defineProvider`; it returns the
|
|
2369
2259
|
ordinary Promise-based Connector factory. The kit stays outside the root
|
|
2370
|
-
graph and its Effect types are internal.
|
|
2371
|
-
|
|
2372
|
-
are unchanged.
|
|
2260
|
+
graph and its Effect types are internal. In each provider, `api.ts` declares
|
|
2261
|
+
the vendor and `tools.ts` the tools.
|
|
2373
2262
|
|
|
2374
|
-
|
|
2375
|
-
A `list` without the legacy `key` returns `{ items, page }`, with
|
|
2263
|
+
The standard `list` builder returns `{ items, page }`, with
|
|
2376
2264
|
`page.nextCursor` only while `hasMore`, and the kit appends `limit` (the
|
|
2377
2265
|
declared default and maximum), `cursor` and `fields` to the tool's filters;
|
|
2378
2266
|
`read` and `get` take `fields: true`. `src/http/fields.ts` narrows after every
|
|
@@ -2460,7 +2348,7 @@ A refused method outside a read/write tool's input schema is inspected through
|
|
|
2460
2348
|
Gmail's 49 non-GET refusals do not add a method field or a write hatch, and Forms'
|
|
2461
2349
|
refused DELETE remains outside its write enum. GitHub's refused raw PUT merge
|
|
2462
2350
|
is likewise outside its write enum; its named guarded alternative is unaffected.
|
|
2463
|
-
|
|
2351
|
+
Such schema refusals happen
|
|
2464
2352
|
before authentication or I/O; details exposes the same reviewed reason as search.
|
|
2465
2353
|
Every schema-reachable refused operation still fails with that reason before
|
|
2466
2354
|
authentication or dispatch. This is policy inspection, never execution admission.
|
|
@@ -2611,12 +2499,11 @@ storage loses them with the store. Key-load outages or corrupt stored keys
|
|
|
2611
2499
|
produce retryable `unavailable`, naming the cursor signing key without its
|
|
2612
2500
|
value. See [cursor-key recovery](./deploying.md#recover-a-cursor-signing-key):
|
|
2613
2501
|
after repairing/deleting a corrupt key, restart every process/isolate to clear
|
|
2614
|
-
cached keys. Pre-upgrade cursors require a new first page.
|
|
2615
|
-
preseed a fixed key only in their harness.
|
|
2502
|
+
cached keys. Pre-upgrade cursors require a new first page.
|
|
2616
2503
|
|
|
2617
2504
|
The helper derives connection metadata and probe messages from
|
|
2618
|
-
validated options and
|
|
2619
|
-
|
|
2505
|
+
validated options and renders every maintained guide through
|
|
2506
|
+
`ProviderContext.usageGuide`.
|
|
2620
2507
|
Candidate checks can refuse before authentication while
|
|
2621
2508
|
preserving the provider's exact diagnostic. Its optional `authScope(options)`
|
|
2622
2509
|
selector fixes OAuth grant ownership from deployment mode at construction;
|
|
@@ -2624,8 +2511,7 @@ CCB uses shared System Auth grants and personal Identity Auth grants. Tool
|
|
|
2624
2511
|
arguments cannot select a grant's owner. On Node, every maintained-provider
|
|
2625
2512
|
request uses the owned sender `listen()` installs, reads included. Without it,
|
|
2626
2513
|
maintained-provider writes and reviewed POST reads are refused before sending;
|
|
2627
|
-
suites exercising those requests configure the sender themselves
|
|
2628
|
-
harness does. Anything a connection
|
|
2514
|
+
focused suites exercising those requests configure the sender themselves. Anything a connection
|
|
2629
2515
|
caches across calls, such as its typed HttpApi client, is built with no
|
|
2630
2516
|
services, because Effect constructors close over the context they run in and a
|
|
2631
2517
|
cached value would otherwise keep its first caller's request alive (INV-7).
|
|
@@ -2669,8 +2555,20 @@ All six Google Workspace products use the shared standard-surface support.
|
|
|
2669
2555
|
archived exact-byte official Discovery documents into deterministic OpenAPI.
|
|
2670
2556
|
The primary vendored pin retains the official URL, revision and source digest;
|
|
2671
2557
|
its `discovery` relation names the sibling source pin and normalizer format.
|
|
2672
|
-
|
|
2673
|
-
|
|
2558
|
+
The sole retained document is `evidence/discovery.document.json`; no converted
|
|
2559
|
+
`openapi.document.json` is retained for these pins. Generation and offline
|
|
2560
|
+
freshness validate the original bytes against `discovery.json` and the primary
|
|
2561
|
+
pin, then derive the conversion in memory, including reviewed summary overrides.
|
|
2562
|
+
Its digest uses two-space JSON indentation and a terminal newline; the generated
|
|
2563
|
+
module records that independent document digest, preserving freshness checks
|
|
2564
|
+
for changes to the normalizer or summaries. This supersedes Decision 0011's
|
|
2565
|
+
retained-conversion requirement for deterministic Discovery evidence. Frozen
|
|
2566
|
+
measurements read those same provider-owned originals but validate the existing
|
|
2567
|
+
`test/fixtures/google-discovery/manifest.json` digests independently: a provider
|
|
2568
|
+
pin update must fail the historical measurement rather than silently rebase it.
|
|
2569
|
+
That reviewed pin-change PR must re-measure and update the product's manifest
|
|
2570
|
+
entry and the Forms #1009 drift-check digests when applicable, or retire the
|
|
2571
|
+
measurement. Full source method inventory
|
|
2674
2572
|
and canonical source-to-relative-path mappings survive normalization. Gmail's
|
|
2675
2573
|
source `userId` becomes deployment-owned `me`; runtime paths are relative to
|
|
2676
2574
|
the existing connection root. Reserved Slides ids remain one encoded segment.
|
|
@@ -2692,13 +2590,13 @@ independent batch-kind, revision and resource guards. Google indexes explicitly
|
|
|
2692
2590
|
set `pathMatching: "uri-template"` on `OperationIndex` to handle encoded literal
|
|
2693
2591
|
collisions and parameter action suffixes. Other indexes retain exact literal
|
|
2694
2592
|
segments and their existing refusal ordering. The matching mode also binds
|
|
2695
|
-
discovery cursors.
|
|
2696
|
-
template and refuses a substituted id resolving to another operation
|
|
2697
|
-
grant evaluation.
|
|
2698
|
-
|
|
2593
|
+
discovery cursors. `googleClient(connection, index)` requires each named request's
|
|
2594
|
+
declared `template` and refuses a substituted id resolving to another operation
|
|
2595
|
+
before grant evaluation. Every maintained Google product uses this indexed
|
|
2596
|
+
client; there is no unindexed settlement mode.
|
|
2699
2597
|
Both the client and `googleHatchBinding(connection, { index, review })` require
|
|
2700
2598
|
the explicit URI-template mode at construction. The hatch requires the binding's
|
|
2701
|
-
exact index identity.
|
|
2599
|
+
exact index identity. Clients and Google bindings reject a missing
|
|
2702
2600
|
index with an explicit construction error. The provider-standard suite checks
|
|
2703
2601
|
actual hatch construction through every Google product fixture, requiring its
|
|
2704
2602
|
Google binding with the same connection and index. The Google binding
|
|
@@ -2707,7 +2605,7 @@ dispatch.
|
|
|
2707
2605
|
|
|
2708
2606
|
The generator's `allSuccessResponses: true` option unions JSON response fields
|
|
2709
2607
|
from every 2xx. Existing providers keep the first JSON success contract until
|
|
2710
|
-
their own reviewed regeneration
|
|
2608
|
+
their own reviewed regeneration.
|
|
2711
2609
|
|
|
2712
2610
|
`src/providers/_shared/google/hatch.ts` supplies JSON framing over the existing
|
|
2713
2611
|
confined `Connection.sendPath`. It retains the hatch's origin/media guards,
|
|
@@ -2734,17 +2632,16 @@ For example, a direct value-mode result has outer `result.data`, the hatch's
|
|
|
2734
2632
|
`result.data.page.nextCursor`, and vendor JSON at `result.data.data`:
|
|
2735
2633
|
`call_tool({ address: "crm.forms_api_read", args: { path:
|
|
2736
2634
|
"/forms/form_1/responses", cursor: previous.data.page.nextCursor },
|
|
2737
|
-
resultMode: "value" })`.
|
|
2738
|
-
provider, not a claim that the Forms migration has shipped.
|
|
2635
|
+
resultMode: "value" })`. Google Forms uses this continuation envelope.
|
|
2739
2636
|
|
|
2740
2637
|
`googleErrors(product, { standard: true })` declares the product's 404 meaning
|
|
2741
2638
|
and uses common status fallbacks; revision-conflict meanings require a
|
|
2742
|
-
separate declaration.
|
|
2639
|
+
separate declaration. `googleClient` preserves failure phase
|
|
2743
2640
|
metadata for partial-create recovery while leaving settlement and wording to
|
|
2744
2641
|
the kit. Its incomplete-body wording covers JSON and binary reads without
|
|
2745
|
-
claiming that binary success was expected to be JSON.
|
|
2746
|
-
|
|
2747
|
-
is
|
|
2642
|
+
claiming that binary success was expected to be JSON. `googleGrant` still uses
|
|
2643
|
+
the nonstandard `googleErrors(product)` mapping for delegated-token rejection;
|
|
2644
|
+
that grant contract is separate from resource-request settlement.
|
|
2748
2645
|
|
|
2749
2646
|
Drive's two-request reads also declare fixed steps: `get_file_content` uses
|
|
2750
2647
|
`metadata` and `content`, and non-root `list_folder_items` uses `folder` and
|
|
@@ -2755,10 +2652,8 @@ Gmail declares separate initial and body-download steps for `get_message`,
|
|
|
2755
2652
|
each of up to 25 summary reads, and `get_thread` names each stored body in
|
|
2756
2653
|
Gmail's 100-message conversation limit. Serving these reads as writes keeps
|
|
2757
2654
|
every request available once.
|
|
2758
|
-
The
|
|
2759
|
-
|
|
2760
|
-
reports how far a failed request got. The core still decides every write's
|
|
2761
|
-
outcome. Gmail's auxiliary draft and reply lookups pass both `effect: "read"`
|
|
2655
|
+
The request adapter reports how far a failed request got; the kit maps the
|
|
2656
|
+
failure and the core decides every write's outcome. Gmail's auxiliary draft and reply lookups pass both `effect: "read"`
|
|
2762
2657
|
and a construction-declared step: the guarded client's early reservation uses
|
|
2763
2658
|
that named slot, while the ledger marks the request auxiliary. A failed lookup
|
|
2764
2659
|
keeps its read verdict and cannot make an unsent draft write unknown.
|
|
@@ -2767,7 +2662,7 @@ Sheets declares its seven API methods in `src/providers/sheets/api.ts`; its
|
|
|
2767
2662
|
kit tools retain the private digest-bound cell cursor, legacy A1 path encoding,
|
|
2768
2663
|
and create/append recovery advice. Its projections and the Google failure
|
|
2769
2664
|
classifier read fields by the names Google gave them, which the kit's parse pass
|
|
2770
|
-
keeps.
|
|
2665
|
+
keeps.
|
|
2771
2666
|
|
|
2772
2667
|
Google's request adapter also offers a reviewed binary send. It marks the
|
|
2773
2668
|
operation `googleBytes` for the product's `binaryBodies` selector and forwards
|
|
@@ -2801,10 +2696,8 @@ Every defect from a run probe or its hooks uses the generic withheld notice,
|
|
|
2801
2696
|
even without a kit dispatch, because a private transport leaves no kit visibility
|
|
2802
2697
|
evidence. An open operation probe retains its original defect.
|
|
2803
2698
|
|
|
2804
|
-
|
|
2805
|
-
|
|
2806
|
-
capacity, transport, failures and result safety. It verifies schema equality
|
|
2807
|
-
before restoring legacy catalog key order. `indexedVendor` derives operation
|
|
2699
|
+
`src/providers/_shared/rest/kit.ts` owns the shared REST call shapes, pinned
|
|
2700
|
+
schema conversion and indexed vendor declarations. `indexedVendor` derives operation
|
|
2808
2701
|
metadata from the index and builds the full manifest lazily; the typed client
|
|
2809
2702
|
contains only named operations and probes. Bulk indexed declarations preserve
|
|
2810
2703
|
the OpenAPI brace paths verbatim and carry explicit parameter Schemas. They
|
|
@@ -2828,7 +2721,7 @@ transport idempotency key. These hints describe behavior; write routing and
|
|
|
2828
2721
|
endpoint restrictions still apply. For example, a tool that only creates a new
|
|
2829
2722
|
note can declare `destructive:false` without promising idempotency.
|
|
2830
2723
|
|
|
2831
|
-
|
|
2724
|
+
Kit tools and the indexed hatch may declare a `writeSteps` map whose values are `"once"`.
|
|
2832
2725
|
Construction freezes the map; every named step sends at most once and an
|
|
2833
2726
|
undeclared step is refused before dispatch. Omitting it retains the single
|
|
2834
2727
|
implicit write step. Auxiliary ownership reads in a write call retain that
|
|
@@ -2981,8 +2874,8 @@ result handling, reviewed value safety and the deployment privacy projection
|
|
|
2981
2874
|
before paging or provider projections can read it. Read methods beyond GET
|
|
2982
2875
|
and HEAD require a review. Construction fixes each write step's capacity;
|
|
2983
2876
|
the guarded transport reserves it before preparation and the shared core
|
|
2984
|
-
decides the whole call's write outcome.
|
|
2985
|
-
|
|
2877
|
+
decides the whole call's write outcome. Drive uploads use write builders over
|
|
2878
|
+
reviewed raw-body sends.
|
|
2986
2879
|
|
|
2987
2880
|
Reviewed path calls resolve their actual method and path through an indexed
|
|
2988
2881
|
safety adapter; a provider-supplied template cannot bypass the policy.
|
|
@@ -3089,10 +2982,10 @@ same version to resolve a single copy. Connecta's own lockfile and packed
|
|
|
3089
2982
|
install are checked for one copy (`test/package-surface.node.test.ts` and
|
|
3090
2983
|
`scripts/check-package.mjs`).
|
|
3091
2984
|
|
|
3092
|
-
The stable `4.0.0` release was re-evaluated on 2026-10-01 with
|
|
3093
|
-
[
|
|
3094
|
-
|
|
3095
|
-
The [raw observations](https://github.com/zackbart/connecta/blob/
|
|
2985
|
+
The stable `4.0.0` release was re-evaluated on 2026-10-01 with this
|
|
2986
|
+
[historical probe source](https://github.com/zackbart/connecta/blob/1ab92695f2636f904274d900ce209553358ff1f3/scripts/probes/effect-v4-evaluation.mjs),
|
|
2987
|
+
retained in Git history rather than the current checkout.
|
|
2988
|
+
The [raw observations](https://github.com/zackbart/connecta/blob/1ab92695f2636f904274d900ce209553358ff1f3/scripts/probes/effect-v4-evaluation-2026-10-01.json)
|
|
3096
2989
|
are synthetic Node requests and neutral esbuild bundles, not live-client or
|
|
3097
2990
|
workerd lifetime verification. Bundle figures add representative prototypes
|
|
3098
2991
|
alongside the current code; they do not claim savings from removing old code.
|
|
@@ -3101,7 +2994,7 @@ Two native input schemas with validation and JSON Schema rendering add 62,148
|
|
|
3101
2994
|
bytes gzip to the root, taking it from 303,083 to 365,231 against a 339,526
|
|
3102
2995
|
cap. Effect can reject excess properties when both decoding and rendering use
|
|
3103
2996
|
`onExcessProperty: "error"`; its default strips them. The generated schemas
|
|
3104
|
-
still differ from the
|
|
2997
|
+
still differ from the published meta-tool schemas, including record rendering and
|
|
3105
2998
|
composed numeric bounds. A Schema replacement would need to preserve that
|
|
3106
2999
|
contract and memoized rendering. Both MCP SDK packages still depend on Zod,
|
|
3107
3000
|
so changing our inputs alone does not remove Zod from an installation.
|
|
@@ -3193,7 +3086,8 @@ compiling and configuring the real thing.
|
|
|
3193
3086
|
rejections are observed; dispatch and lease guards still contain detached
|
|
3194
3087
|
work. Per-await I/O cancellation remains useful for releasing resources,
|
|
3195
3088
|
while prompt refusal is enforced at the boundary
|
|
3196
|
-
(`test/
|
|
3089
|
+
(`test/cancellation-faults.test.ts`, `test/operation-cancellation.test.ts`
|
|
3090
|
+
and `test/cancellation-journey.node.test.ts`). Invocation owns
|
|
3197
3091
|
the recovery and logical-call records it reads after teardown. Closing an
|
|
3198
3092
|
outer call also revokes nested calls paused in preparation. Request-owned
|
|
3199
3093
|
MCP sessions and token flights outlive individual calls and close with the
|
|
@@ -3286,8 +3180,9 @@ compiling and configuring the real thing.
|
|
|
3286
3180
|
at construction) and the predicate matched, which the ledger records on the
|
|
3287
3181
|
request. Only Stripe declares it (`src/providers/stripe/api.ts`, reviewed
|
|
3288
3182
|
as a `manual` check in its `drift.json`): an API v1 answer carrying Stripe's
|
|
3289
|
-
`Request-Id`.
|
|
3290
|
-
|
|
3183
|
+
`Request-Id`. The real HTTP hostile-response journey checks this refusal
|
|
3184
|
+
against an ambiguous committed write; there is no copied declaration list.
|
|
3185
|
+
Q8 is decided in one place, `settleWrite` in
|
|
3291
3186
|
`src/write-outcome.ts`, once per logical call and over every request it
|
|
3292
3187
|
recorded. The invocation calls it for every failure of a served write: a
|
|
3293
3188
|
thrown or mapped error, a custom connector's, a program's call, and its
|
|
@@ -3466,7 +3361,7 @@ compiling and configuring the real thing.
|
|
|
3466
3361
|
(`keyProtectsLogicalCall`). Every resource request dispatched under the
|
|
3467
3362
|
logical call, from any ledger, is recorded on it once per dispatch with
|
|
3468
3363
|
its method and the genuine key it carried (`ProviderRequest.key`, set by
|
|
3469
|
-
|
|
3364
|
+
the kit's guarded transport only for a key fetch sends as given). The advice stands only when
|
|
3470
3365
|
exactly one boundary was entered, the invocation's object owns it as for
|
|
3471
3366
|
`knownForLogicalCall`, that boundary tracks every request, and exactly one
|
|
3472
3367
|
dispatched request was a write, carrying the named key; a request counts as
|
|
@@ -3511,10 +3406,10 @@ compiling and configuring the real thing.
|
|
|
3511
3406
|
reconciliation even with an idempotency key; direct transport calls
|
|
3512
3407
|
without a served verdict can still prove repeatability, but only with a
|
|
3513
3408
|
genuine key sent to a vendor that honors it (Stripe today, through
|
|
3514
|
-
`
|
|
3409
|
+
`hatch.idempotency`): the REST write tool refuses an `idempotencyKey` that fetch
|
|
3515
3410
|
would send empty after trimming or would not send at all (CR, LF, NUL, any
|
|
3516
3411
|
other control character but tab, DEL, or a code point past Latin-1), as
|
|
3517
|
-
`invalid_args` before recovery is recorded, and
|
|
3412
|
+
`invalid_args` before recovery is recorded, and the guarded transport marks a request
|
|
3518
3413
|
repeatable only for a key fetch sends as given.
|
|
3519
3414
|
`providerCallFailure` (`src/write-outcome.ts`) is the one finalizer for a
|
|
3520
3415
|
direct write's failure: the `api()` handler boundary, a guarded transport
|
|
@@ -3536,29 +3431,17 @@ compiling and configuring the real thing.
|
|
|
3536
3431
|
`write_outcome_unknown`. The caller's own abort reason still passes by
|
|
3537
3432
|
identity for a read and for a served call, whose timeout passes through
|
|
3538
3433
|
unchanged for the invocation to report.
|
|
3539
|
-
|
|
3540
|
-
|
|
3541
|
-
|
|
3542
|
-
|
|
3543
|
-
|
|
3544
|
-
|
|
3545
|
-
|
|
3546
|
-
|
|
3547
|
-
|
|
3548
|
-
|
|
3549
|
-
|
|
3550
|
-
composite success followed by refusal, GitHub preflight failures, typed
|
|
3551
|
-
handler errors after successful sends, Forms cursor conflicts after 200,
|
|
3552
|
-
generic-code vendor refusals, auxiliary failures after resource dispatch,
|
|
3553
|
-
redaction of refusal errors, and concurrent direct-call ledger isolation.
|
|
3554
|
-
The round-6 cases cover a composite write's early refusal while siblings
|
|
3555
|
-
await credentials or are in flight, requests started after the call ended,
|
|
3556
|
-
connect-phase errnos with each body kind (all unknown for a write, and a
|
|
3557
|
-
direct read stays retryable), a request aborted with a refusal-shaped
|
|
3558
|
-
reason, an errno outside fetch's network error, and
|
|
3559
|
-
undeclared handlers whose untracked send precedes a typed failure. Each
|
|
3560
|
-
catalog case also checks that the ledger recorded every resource request
|
|
3561
|
-
the network saw, and the inventory that every API connector declares it.
|
|
3434
|
+
Shared provider outcomes and the real HTTP hostile-response journey check
|
|
3435
|
+
returned data, failure/recovery, privacy and physical writes without a
|
|
3436
|
+
catalog-wide status matrix. `test/provider-failure-sweep.test.ts` retains
|
|
3437
|
+
fault probes for Docs creation with initial text, composite success followed
|
|
3438
|
+
by refusal, GitHub preflight failures, typed handler errors after successful
|
|
3439
|
+
sends, Forms cursor conflicts after 200, generic-code vendor refusals,
|
|
3440
|
+
auxiliary failures after resource dispatch and concurrent direct-call isolation.
|
|
3441
|
+
It also holds siblings awaiting credentials or already in flight when another
|
|
3442
|
+
write fails, refuses requests after call closure, and probes network errors,
|
|
3443
|
+
refusal-shaped abort reasons and untracked sends. Native transport and
|
|
3444
|
+
request-lifetime suites retain their platform-specific evidence.
|
|
3562
3445
|
`test/write-evidence.test.ts` uses real refused, reset, and held sockets on
|
|
3563
3446
|
both runtimes: a refused write is unknown and a refused read retryable,
|
|
3564
3447
|
including a write aborted with another fetch's real refusal as its reason
|
|
@@ -3831,7 +3714,7 @@ and workerd. `remote-mcp-native-bundle.node.test.ts` additionally loads an actua
|
|
|
3831
3714
|
minified production bundle to verify call/cache registration, request Context,
|
|
3832
3715
|
native storage, saved-original delegates, custom replacements and closed-owner
|
|
3833
3716
|
refusal. Existing wire, physical-attempt, cache and OAuth lifetime suites remain
|
|
3834
|
-
the compatibility evidence
|
|
3717
|
+
the compatibility evidence.
|
|
3835
3718
|
|
|
3836
3719
|
### Native upward MCP orchestration (contributor)
|
|
3837
3720
|
|