examples/showcases/reskinnable-demo/README.md
One Next.js app whose entire experience — brand, theme, layout, pages,
tools, and agent — is reskinnable at runtime. A skin-agnostic shell hosts
one skin per route segment /[skin]/..., and ships two of them:
banking — "Northwind Finance", a corporate banking dashboard. REST-backed
(a live ledger at /api/banking/v1/*): transactions, cards, expense policies,
an approvals queue, filed reports on a canvas, and a teachable
over-limit-approval flow.airline — "Aeronova", a passenger concierge. In-memory (a seed-backed
React store): check-in and seat selection, loyalty, and disruption rebooking.The two skins run behind the same Skin contract on purpose: one is
REST-backed and one is in-memory, which proves the contract is
substrate-agnostic. Both get the same shared chat panel, tool-activity lines,
suggestion pills, and full-region canvas from the shell.
Skin interface (src/shell/skin-contract.ts) swapping a whole
product — brand, theme, nav, pages, tools, agent — with the shell knowing
nothing domain-specific..theme-<id> block, so a reskin is a pure value swap.pnpm install # from the repo root — this is a workspace package
cp .env.example .env # then fill in OPENAI_API_KEY
pnpm dev
Open http://localhost:3000. / redirects to the default skin
(banking; set in src/shell/skins-config.ts). This default OSS mode needs only
OPENAI_API_KEY — an SSE runtime with an in-memory agent runner, no external
services. Durable cross-thread memory is env-gated (Intelligence mode); see
.env.example and the memory section below.
Use the floating selector at the bottom-left of any page — it lists every
registered skin and navigates to /<id> client-side (instant, no reload). Each
skin starts in its own fresh thread. You can also go straight to /banking or
/airline.
Follow the repo-local reskin skill in .claude/skills/reskin/ (SKILL.md +
templates.md). The shape:
src/skins/<id>/ and implement each Skin contract field.theme.css (a .theme-<id> block re-valuing the shared tokens) and
side-effect-import it from the skin's layout.tsx.agent.ts (no "use client", no JSX).src/shell/registry.ts (client) and
src/shell/agent-registry.ts (server), keyed by the identical id.See CLAUDE.md for the full architecture: the contract field by field, the client/server boundary, routing/provider composition, the theming contract, and the shared canvas / OGUI model.
The banking skin is the richer of the two and doubles as a CopilotKit feature tour. Notable beats:
useAgentContext, so "what's on my screen?" answers truthfully.render_report paints a multi-widget spend report
full-region on the shared canvas, binding live figures on the client.docs/teach-mode/.By default the runtime is pure OSS — the teach-a-workflow loop works within a
single conversation, but nothing persists across threads or restarts. When
INTELLIGENCE_API_URL, INTELLIGENCE_GATEWAY_WS_URL, and INTELLIGENCE_API_KEY
are all set (src/app/api/copilotkit/[[...slug]]/route.ts), the runtime builds
in Intelligence mode: the agent gains durable long-term memory via the
recall_memory / save_memory tools, so a demonstrated over-limit procedure
(and remembered facts/preferences) survive across threads and users. The bundled
docker-compose.yml and *-demo.sh scripts stand up the memory stack; the
.env.example documents the required variables.
The images under assets/ (aurora-dashboard.png, copilot-chat.png,
learning-mode-vignette.png, project-preview.png) illustrate the banking
skin specifically — its dashboard, chat panel, and learning-mode recording
vignette. They predate parts of the current reskinnable shell chrome (e.g. the
floating skin selector) and do not depict the airline skin, so treat them as
banking-skin illustrations rather than a picture of the whole app.
pnpm test:unit # vitest
pnpm test:e2e # playwright
pnpm test:e2e:ogui # open generative UI suite
pnpm test:self-learning # the memory CI gate
Next.js 16, React 19, Tailwind v4, and workspace (workspace:*) builds of
@copilotkit/react-core, @copilotkit/runtime, @copilotkit/a2ui-renderer,
@copilotkit/core, and @copilotkit/shared (the v2 entry points).