Replace the final-snapshot-only shared-state-streaming behavior with a
write_document tool whose document arg streams; per-token state.document
emission is bridged on the copilotkit route (see the routing commit).
harness-control-plane and harness-pool-worker both declared a build: block
AND the same image: showcase-harness:local. Under the parallel docker buildx
bake path (default in recent Docker Compose) both targets build and race to
tag the identical image, failing the whole 'bin/showcase up' with
'image "...showcase-harness:local": already exists'. It only surfaces on a
cold parallel bake build (Colima/Homebrew, fresh clone), which is why it is
intermittent across toolchains.
Give the image a single build owner: harness-pool-worker now reuses the
image built by harness-control-plane (worker vs control-plane role is chosen
at runtime via HARNESS_ROLE) instead of declaring its own build:.
Task 1 of OSS-582 (frontend parity). Bring the app chrome + beautiful-chat
byte-identical to the langgraph-python north star:
- globals.css: adopt LGP theme (@theme inline tokens + green palette)
- middleware.ts: add (was missing) — sets x-pathname like LGP
- layout.tsx: adopt LGP structure; keep FastAPI in title/log (identity carve-out)
- beautiful-chat/page.tsx: sync stale doc comment
Also fix a Dockerfile parity gap: fastapi was missing the COPY manifest.yaml
that LGP has. demos/layout.tsx reads manifest.yaml at request time via
generateMetadata (headers() -> dynamic), so without it every /demos/* route
crashed with an RSC render error (ENOENT /app/manifest.yaml).
## What
Fixes multi-turn chat on every mastra showcase demo, which 400s on the
2nd turn:
> `AI_APICallError: Invalid 'input[3].id': 'msg-92Y7BhMpWBhXt7dm'.
Expected an ID that contains letters, numbers, underscores, or dashes,
but this value contained additional characters.` (`INCOMPLETE_STREAM`)
## Root cause
OpenAI's Responses API actually **rejects dashes** in `input[].id`. Its
400 message misleadingly lists dashes as allowed, but empirically only
`[A-Za-z0-9_]` is accepted:
| `input[].id` | result |
|---|---|
| *(omitted)* | ✅ 200 |
| `msg_92Y7BhMpWBhXt7dm` (underscore) | ✅ 200 |
| `msg-92Y7BhMpWBhXt7dm` (**the failing client id**) | ❌ 400 |
CopilotKit mints message ids like `msg-…`, and `@ag-ui/mastra` + the AI
SDK forward them straight into `input[].id` when replaying prior-turn
history — so turn 1 works (no prior ids) and every turn after dies.
## Fix
The mastra provider already routes every outbound LLM call through
`forwardingFetch` (the header-forwarding shim). This rewrites dashes
(and any other non-`[A-Za-z0-9_]` char) in each outbound `input[].id` to
`_` there.
**Why here, not in the bridge's message conversion:** it touches only
the bytes sent to OpenAI. Mastra's in-memory `CoreMessage.id` — which
drives its upsert-by-id history **dedup** — is untouched, so dedup is
unaffected. OpenAI-issued ids (`msg_…`, `rs_…`, no dashes) pass through
unchanged, preserving server-side conversation-state references. Chat
Completions bodies (no `input[]` array) are untouched.
This **supersedes ag-ui-protocol/ag-ui#2227** — a bridge-layer charset
munge that *kept* dashes (`[^A-Za-z0-9_-] → -`), making it a no-op on
the real failing ids. That PR is being reverted.
## Tests
`tests/vitest/header-forwarding-id-sanitize.test.ts` — 8 cases: the real
failing id, valid-id no-op, full-charset mapping, in-body rewrite,
no-op/passthrough, and chat-completions-untouched. All green.
## Verification status
- ✅ Transform verified against the exact failing id; `msg_…` form
confirmed accepted by the real OpenAI Responses API.
- ✅ 8 unit tests pass in-module.
- ⚠️ Full end-to-end wasn't run locally (the showcase runtime OOMs a 16
GB box), but **every** showcase OpenAI call flows through this wrapper,
so **staging is the final check** — deploy and re-run a two-click
multi-turn on `/demos/agentic-chat`.
## Refs
- Linear **OSS-381** (mastra refresh umbrella).
- Supersedes ag-ui-protocol/ag-ui#2227 (revert incoming).
- Follow-up worth filing upstream: `@ag-ui/mastra` / AI SDK shouldn't
forward non-provider message ids into `input[].id` at all.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
## What
Two mastra showcase D6 follow-ups to #5798 (v1 bridge alpha). Both cells
went red the moment #5798 took them out of `not_supported_features` —
they were claimed supported before actually passing. **Neither is a
v1-bridge streaming regression.**
## Commits
**1. gen-ui-agent completes all 3 steps (raise step cap)** — `57afed6dd`
"Generative UI: Agent State" (gen-ui-agent) stalled at 2/3 steps:
`genUiAgent` set no stop condition, so the AI SDK default halted the
agentic loop before the 3rd step completed. Adds
`defaultOptions.stopWhen = stepCountIs(12)`. Verified 6/6 on the Node-22
+ `next start` + aimock replay rig; tool-rendering / gen-ui-tool-based
unaffected.
**2. useComponent (gen-ui-tool-based) — probe took the wrong path** —
`4640d6304`
The D5 `gen-ui-custom` probe omitted `mastra` from `CHART_INTEGRATIONS`,
so it sent the *haiku* prompt and hunted for a haiku card. mastra's demo
is the LGP-style `useComponent` chart demo (`render_pie_chart` /
`render_bar_chart`) with no haiku tool, so the assistant bubble came
back empty (*"haiku card [data-testid=copilot-assistant-message]
rendered but has no text content"*).
- Add `"mastra"` to `CHART_INTEGRATIONS`.
- Add `aimock/d6/mastra/gen-ui-custom.json` (mirrors langgraph-python;
identical pie schema `{title, description, data:[{label,value}]}`) so
the cell is deterministic under replay instead of falling through to the
live upstream.
- Repoint the probe unit test's haiku-empty-card case from `"mastra"` →
`"agno"` (a genuine haiku integration).
## Verification
- gen-ui-agent: 6/6 on the faithful rig.
- useComponent: logic-only harness + fixture changes; harness unit tests
run in CI (sparse local checkout has no vitest).
## Refs
- Follow-on to #5798. Linear **OSS-381** (mastra refresh umbrella).
- Companion `@ag-ui/mastra` PR — multi-turn Responses-API message-id 400
fix: ag-ui-protocol/ag-ui#2227.
- Sibling from the same triage (separate, not fixed here): **PNI-100** —
hitl-in-app follow-up-run gap.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
- a2ui-recovery: add opt-in createA2UIRecoveryAgent() — generate_a2ui runs a
validate->retry loop and, once the attempt cap is hit with only invalid
surfaces, returns the { code: 'a2ui_recovery_exhausted', error, attempts }
envelope the A2UI middleware paints as the graceful failure card. Wired only
into the a2ui-recovery route; createDeclarativeGenUIAgent behavior unchanged.
D6 EXHAUST turn now green.
- multimodal: add opt-in createMultimodalAgent() that flattens PDF document
parts to text server-side via unpdf (TS equivalent of LGP's pypdf) through a
new opt-in preprocessMessages hook on createBuiltInAgent (default pass-through,
other demos byte-identical). D6 PDF turn now green.
- deps: add unpdf for server-side PDF text extraction.
Both fixes opt-in; shared factory defaults unchanged. next build + Docker
rebuild + D6 probes all green.
Diffs an integration's frontend surface (all src/** UI files except
src/agents/** and src/app/api/**, tests, qa) against a reference
integration (default langgraph-python) byte-for-byte, normalizing
integration identity (manifest name/slug) so name-only differences
report as IDENTITY rather than DRIFT. Exits 0 when the frontend is
byte-identical modulo the integration's own name. Supports --md
(markdown audit), --full, --all (fleet ranking), --verbose, --ref.
Complements the structural-only validate-parity.ts. Zero-dependency;
runs on node 23+ directly or via tsx.
- shared-state-read: remove spurious turnIndex:0 on the turn-2 fixture entry
(turnIndex counts assistant msgs = 1 on turn 2, so the constraint could never
match -> turn 2 dom-missing). Now D6 GREEN.
- a2ui-recovery: register built-in-agent heal/exhaust prompts in the shared
probe PROMPTS (new demo BIA lacked) + add its aimock fixture. HEAL turn now
GREEN; EXHAUST still red pending a backend factory change (emit the
a2ui_recovery_exhausted envelope) — tracked, not fixable at fixture layer.
- multimodal: fix conversation-runner skipSend baseline (snapshot run-start
BEFORE preFill, since preFill issues the run on skipSend turns; fast
in-process runtimes else false-red done-signal-missing). Image turn now
GREEN; PDF turn still red (BIA runtime has no document/PDF flattening path).
NOTE: conversation-runner.ts is a SHARED harness helper — change is guarded to
skipSend turns (non-skipSend byte-identical) and only corrects the baseline;
flagged for harness-owner review.
BIA's globals.css was a 17-line stub missing LGP's @theme inline Tailwind-v4
token map + the :root design-token palette (--background/--card/--primary/
--muted/--accent/--radius + CopilotKit brand vars). Without it every shadcn /
AI-Elements / prompt-kit primitive fell back to unstyled — most visible on
beautiful-chat. Copy LGP's globals.css verbatim so the byte-identical demo
frontends render with the correct theme.
Multi-turn chat on every mastra demo fails on the 2nd turn:
AI_APICallError: Invalid 'input[3].id': 'msg-92Y7BhMpWBhXt7dm'.
Expected an ID that contains letters, numbers, underscores, or dashes,
but this value contained additional characters. (code: INCOMPLETE_STREAM)
Root cause: OpenAI's Responses API actually REJECTS dashes in `input[].id`
(its 400 message misleadingly lists dashes as allowed — empirically only
`[A-Za-z0-9_]` is accepted; `msg-92Y7…` 400s, `msg_92Y7…` succeeds).
CopilotKit mints message ids like `msg-…`, and @ag-ui/mastra + the AI SDK
forward them straight into `input[].id` when replaying prior-turn history, so
the whole request fails. Turn 1 works (no prior ids); every turn after dies.
Fix at the HTTP boundary: the mastra provider already routes every outbound
LLM call through `forwardingFetch` (header-forwarding shim). Rewrite dashes
(and any other non-`[A-Za-z0-9_]` char) in each outbound `input[].id` to `_`
there.
Why here and not in the @ag-ui/mastra message conversion: this touches ONLY
the bytes sent to OpenAI. Mastra's in-memory `CoreMessage.id` — which drives
its upsert-by-id history dedup — is left untouched, so dedup is unaffected.
OpenAI-issued ids (`msg_…`, `rs_…`) contain no dashes and pass through
unchanged, preserving server-side conversation-state references. Chat
Completions bodies (no `input[]` array) are untouched.
Supersedes the ineffective ag-ui-protocol/ag-ui#2227 (a bridge-layer charset
munge that kept dashes — a no-op on the real failing ids; being reverted).
Tests: tests/vitest/header-forwarding-id-sanitize.test.ts (8 cases — the real
failing id, valid-id no-op, full-charset mapping, body rewrite, no-op/passthrough,
chat-completions untouched). All green.
--no-verify: sparse showcase checkout has no monorepo lefthook/commitlint binaries.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
## What
Adds a **"Show unique"** filter to the Showcase Dashboard feature grid,
mirroring the existing **"Show deprecated"** toggle. A demo is
**common** when ≥ 2 frameworks ship it; single-framework (and
zero-framework) demos are **unique**.
Both toggles default **OFF**, so the default view is **common ∩
non-deprecated** — the cross-framework gold-standard surface. Each
toggle independently widens the set (AND-combined).
This makes room for framework-specific demos (e.g. the planned Mastra
browser-use / observational-memory demos): once added they'll be hidden
by default and revealed via "Show unique".
## Why the "ships a demo" signal
"Framework supports a demo" is defined as `integration.demos.some(d =>
d.id === feature.id)` (the grid's existing `isWired` signal). The two
alternatives were rejected:
- `integration.features[]` — stale in the data (e.g.
`interrupt-headless` has demos in ~19 integrations but 0 `features[]`
declarations).
- `not_supported_features` — a brand-new single-framework demo never
appears in another integration's `not_supported_features`, so it would
be wrongly classified as common. This is exactly the Mastra case that
motivated the feature.
## UI
- `Show unique (N)` checkbox next to `Show deprecated`, rendered only
when `N > 0`. Tooltip: "N demos supported by fewer than two frameworks —
hidden by default…".
- Subtitle shows the **exact distinct hidden-row count** — `(N hidden)`
— rather than an additive per-category breakdown (a feature can be both
deprecated and unique; the per-category badges provide attribution,
faceted-filter style).
## Testing
- 6 new behavioral tests in `feature-grid.test.tsx` (default-hidden,
reveal-on-toggle, count label, accurate tooltip wording, exact distinct
subtitle count, note-drop when both filters enabled). Suite: **37/37
green**.
- `tsc --noEmit` clean; `oxlint` clean (on the changed files); `next
build` succeeds.
## Notes / follow-up
- **Column-header tallies** count the full matrix regardless of
row-visibility filters. This is pre-existing (unchanged by this PR) and
arguably correct-by-design (a coverage metric over the whole matrix, per
the `computeColumnTally` docstring). Flagged in review, deferred.
- The "unique" count uses `frameworkCount < 2`, intentionally grouping
zero-demo features with single-framework ones (approved design
decision); tooltip wording reflects this.
## Scope
Client-side view state only — no registry, catalog, props, or SSE
changes; all edits internal to `FeatureGrid`.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Per-category subtitle counts overlapped (a feature can be both deprecated
and unique), overstating hidden rows. Show the distinct total instead;
per-category counts remain on the toggle badges. CR round 1 finding F2.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Tooltip said 'only one framework' but uniqueCount is frameworkCount<2,
which includes zero-framework demos. CR round 1 finding F3.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Hides single-framework (non-common) demo rows by default, mirroring the
Show deprecated toggle. Common = shipped by >=2 frameworks (demos[]).
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Both were suspected downstream-host RED; per-demo probes against a context-scoped
aimock confirm GREEN. declarative-gen-ui: cross-slug shadowing was the sole cause
(a2ui-fixed-schema passes on the same host). mcp-apps: fixed via the create_view
elements JSON-string fixture correction. Update manifest note + PARITY_NOTES to
the resolved state.
Excalidraw's MCP create_view tool declares `elements` as a string (JSON-encoded
array) in its inputSchema; the fixtures emitted a raw JSON array. BIA declares
the injected MCP tool locally via jsonSchemaToZod -> z.string(), so the array
failed input validation, the tool never executed against excalidraw, no
ACTIVITY_SNAPSHOT fired, and the MCP Apps iframe never mounted (D6 red).
Stringify the elements arg to match the inputSchema. Verified D6 green.
Same latent fix applied to the flowchart pill in mcp-apps.json.
The byte-identical open-gen-ui-advanced frontend carries the
sandbox-function-registration @region in both page.tsx and
sandbox-functions.ts (verbatim from LGP, which is already allowlisted).
Add the built-in-agent allowlist entry so bundle-demo-content passes —
unblocks Validate Showcase + the shell/shell-docs/shell-dojo build-checks
(all run the bundler).
Copy every langgraph-python demo frontend verbatim into built-in-agent
(diff -r clean across all 42 demo dirs), plus the shared shadcn UI
(src/components/ui, 25 primitives) and src/lib/utils, all byte-identical
to LGP. Adds the 5 demos BIA was missing (a2ui-recovery, declarative-
hashbrown, declarative-json-render, shared-state-read, threadid-frontend-
tool-roundtrip) and removes the orphaned _components dir.
Adds the frontend deps the copied UI requires (radix-ui, react-checkbox,
react-separator, cmdk, embla-carousel-react, react-markdown, remark-gfm,
yaml) and syncs package-lock. next build compiles clean.
Backend named-agent wiring + D6 parity follow in subsequent commits.
Establish the named-agent registry pattern for LGP parity:
- agentic-chat frontend copied byte-identical from langgraph-python
(diff -r clean); removes the BIA-bespoke setBackground variant.
- New createAgenticChatAgent() (prompt-only, LGP system prompt) registered
as the named agent 'agentic_chat'; the runtime resolves agent="agentic_chat"
against the agents map (cloneAgentForRequest -> resolveAgents).
- Fix gpt-4o -> gpt-5.5 in the shared tanstack factory (house rule).
Proven: bin/showcase test built-in-agent:agentic-chat --d6 --direct -> green.
## What
Fixes three broken **Built-in Agent** showcase demos by forwarding the
tools that runtime middleware injects into `input.tools`. The in-process
TanStack factories were dropping them with `tools: []`.
- **open-gen-ui** — agent now calls `generateSandboxedUi` (was emitting
the UI as a raw HTML code block)
- **open-gen-ui-advanced** — same factory/route; the sandbox → host
callbacks can now engage
- **mcp-apps** — agent now sees `create_view` and can render the
Excalidraw view (was replying with plain text)
## Why
`OpenGenerativeUIMiddleware` / `MCPAppsMiddleware` inject their tool
into `input.tools` at request time. The working main
`tanstack-factory.ts` forwards `input.tools` into `chat({ tools })`, but
`ogui-factory.ts` and `mcp-apps-factory.ts` hard-coded `tools: []` — so
the model never received the tool and fell back to prose/HTML. This is
exactly why the demos look broken on the **live Railway deploy** (real
LLM): given no tool, a real model just prints the UI as text.
## How
Declare the injected tools via `toolDefinition()` — the same pattern the
main factory already uses — and `export` its `jsonSchemaToZod` helper
for reuse (no duplication).
Note: `convertInputToTanStackAI(input).tools` would be simpler, but that
return field only exists in `@copilotkit/runtime >= 1.61.0`. This app
pins **1.60.2**, so the `toolDefinition()` route is the version-safe
fix.
## Verification
- ✅ `tsc --noEmit` against the pinned `@copilotkit/runtime@1.60.2` — the
three changed files are type-clean. (The app has pre-existing, unrelated
zod-version-skew tsc errors in the A2UI catalog files; those are on
`main` and untouched here.)
- ⚠️ **D5/D6 aimock replay was NOT run** — no Docker in my environment.
Needs a CI / Docker-capable run to confirm the demos render.
- ⚠️ **Fixtures may need re-recording.** The aimock fixtures for
`gen-ui-open`, `gen-ui-open-advanced`, and `mcp-apps` (built-in-agent)
may have been captured in the broken (no-tool-call) state; if so, replay
won't demonstrate the fix until they're re-recorded against a real LLM
(showcase Procedure 3). Please confirm the D5/D6 run and re-record if
needed.
## Follow-ups
- After merge, **redeploy the built-in-agent Railway service** so the
live showcase reflects the fix.
- P0 slice of the broader **OSS-594** parity effort; structural drift +
runtime-capability gaps are tracked in that ticket.
Refs OSS-594.
## What
The built-in-agent **prebuilt-sidebar** and **prebuilt-popup** demos
each rendered a single hard-coded "Say hi" suggestion pill, even though
a correct 3-pill hook (`usePrebuiltSidebarSuggestions` /
`usePrebuiltPopupSuggestions`, byte-identical to `langgraph-python`)
already lived in each demo's own `suggestions.ts` — just never imported.
This wires the existing hooks so the pills match canonical:
- **prebuilt-sidebar**: Say hi · Fun fact · Is 17 prime?
- **prebuilt-popup**: Say hi · Limerick · Is 17 prime?
## Why
Classic scaffold-then-drift: the flavor was copied from canonical
(bringing the `suggestions.ts` hook along) but each `page.tsx` was
hand-written with a degraded inline single-pill version and never wired
back. Part of the **OSS-594** P1a "orphaned suggestions" cleanup.
## How
Call the existing hook from each `page.tsx` and drop the now-unused
`useConfigureSuggestions` import. No new files; the only behavior change
is the suggestion set.
## Verification
- lefthook (`oxlint` + `oxfmt`) clean on commit.
- Leans on CI `build-check (built-in-agent…)` + `check-types` — both
green on the sibling P0 PR #6100 for the same app.
- 6 insertions / 18 deletions across 2 files.
Refs OSS-594.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Both demos hard-coded a single inline "Say hi" pill while their own
`usePrebuiltSidebarSuggestions` / `usePrebuiltPopupSuggestions` hooks (3 pills each,
byte-identical to langgraph-python) sat unused. Call the existing hooks so the pills
match canonical, and drop the now-unused `useConfigureSuggestions` import.
Refs OSS-594.
The OGUI and MCP-Apps factories built the in-process TanStack agent with `tools: []`,
discarding the tools the runtime middleware injects into `input.tools`
(`generateSandboxedUi` for Open Generative UI, `create_view` for MCP Apps). The model
never saw the tool, so it emitted the UI as raw HTML/text instead of a tool call — no
sandboxed iframe / MCP view rendered.
Declare the injected tools via `toolDefinition()` (the pattern the working main
tanstack-factory already uses), exporting its `jsonSchemaToZod` helper for reuse. The
converter's own `tools` return only exists in @copilotkit/runtime >= 1.61.0; this app
pins 1.60.2. Fixes open-gen-ui, open-gen-ui-advanced, mcp-apps.
Refs OSS-594.
The "Generative UI: useComponent" cell (gen-ui-tool-based) went red on mastra
the moment OSS-381 took it out of not_supported: the D5 gen-ui-custom probe
sent the *haiku* prompt and hunted for a haiku card, but mastra's demo is the
LGP-style `useComponent` chart demo (render_pie_chart / render_bar_chart) with
no haiku tool — so the assistant bubble came back empty ("haiku card
[data-testid=copilot-assistant-message] rendered but has no text content").
Root cause: the probe's CHART_INTEGRATIONS allowlist in
harness/src/probes/scripts/d5-gen-ui-custom.ts omitted mastra, so
isChartIntegration("mastra") was false and it took the haiku branch. mastra's
gen-ui-tool-based page registers render_pie_chart / render_bar_chart via
useComponent exactly like langgraph-python and google-adk.
- Add "mastra" to CHART_INTEGRATIONS so the probe sends the pie-chart prompt
and asserts the donut SVG + "pie"/"chart" follow-up tokens.
- Add aimock/d6/mastra/gen-ui-custom.json (mirrors langgraph-python's, context:
mastra; the pie schema is identical — {title, description, data:[{label,value}]})
so the cell is deterministic under aimock replay instead of falling through to
the live upstream.
- Repoint the probe unit test's haiku-empty-card case from "mastra" to "agno"
(a genuine haiku integration) now that mastra is a chart integration.
Not a v1-bridge streaming regression — a harness/fixture gap exposed when the
cell was un-suppressed. Harness unit tests not run locally (sparse showcase
checkout has no vitest); logic-only changes.
--no-verify: sparse showcase checkout has no monorepo lefthook/commitlint binaries.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The "Generative UI: Agent State" cell (gen-ui-agent) was stuck at D4 — the
d5-single-pill e2e ("marks every step as completed") failed with only 2/3 steps
reaching "completed", which blocks D6.
Root cause: the planner scripts 3 steps × 2 set_steps transitions (in_progress →
completed) + 1 initial "all pending" call + 1 closing message (~8 model turns),
but genUiAgent set no stop condition, so the AI SDK's default halted the agentic
loop before the 3rd step completed. (LangGraph gold loops until the graph ends
and needs no equivalent; this is the AI-SDK step-cap analogue — cf.
toolRenderingAgent's d20 sequence.)
Add defaultOptions.stopWhen = stepCountIs(12) to genUiAgent so the full
progression runs to completion.
Verified on the faithful rig (Node 22 + next build/start + aimock 1.37.4 replay):
gen-ui-agent.spec 6/6; tool-rendering 6/6 and gen-ui-tool-based 4/4 unchanged
(no regression). Isolated to genUiAgent — no other agent/demo affected.
--no-verify: sparse showcase checkout has no monorepo lefthook/commitlint binaries.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
## Mastra Partner Refresh — showcase finalization (OSS-381)
Bumps the showcase Mastra integration onto the **v1 bridge alpha** and
flips the
features it unblocks out of `not_supported`. Opened for CI to run the
D6/e2e
suite (local Docker daemon is wedged in the authoring env — see notes).
### Landed
- **OSS-382 (gate):** `@ag-ui/mastra` `0.2.1-beta.2` →
**`1.1.0-alpha.0`**.
- Alpha verified to ship all features (grep on dist):
`emitInterruptOutcome`,
`STATE_DELTA`, `observationalMemory`, `background-task`,
`tracingOptions`,
`getA2UITools`/recovery. Peers satisfied (`@mastra/core` 1.41,
`client-js`
1.23.2, runtime 1.61.2).
- `next build` passes (40 routes). Unit tests **identical to the beta.2
baseline** (13 pre-existing failures in `route.test.ts`'s error-path
mocks,
unrelated to the bump — proven by a stash+reinstall A/B).
- **OSS-384 / OSS-423:** moved into `features` (demos + e2e + aimock
fixtures
were already wired, gated on this release):
`agentic-chat-reasoning`, `reasoning-default-render`,
`tool-rendering-reasoning-chain`, `shared-state-streaming`. Added the
missing
`reasoning-default` / `reasoning-custom` manifest demo entries.
- **Parity:** `not_supported_features` now holds only `gen-ui-interrupt`
+
`interrupt-headless`, matching the **langgraph-python gold standard**,
which
quarantines the same two cells on an upstream `@copilotkit/react-core`
v2
resume-path hook bug (published-package fix, out of scope). The native
interrupt + RUN_FINISHED-outcome path ships in the bridge; the showcase
cell
is blocked by the same upstream bug, not the bridge.
- **OSS-424:** execution-tracing note (`tracingOptions` in / `traceId`
on
`RUN_FINISHED.result` out) added to the Mastra Copilot Runtime doc.
- **OSS-425:** GenUI `generative_ui` spectrum already at parity with
gold
(`constrained-explicit`, `a2ui-fixed-schema`, `a2ui-dynamic-schema`).
### Not in this PR (scoped, blocked, or pending)
- **OSS-422 a2ui-recovery**, **OSS-426 background-agents**, **OSS-427
observational-memory** — new demo cells. Reference material + build
plans
ready. OM additionally needs `@mastra/memory` ≥1.21.2 (repo pins
`1.0.1-alpha.1`; the on-stream async-buffering path won't fire below
that).
- **OSS-91 browser-use** — Mastra-only, non-deterministic (no clean
aimock
replay), needs a Browserbase key not present in the env. Blocked.
- **OSS-392 input.context** — owner exception; only if langgraph
showcases it.
### Verification note
Local D6 could not be run: the Docker daemon's container-creation path
is wedged
in this environment (a trivial `hello-world` create hangs), and
unwedging needs a
Docker Desktop restart that would destroy a concurrent session's running
stack.
Relying on CI for D6/e2e. Everything above is build-level verified +
committed.