scripts/self-learning-smoke.mjs proves the banking demo's recording seam
end-to-end against a running Intelligence backend: posts four teaching
actions through the demo BFF /api/copilotkit/annotate (the platform
requires UUID clientEventIds), optionally runs one sl-worker sweep when
INTELLIGENCE_REPO is set, and asserts the distilled vendor policy reads
back through the platform /mcp knowledge tool. Wired as the
test:self-learning package script and documented in the README.
Verified live: PASS 6/6 against Intelligence @ mme/learn-from-user-activity
(records as rows 13-16, sweep editCount=0 steady-state, recall returns the
pre-cleared vendor policy).
next lint was removed in Next 16, so the demo's lint script failed before
linting anything. Switch to eslint . with a flat eslint.config.mjs built on
eslint-config-next's native flat exports (same shape as the other Next 16
example apps), and fix the findings the new react-hooks rules surfaced:
- actions.ts / team/actions.ts: wrap mount fetches in an async IIFE so
set-state-in-effect can see the setState calls are asynchronous
- auth-context: derive currentUser from selection ?? team[0] instead of
syncing state in an effect
- use-theme: lazy-init theme from localStorage (SSR-guarded) and apply the
DOM class in an effect keyed on theme; hoist applyTheme to module scope
- threads-drawer: copy timeout maps to locals inside the effect so cleanup
does not read refs that may have changed
The 'Known gap' section predated the recording fix: the hook exists as
useLearnFromUserActionInCurrentThread and record-user-action.ts is now a
real adapter. Document the /annotate flow and the backend route
requirement (/connector/annotate) instead.
Dashboard, copilot chat panel, and the learning-mode recording vignette
(the violet glow shown while an officer demonstration is being recorded).
PNGs are LFS-tracked per the repo .gitattributes.
Replace the no-op recorder shim with a real adapter over the v2 hook
(renamed from useRecordUserActionInCurrentThread in #4839/#5073): call-site
{title, description, previousData, newData, metadata} maps to the hook's
{title, description, data: {previous, next, metadata}}, with threadId
sourced from the surrounding chat config provider.
Add an optional INTELLIGENCE_USER_ID / INTELLIGENCE_USER_NAME override to
identifyUser for backends that enforce org membership of the asserted user
(e.g. a local Intelligence stack with seeded fixture users); the default
remains the derived northwind-<role> identity. Documented in the README.
Verified end-to-end against Intelligence @ mme/learn-from-user-activity
(PUT /connector/annotate): record -> cpki.sl_annotations -> sl-worker
distill -> /project knowledge file -> recall via /mcp. Recording requires a
backend that exposes /connector/annotate; the OSS default path
(InMemoryAgentRunner, no INTELLIGENCE_* env) is unchanged.
@copilotkit/runtime@1.59.5 declares @ai-sdk/mcp ^1.0.21; fresh installs
resolve 1.0.47, whose MCP client assigns transport.protocolVersion after
the server's initialize response — a getter-only property on
@modelcontextprotocol/sdk@1.29.0's StreamableHTTPClientTransport. Every
MCP-enabled run then fails with:
TypeError: Cannot set property protocolVersion of
#<StreamableHTTPClientTransport> which has only a getter
The workspace-tested resolution was 1.0.21 (no such assignment — verified
by source diff of the published tarballs). Pin it via pnpm.overrides until
@copilotkit/runtime supports the newer client line.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The Slack example is a **consumer** of the packages we shipped today,
but its `workspace:*` deps forced every deployment to rebuild the
monorepo (and fight nx inside builders — exit-130 city). This PR makes
the example what an example should be: installable and runnable anywhere
with zero monorepo context.
## Changes
- **`workspace:*` → published ranges** (`@copilotkit/bot*` `~0.0.1`,
`@copilotkit/runtime` `^1.59.5`). In-repo it now installs from the
registry like any user's project; `tsx` runs the source directly — there
is no build step anymore, anywhere.
- **Drop the private `@copilotkit/typescript-config` devDep**, inlining
the base compiler options into the example's `tsconfig.json` (identical
`tsc` behavior, verified).
- **Standalone `pnpm-lock.yaml`** inside `examples/slack` so isolated
installs (Railway `rootDirectory`, users copying the folder) are
reproducible. Root workspace installs ignore it.
- **Slack manifest fixes** (both variants): remove the `assistant:write`
scope + `assistant_thread_started` event — Slack's manifest validator
rejects them without an `assistant_view` feature block, and the bot
doesn't implement that surface; add the `/triage` slash command the bot
actually registers (previously had to be added by hand).
## Verification
- `slack-example` tests: **38/38** against the published packages
- Direct `tsc --noEmit`: clean
- Clean-room (gitless snapshot, isolated dir): install from registry →
runtime boots to `listening`, bot boots to a loud Slack auth failure on
dummy tokens (the correct failure)
- Live deploy validation on Railway follows this merge
(rootDirectory=/examples/slack, no build command)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Replace floating "beta" dist-tags with exact versions for @ag-ui/mastra,
@mastra/{client-js,core,libsql,memory}, and mastra in both the examples
and showcase mastra packages. Showcase mastra also raises its zod floor
^3.24.0 -> ^3.25.0. The examples mastra package additionally carries the
fleet-wide @ag-ui/client 0.0.55 bump and single-tree overrides here, since
its manifest mixes both changes.
Bring the starter agents' Python dependency pins (pyproject.toml + uv.lock
for adk, langgraph-fastapi, langgraph-python, pydantic-ai, strands-python;
requirements.txt + docker override for crewai-crews) in line with the
showcase fleet pin standard.
Bump @ag-ui/client 0.0.53 -> 0.0.55 across 8 starter example packages and
add npm overrides pinning @ag-ui/{client,core,encoder,proto} to 0.0.55 so
each install resolves a single @ag-ui tree. The mastra starter receives the
same bump alongside its dist-tag pin fixes in a separate commit.
- dependencies: workspace:* -> published ranges (@copilotkit/bot* ~0.0.1,
@copilotkit/runtime ^1.59.5) — the example is a consumer of the released
packages, installable and deployable with zero monorepo context
- drop the private @copilotkit/typescript-config devDep; inline the base
compiler options into tsconfig.json (verified identical tsc result)
- commit a standalone examples/slack/pnpm-lock.yaml for isolated installs
(root workspace installs ignore it)
- slack-app-manifest.{yaml,json}: remove assistant:write scope +
assistant_thread_started event (Slack rejects them without an
assistant_view feature block; the bot doesn't implement that surface),
add the /triage slash command the bot registers
Verified: slack-example tests 38/38 against the published packages; direct
tsc --noEmit clean; standalone install + runtime/bot boot exercised in a
gitless clean-room snapshot.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
100% JSX bot at feature parity with the PoC example: issue/page cards,
tables, Chart.js charts, Mermaid diagrams, incident/status/links cards,
a confirm_write HITL gate, and /agent + /triage slash commands.
Registers examples/slack in the pnpm workspace.
The locked-state card told users to add an Intelligence license with
`copilotkit add-intelligence`, but that command only drops the
Intelligence overlay and does not issue a license (and is not yet wired
into the CLI dispatch). The command that issues a license key is
`copilotkit license`.
The standalone threads template is retired: the ENT-679 rollout was
reverted from main (#5215/#5216/#5217) and the settled model is base
langgraph-python + Intelligence activation overlay. The Intelligence
CLI (main and published copilotkit@3.0.2) no longer references it.
Also drops its two entries from .github/config-allowlist.txt.
## Problem
CLI starters for Mastra, Agno, PydanticAI, AWS Strands, Google ADK, MS
Agent Framework, and LlamaIndex fail on `npm run dev` with:
```
Error: dependency failed to start: container copilotkit-intelligence-intelligence-1 is unhealthy
intelligence-1 | error: database "intelligence_app" does not exist
```
## Root cause
The overlay compose relied on a bind-mounted `docker/init-db/` script to
create `intelligence_app`, but the CLI's Intelligence activation copies
**only** `docker-compose.yml` into scaffolded projects. The mount source
never exists there, so Docker creates it as an empty directory, postgres
initializes with only the default DB, and the composite's migrations
fail.
`langgraph-python-threads` was unaffected because its template ships its
own compose + `docker/init-db/` in-repo.
## Why it keeps biting internal testers
The compose project name is fixed (`copilotkit-intelligence`), so
**every starter on a machine shares one `postgres-data` volume** — and
postgres only honors `POSTGRES_DB`/init scripts on first init of an
*empty* volume. One broken run poisons the volume for every subsequent
starter, regardless of framework.
## Fix (self-contained + self-healing)
- `POSTGRES_DB: intelligence_app` and drop the `docker/init-db` bind
mount + script (the shadow DB it also created is only used by repo-local
dev tooling, never by the composite)
- Add an idempotent `provision-db` one-shot (same pattern as the
existing `provision-user`) that creates `intelligence_app` when missing
— this heals already-poisoned volumes on the next `docker compose up`,
with no manual `down -v`
- Gate `intelligence` on `provision-db` completion; align the postgres
healthcheck dbname
Because the CLI fetches this overlay live from `main` at scaffold time,
merging this fixes every CLI version in the wild immediately — no CLI
release needed.
## Verification
Tested with real Docker on isolated compose projects:
1. **Poisoned volume** (reproduced by running the old compose revision
with the empty `init-db` dir the CLI leaves behind → volume with no
`intelligence_app`): new compose → `provision-db` exits 0, migrations
run, composite **Healthy**, `up -d --wait` exits 0
2. **Fresh volume**: DB created via `POSTGRES_DB`, `provision-db`
no-ops, composite **Healthy**
3. **Idempotency**: second `up -d --wait` on a running stack exits 0
🤖 Generated with [Claude Code](https://claude.com/claude-code)
The activation overlay's docker-compose.yml relied on a bind-mounted
docker/init-db script to create the intelligence_app database, but the
CLI copies only docker-compose.yml into scaffolded projects. The mount
source never exists there, Docker creates it as an empty directory,
postgres initializes without intelligence_app, and the composite's
migrations fail: 'database "intelligence_app" does not exist' →
'dependency failed to start: container ...intelligence-1 is unhealthy'.
Make the compose file self-contained:
- Set POSTGRES_DB: intelligence_app (drop the init-db bind mount and
the now-unused init script; the shadow DB it also created is only
used by repo-local dev tooling, never by the composite).
- Add an idempotent provision-db one-shot that creates the database
when missing. POSTGRES_DB only applies on first init of an empty
volume, and the volume is shared across all scaffolds via the fixed
compose project name — so machines that already hit the bug have a
data volume without the database. The one-shot heals those on the
next 'docker compose up' with no manual 'down -v'.
- Gate the composite on provision-db completion instead of postgres
health, and align the postgres healthcheck dbname.
New users were still discovering cloud.copilotkit.ai through docs pages,
the README, example READMEs, and in-app banners/console messages. Replace
all user-facing web links with dashboard.operations.copilotkit.ai (the
destination the marketing-site CTAs already use). Functional API endpoints
(api.cloud.copilotkit.ai) are deliberately untouched since existing cloud
customers depend on them.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Left over from instrumenting the HITL render lifecycle while verifying that
clicking a card in the in-chat picker resolves `respond()` and triggers the
agent's continuation run.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Teach-mode UX (staged on the no-op recorder shim, ready for the live hook):
- Suggested-prompt pill leads the welcome screen — "Approve the $5,000
Marketing transaction" — a one-click path straight into the
over-policy-limit gate (seed t-1: Google Ads -$5,000, Marketing limit
$5,000 / spent $500). The same pill drives both halves of the arc:
fails pre-learning, succeeds post-learning.
- Pulsating violet recording vignette frames the canvas while the officer
is teaching. Ref-counted around every `recordUserAction` call so it
stays continuous across opened+finalized; minimum 1.2s visible duration;
non-blocking; static fallback under prefers-reduced-motion. Mounted at
z-1300 to read clearly even over the docked chat panel.
- Inline policy-exception card replaces the popup modal: the officer's
whole demonstration (see symptom → file exception → record) now
happens in the chat as a single HITL card, with identical REST
callers and identical `policy_exception.opened`→`finalized` recording
payloads to the old modal.
CK v2 provider fix:
- Swap the v1 `CopilotKit` compatibility bridge for the v2-native
`CopilotKitProvider`. The bridge wraps the chat in a heavier stack
(ThreadsProvider + a second CopilotChatConfigurationProvider + listeners);
that churn re-fires CopilotChat's /connect effect cleanup mid-run, and
the cleanup calls AG-UI `detachActiveRun()` — which silently tears down
the in-flight run the instant the agent emits a frontend HITL tool call.
Symptom was a clean run with no error but no HITL render. With
CopilotKitProvider the `/connect` storm and ERR_ABORTED are gone and
runs complete cleanly. The inbox keeps working because v2 `useThreads`
reads CopilotKitProvider's own context.
- `reactStrictMode: false` in next.config to remove the dev double-mount
that aggravates the same teardown class. Production unaffected.
Other:
- Switch model to `openai/gpt-5.4-mini-2026-03-17` (verified reachable;
same tool-calling surface).
- Add `selectCard` HITL tool + visual `CardPicker` (in-chat brand+last4
picker) so card-targeted flows (PIN, policy assign) get a visual
picker instead of a text list.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
examples/showcases/teach-mode/ was a stray, non-runnable folder under examples/showcases (which is for runnable showcases). Moved the cookbook (README), LEARNING-TRACK-PLAN, and verify-teachable-gate.sh into examples/showcases/banking/docs/teach-mode/, dropped the duplicate record-user-action.ts (the demo's real seam lives at src/lib/record-user-action.ts), and fixed internal references.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Continues the closed draft #5183 on top of the merged #5180. Adds: v2 Threads as a docked chat side panel + inbox; the self-learning teachable policy-exception gate (symptom-only over-limit gate, justifying-exception unlock, recipe withheld; OSS default, env-gated CopilotKitIntelligence); the Aurora design system; a reusable teach-mode cookbook (examples/showcases/teach-mode/); and a learning-track plan. 53 files, scoped to examples/showcases/{banking,teach-mode}.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Northstar AI CRM — a full-featured agentic sales CRM for an enterprise
hardware seller, built with CopilotKit, the AG-UI protocol, and a
TypeScript Strands agent (@strands-agents/sdk + @ag-ui/aws-strands).
The first TypeScript Strands example under examples/.
Highlights:
- Agentic canvas: tool calls render on the workspace — quote approval
opens a quote page; analyze_team and generate_weekly_report open
dedicated report pages; frontend tools navigate the workspace.
- Generative UI cards, human-in-the-loop follow-up approval, and a live
STATE_SNAPSHOT that syncs a SQLite CRM store with the board,
dashboard, and report pages.
- Dashboard, pipeline (Kanban), products, team, and reports surfaces.
Self-contained under examples/showcases/strands-crm with an agent/ +
frontend/ split and a concurrently dev script; listed in
examples/README.md.
## Summary
Makes the `examples/showcases/banking/` SaaS demo customer-ready by
migrating it to **CopilotKit v2** and polishing it into a credible,
reliable reference. Closes the non-memory gaps from FOR-133's assessment
(FOR-138).
- **v2 migration**: v2 Hono runtime route (`BuiltInAgent` +
`createCopilotHonoHandler` + `InMemoryAgentRunner`), `CopilotKit`
provider + `CopilotPopup`, hooks moved to `@copilotkit/react-core/v2`
(`useAgentContext`, `useHumanInTheLoop`, `useComponent`, Zod params), on
`workspace:*` packages.
- **File-backed data store**: domain data in `src/data/seed.json` behind
a typed `src/lib/store.ts` (in-memory, resets to seed on restart). Clean
seam left for the memory track (FOR-137).
- **Credible identity + data**: Northwind Finance / Alex Morgan /
`@northwind.example`, refreshed transaction dates + future card
expiries, `Intl` currency formatting.
- **Dropped** the SQL page + fake-MSA RAG feature (and committed
ServiceNow secret) — focused fintech story.
- **Framework/build**: Next 16 async route `params`, Tailwind v4 (so the
v2 stylesheet imports normally), correct `next`/`react` versions, single
lockfile, accurate v2 README.
- **Tests**: LLM-free Playwright smoke test (also fails on
hydration/uncaught errors).
## Verified live (real OpenAI key)
Full golden path works end-to-end: chat renders → "show transactions for
card 4242" renders the generative-UI list → "add a card" → HITL approval
card → Approve → new card appears in the grid. 0 console errors. Build +
typecheck + smoke test green; no committed secrets.
Three v2 chat-rendering bugs were found and fixed by running it live:
use the full `CopilotKit` provider (not the low-level
`CopilotKitProvider`, which omits `ThreadsProvider`); set
`useSingleEndpoint={false}` to match the multi-endpoint route; and use
`useComponent` with a `deps` array for display-only generative UI
(avoids a stale-closure empty render).
## Non-goals (deliberately out of scope)
- Real auth.
- Conversation threads + long-term/self-learning memory → FOR-137.
- Deleting the duplicate `enterprise-brex` demo + repointing its deploy.
## Test plan
- [ ] `pnpm --filter demo-saas-copilot build` succeeds
- [ ] `pnpm --filter demo-saas-copilot exec tsc --noEmit` clean
- [ ] `pnpm --filter demo-saas-copilot test:e2e` passes
- [ ] With `OPENAI_API_KEY` set: run the golden path (transactions
gen-UI, add-card HITL → approve → grid update)
## Known minor follow-ups
- Removing deprecated `showDevConsole` surfaces the v2 Web Inspector /
announcement banner.
- Newly-added cards get a near-term generated expiry.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
The smoke Dockerfile previously relied on a floating `npm install
next@latest` to upgrade crewai-crews from its pinned Next ^15.5.15 to
Next 16. PR #5250 removed that floating line for all starters, which was
correct for the other five but broke crewai-crews: Next 15 cannot
compile @copilotkit/react-core's `export *` re-exports, so the app build
failed.
Pin `next` to 16.2.7 (current latest, the patched build that compiles
react-core and is free of the 16.0.x security advisory) instead of
restoring the floating dependency. Locally, a clean no-cache
docker-compose smoke build compiles, boots, and passes all 4 starter
smoke tests.
The smoke-test app Dockerfiles ran `RUN npm install next@latest` right after
installing the pinned deps from package.json. This overrode the deliberate
`next` pin with a floating version (non-deterministic builds) and added a
flaky network round-trip that broke the agno smoke build with ECONNRESET on
2026-06-04 (run 26972381969). Every affected starter already pins `next` in
package.json (agno 16.0.7, adk 16.1.1, crewai ^15.5.15, llamaindex 16.0.8,
ms-agent-framework-python 16.0.8, pydantic-ai 16.0.7), so the extra install
is pure harm. Removing it makes builds deterministic and removes the network
fragility.
Render a per-turn persistent intelligence indicator that stays stable
across multi-step turns and settles into a "finished" tag. Splits the
component into IntelligenceIndicator (logic) + IntelligenceIndicatorView
(presentation), wires it into CopilotChatView / CopilotChatMessageView,
adds the slot styles to globals.css, and a Storybook story plus
timer-free logic tests.
Conflict resolutions:
- contract test: keep the rollout's parameterized version and add
strands-python to migratedIntegrations/appRoots (60/60 passing) in
place of her bespoke MIGRATED_INSTANCES file
- parity manifest: rollout's version with strands' three threads-shield
allowances removed (mirrors the langgraph-fastapi migration); parity
verify green — strands now 88 tracked files, zero drift
- package-lock: regenerated at 1.59.3 (a2ui-renderer stays 1.56.5,
the family-wide pin shared with the north-star)
Also rides: her react-core A2UIMessageRenderer test flake fix
(act -> waitFor), kept intentionally.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Conflict resolution: take the rollout's contract test and append the
agentcore describe block (CDK lambda runtime gate, Vite frontend with
import.meta.env gate, docker env wiring). Bump both agentcore
package.jsons 1.59.1 -> 1.59.3 + regen lockfiles. 54/54.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Conflict resolution: take the rollout's parameterized contract test and
append the a2a-a2ui bespoke tests (namespaced helper, 1.59.3 pins).
Bump a2a-a2ui @copilotkit/* 1.59.1 -> 1.59.3 + regen lockfile. 49/49.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- bump a2a-middleware, mcp-apps, agent-spec from 1.59.1 (their verified
pre-revert state) to 1.59.3 to match the starters
- regenerate package-lock.json for the 11 examples whose package.json
changed (drawer deps re-added on starters, version bumps on the three)
- update the migration contract test's version assertions to 1.59.3
(43/43 passing); oxfmt pass
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Restores #5151 (north-star + batch 1 + crewai-flows + llamaindex),
#5196 (pydantic-ai), #5205 (a2a-middleware), #5211 (mcp-apps), reconciled
onto the current main baseline rather than the pre-revert tree:
- keep main's 1.59.3 pins, AGENT_URL normalization, default agent keys,
useConfigureSuggestions, available:false, useRenderTool
status/parameters API, call-time agent.state reads, and crewai-crews'
rebuilt page (not yet threads-migrated)
- graft the threads layer (drawer/gate/provider, env-gated route
intelligence block, next.config gate, env docs, drawer deps) on top
- drop threads-era sidebar suggestions props where main now registers
suggestions via useConfigureSuggestions (or omits them)
- fix the stale pydantic-ai doc link main reintroduced in ms-af-dotnet
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The updateProverb useFrontendTool passed the live `agent` object in its
deps array. react-core's use-frontend-tool does JSON.stringify(extraDeps),
which throws "Converting circular structure to JSON" on agent.activeRunDetach$
(an RxJS Subject), crashing the React tree so no assistant bubble renders.
`agent`/`agent.setState` are stable references; only `state` needs to be a
dep. Also bump the docker ag-ui-crewai override to >=0.2.0,<0.3.0 to match
agent/requirements.txt and the showcase backend.
Swap the boilerplate "Create Next App" / "Generated by create next app"
title and description in each starter layout for a per-framework
"<Framework> + CopilotKit Starter" title and matching description.
crewai-flows hardcoded the agent URL with no AGENT_URL env override; add
the fallback to match siblings. agno and llamaindex concatenate a path
suffix onto the base URL, so strip any trailing slash first to avoid a
double slash when AGENT_URL ends in "/".
The welcome message promised theme/proverb/weather tools, but the page
registered none of them (only a debug console.log of agent.state).
Mirror the crewai-flows sibling to wire setThemeColor, the proverbs
shared-state tool, and a weather render tool, remove the leftover
console.log effect, and drop the stray w-screen overflow.
The agno and llamaindex add_proverb frontend tools closed over a stale
`state` snapshot with no dependency array, so rapid successive adds
dropped earlier proverbs. Read agent.state at call time inside the
handler instead. Also drop the stray w-screen on the llamaindex page
that caused horizontal scrollbar overflow.
The smoke build path (docker/Dockerfile.agent) runs `uv sync` against
agent/pyproject.toml + agent/uv.lock, but those still pinned
ag-ui-langgraph==0.0.34 (and the lock still pinned copilotkit==0.1.87).
copilotkit 0.1.93 requires ag-ui-langgraph[fastapi]>=0.0.35, so uv sync
failed with "No solution found" and the langgraph-fastapi smoke job went
red. The prior fix only bumped the production Dockerfile's
`uv pip install`, which the smoke path does not use.
Bump pyproject to ag-ui-langgraph[fastapi]==0.0.37 and regenerate uv.lock
(copilotkit 0.1.87->0.1.93, ag-ui-langgraph 0.0.34->0.0.37). Verified by
building docker/Dockerfile.agent locally: uv sync now resolves and the
agent boots ("Uvicorn running on 0.0.0.0:8123" / "Application startup
complete") serving HTTP 200 on /health.
Also reconcile parity: strands-python's entrypoint.sh legitimately diverges
from the langgraph-python north-star (it boots the strands agent via
`uv run python main.py` and serves Next via `next start`, not serve.py +
standalone server.js). Add entrypoint.sh to strands-python's
allowedDivergence, mirroring how langgraph-js already declares its own
custom entrypoint. parity:check now reports 0 errors.
The entrypoint was copy-pasted from langgraph-python: it logged
'langgraph-python starter', ran 'python serve.py' (no serve.py exists in this
starter), and started Next via standalone 'node server.js' (this image is a
non-standalone .next + node_modules build, so server.js does not exist either).
The container crash-looped on boot with
"python: can't open file '/app/serve.py'".
Run the Strands agent's self-serving agent/main.py via its uv venv
(AGENT_PORT=8123) and serve the frontend with 'next start'. Verified by booting
the image: agent reaches 'Application startup complete' on :8123 and the
container serves HTTP 200 on /.
copilotkit 0.1.93 re-exports StateStreamingMiddleware/StateItem FROM
ag_ui_langgraph.middlewares.state_streaming, which only exists in
ag-ui-langgraph>=0.0.35. The Dockerfiles installed copilotkit with --no-deps
and pinned ag-ui-langgraph[fastapi]==0.0.22, so the middlewares submodule was
missing and the agent crash-looped at boot with
'ModuleNotFoundError: No module named ag_ui_langgraph.middlewares'.
Bump the pin to 0.0.37 (the version copilotkit 0.1.93 resolves with deps).
Verified by booting the langgraph-python image: the agent now reaches
'Application startup complete' / 'Uvicorn running on 0.0.0.0:8123' with no
ImportError, and the container serves HTTP 200 on /.