feat(embed): add the TypeScript router + conformance suite - #14
feat(embed): add the TypeScript router + conformance suite#14mattj-monad wants to merge 2 commits into
Conversation
fbb2e38 to
2cd9b48
Compare
044e201 to
34ceccc
Compare
|
Force-pushed review fixes (TS router + conformance):
|
34ceccc to
1cb65e7
Compare
|
Force-pushed: 404/409 are now real implementation, not deferred. The router translates Monad's upstream status into the contract's error model — |
1cb65e7 to
5f893f2
Compare
|
Force-pushed: hardened the conformance mock. The connectors-list mock now returns Monad's real envelope shape — |
5f893f2 to
55e229f
Compare
|
Force-pushed: extended the mock hardening. The connectors mock now also returns the list as |
Adds @monad-inc/embed-server — a zero-runtime-dependency /embed router that mounts into Express or bare Node http via createEmbedRouter (core logic + node adapter + Monad API adapter) — and the language-agnostic conformance suite that proves any backend satisfies the contract over HTTP: - conformance/ — Schemathesis response-conformance across all 9 routes plus scripted lifecycle scenarios (mint -> build -> status -> disable -> remove, and egress), driven against a stateful in-memory mock Monad. The harness boots the router under test as a subprocess (ROUTER=ts|go|python); only the ts server ships here — go/python servers land with their router layers. - A CI "Conformance (ts)" job builds the router and runs ROUTER=ts. From here, conformance is the required gate every later router PR must pass. Also ignores the Python harness .venv in prettier and formats two source files that weren't prettier-clean. Local: TS router 13 tests + conformance 14 checks green (ROUTER=ts); full typecheck / lint / format / build clean. Layer 3 (PRO-402), stacked on the browser client (PRO-401). Co-Authored-By: Claude Opus 4.8 <[email protected]> Claude-Session: https://claude.ai/code/session_011ASKA2VrufrNLGGrcFjY7n
55e229f to
2f59032
Compare
|
Force-pushed: fully aligned the conformance mock with the real Monad API (read from its OpenAPI in
Finding: the routers are mostly defensively written (they already handle both the old simplified shapes and the real ones — bare-array-or- |
…idelity Adds a live conformance mode (MONAD_LIVE=1) that boots the router against the real Monad API instead of the mock, driven by env-configurable credentials/org/ provisioned ids (all defaulting to the mock fixtures, so the hermetic run is unchanged). Schemathesis is restricted to read-only GET operations in live mode. Adds test_mock_fidelity.py + monad_schemas.py, which validate every mock response against the Monad response shapes the routers consume — pinning the mock to the documented upstream contract (needs jsonschema). Co-Authored-By: Claude Opus 4.8 <[email protected]> Claude-Session: https://claude.ai/code/session_011ASKA2VrufrNLGGrcFjY7n
andrewc-monad
left a comment
There was a problem hiding this comment.
I have a few questions & comments about this new stuff:
- If the conformance stuff is to be run only as validation, like during a CI run for each router implementation, can we move the folder into a
testfolder and make it more explicit that this part of the repo isn't something that a consumer of theembedpackage would need to worry about? - The root of the
embedrepo is the "workspace" for all packages in this repo, including@monad-inc/embedwhich is the existing embedded UI frontend withcreateConnectorFrame.- I think it makes more sense to have the new
@monad-inc/embed-servermoved to thepackages/folder in this repo as its own package, and then it can be exported under a subpath just like the pieces ofpackages/embed. I think this makes it so both client-side (createConnectorFrame, etc) and the server-side (the TS router), are both exported and available in a single package. - Doing it this way I think makes it more explicit that we want our customers who use this package to build their embedded UIs to use the server-side pieces we provide.
- I think it makes more sense to have the new
For the python & go versions, is it OK to push those to later? having those go out increases the surface area of what we have to support, and especially for python, even though we don't use it a lot at Monad, we'd be expected to be able to help end-users using embed to get it integrated.
Layer 3 of the Monad Embed SDK staged rollout (PRO-402). Stacked on #13 (PRO-401) — targets
feature/pro-401; review/merge the stack bottom-up.What this adds
@monad-inc/embed-server— a zero-runtime-dependency/embedrouter that mounts into Express or bare NodehttpviacreateEmbedRouter(core logic + node adapter + Monad API adapter). 13 unit tests.conformance/— the language-agnostic suite that proves any backend satisfies the contract over HTTP: Schemathesis response-conformance across all 9 routes + scripted lifecycle scenarios (mint → build → status → disable → remove, and egress), driven against a stateful in-memory mock Monad. It boots the router under test as a subprocess (ROUTER=ts|go|python); only the ts server ships here — the go/python servers land with their router layers.ROUTER=ts. From here, conformance is the required gate every later router PR must pass.Conformance runner stays Python (Schemathesis)
We considered moving it to Node to keep the shared gate on one runtime, but kept Schemathesis: it's the canonical tool for cross-language OpenAPI conformance, there's no mature 3.1 Node equivalent (Dredd/jest-openapi are 3.0-oriented), so Node would mean owning ~100 lines of validation glue — the opposite of low-maintenance. Python is already a shipped router (PRO-404), and conformance is a CI gate, so contributors rarely need Python locally.
Also
.venvin Prettier (mirrors the eslint ignore) and formatted two source files that weren't Prettier-clean on the source branch.Verification (local)
ROUTER=ts); full typecheck / lint / format / build clean.Stack
400 → 401 → 402 → 403 (Go) → 404 (Python) → 405 (docs/CI). Go and Python will generalize the conformance CI job to a matrix.
🤖 Generated with Claude Code
https://claude.ai/code/session_011ASKA2VrufrNLGGrcFjY7n