DevOps & Infra
go-to-production - Claude MCP Skill
Pre-deploy checklist for CopilotKit v2 apps — persistent AgentRunner (not InMemory) behind horizontal scaling, CORS, showDevConsole off, debug off, credentials:'include' for cookie auth, env-sourced secrets on edge runtimes, publicApiKey / licenseToken, dev-only-prop audit (agents__unsafe_dev_only, selfManagedAgents). Pointer skill — does NOT teach auth, rate-limit, or observability (those are server- framework concerns wired via the middleware skill). Load before any first production deploy of a CopilotKit v2 app.
SEO Guide: Enhance your AI agent with the go-to-production tool. This Model Context Protocol (MCP) server allows Claude Desktop and other LLMs to pre-deploy checklist for copilotkit v2 apps — persistent agentrunner (not inmemory) behind horizonta... Download and configure this skill to unlock new capabilities for your AI workflow.
Documentation
SKILL.md# CopilotKit v2 — Go-Live Checklist
Run through each section before deploying. This is a pointer skill — each
check delegates to the skill that owns the detail.
## Persistent Runner Checks
### Check: runner is NOT InMemoryAgentRunner under horizontal scale
Expected:
```ts
import { CopilotRuntime } from "@copilotkit/runtime/v2";
import { SqliteAgentRunner } from "@copilotkit/sqlite-runner";
new CopilotRuntime({
agents,
runner: new SqliteAgentRunner({ dbPath: "/var/data/threads.db" }),
});
```
Fail condition: runtime uses the default `InMemoryAgentRunner` (or passes
one explicitly) while the deployment has more than one replica or any
restart-surviving requirement.
Fix: switch to `SqliteAgentRunner` (single-host durable) or
CopilotKitIntelligence (multi-host durable). See `copilotkit/runtime` → `references/agent-runners.md`.
### Check: Intelligence mode points at cloud URLs if enabled
Expected:
```ts
// Node / server runtime — `env` here is Node's `process.env`:
new CopilotRuntime({
agents,
intelligence: {
apiUrl: "https://api.cloud.copilotkit.ai",
wsUrl: "wss://api.cloud.copilotkit.ai",
licenseToken: process.env.COPILOTKIT_LICENSE_TOKEN,
},
});
```
Fail condition: `apiUrl` points to a self-hosted URL — Intelligence is not
self-hostable.
Fix: use Cloud URLs or downgrade to SqliteAgentRunner for on-prem
durability. See `copilotkit/runtime` → `references/intelligence-mode.md`.
## CORS Checks
### Check: cross-origin deployments enable CORS on the fetch handler
Expected:
```ts
const handler = createCopilotRuntimeHandler({
runtime,
basePath: "/api/copilotkit",
cors: true,
});
```
Fail condition: frontend and runtime are on different origins, and `cors`
is not enabled (or is not equivalently handled by a reverse proxy / CDN).
Fix: set `cors: true` on `createCopilotRuntimeHandler`, or handle CORS at
the proxy layer. See `copilotkit/runtime` → `references/setup-endpoint.md`.
## Debug Checks
### Check: showDevConsole is off in production
Expected:
```tsx
<CopilotKitProvider runtimeUrl="/api/copilotkit" showDevConsole="auto" />
```
Fail condition: `showDevConsole={true}` hardcoded — internal error details
render to end users.
Fix: use `"auto"` (the default), or gate on `NODE_ENV`.
### Check: debug prop is off (or dev-only)
Expected:
```tsx
<CopilotKitProvider
runtimeUrl="/api/copilotkit"
debug={process.env.NODE_ENV !== "production"}
/>
```
Fail condition: `debug={{ events: true, lifecycle: true, verbose: true }}`
shipped to prod — large log volume and verbose logs can include PII
payloads.
Fix: gate `debug` on environment, or omit it entirely.
### Check: runtime debug is off
Expected:
```ts
new CopilotRuntime({
agents,
debug: process.env.NODE_ENV !== "production",
});
```
Fail condition: `debug: true` or `{ verbose: true }` shipped — Pino logs
expand in volume and may include tool-call payloads.
Fix: gate on environment. See `copilotkit/debug-and-troubleshoot`.
## Credentials / Auth Checks
### Check: cookie-based auth sets credentials:'include'
Expected:
```tsx
<CopilotKitProvider
runtimeUrl="https://api.myapp.com/copilotkit"
credentials="include"
/>
```
Fail condition: cross-origin runtime with cookie-session auth, no
`credentials="include"` — browsers strip cookies and `/info` plus the SSE
stream go unauthenticated.
Fix: add `credentials="include"`, and set CORS on the runtime to allow
credentials. See `copilotkit/react-core` → `references/provider-setup.md`.
### Check: auth / rate-limit / observability wired through middleware
Expected:
```ts
new CopilotRuntime({
agents,
hooks: {
onBeforeHandler: async ({ request }) => {
const session = await getSession(request);
if (!session) return new Response("Unauthorized", { status: 401 });
},
},
});
```
Fail condition: ad-hoc auth checks inside tool handlers instead of hook /
middleware.
Fix: centralize auth in `hooks.onBeforeHandler` or
`beforeRequestMiddleware`. CopilotKit does NOT ship auth, rate-limit, or
observability — use your server framework's tooling. See
`copilotkit/runtime` → `references/middleware.md`.
## License Checks
### Check: publicApiKey is env-sourced, not hardcoded
Expected:
```tsx
<CopilotKitProvider publicApiKey={import.meta.env.VITE_CPK_PUBLIC_API_KEY} />
```
Fail condition: key inlined as a string literal in committed source.
Fix: read from build-time env (`VITE_*`, `NEXT_PUBLIC_*`, etc.) and inject
via CI. `publicLicenseKey` is also accepted as an alias
(`publicApiKey ?? publicLicenseKey`); prefer `publicApiKey` for
consistency with the HTTP header (`X-CopilotCloud-Public-Api-Key`) and
Cloud dashboard label.
### Check: runtime licenseToken is env-sourced
Expected (Node / server runtime):
```ts
new CopilotRuntime({
agents,
licenseToken: process.env.COPILOTKIT_LICENSE_TOKEN,
});
```
On Cloudflare Workers, `env` here refers to the Worker binding argument
passed to `fetch(request, env)` — not a module-global.
Fail condition: license token hardcoded in source or absent in prod.
Fix: inject via environment variable. See `copilotkit/runtime` → `references/setup-endpoint.md`.
## Env-Sourced Secrets Checks
### Check: edge runtimes use env binding, not process.env
Expected (Cloudflare Workers — runtime hoisted to module scope, lazy init):
```ts
import {
CopilotRuntime,
createCopilotRuntimeHandler,
BuiltInAgent,
} from "@copilotkit/runtime/v2";
interface Env {
OPENAI_API_KEY: string;
}
let cachedHandler: ((r: Request) => Response | Promise<Response>) | null = null;
function getHandler(env: Env) {
if (cachedHandler) return cachedHandler;
const runtime = new CopilotRuntime({
agents: {
// Thread env.OPENAI_API_KEY explicitly — `process.env` is undefined on
// Workers, so BuiltInAgent's env-var fallback never fires.
default: new BuiltInAgent({
model: "openai/gpt-4o",
apiKey: env.OPENAI_API_KEY,
}),
},
});
cachedHandler = createCopilotRuntimeHandler({
runtime,
basePath: "/api/copilotkit",
cors: true,
});
return cachedHandler;
}
export default {
fetch(request: Request, env: Env) {
return getHandler(env)(request);
},
};
```
Fail condition: Workers / Vercel Edge code reads `process.env.*` — those
runtimes don't expose it. Also: constructing `new CopilotRuntime(...)`
inside `fetch(request, env)` on every request wastes CPU and drops
in-memory runner state.
Fix: use the platform's env argument (Workers `env`, Vercel Edge
`request.env`), and hoist the runtime + handler to module scope. Workers
isolates reuse module globals across requests (in-isolate only — for
cross-isolate durability pair with `SqliteAgentRunner` or Intelligence).
See `copilotkit/0-to-working-chat`.
## Dev-Only-Prop Audit
### Check: no agents\_\_unsafe_dev_only in shipped client code
Expected:
```tsx
<CopilotKitProvider runtimeUrl="/api/copilotkit" />
// or
<CopilotKitProvider publicApiKey="ck_pub_..." />
```
Fail condition: any `agents__unsafe_dev_only={{ ... }}` prop in shipped
client code — registers agents in the browser and leaks credentials.
Fix: move agent construction to the server (runtime) or use
`publicApiKey` (Cloud). See `copilotkit/spa-without-runtime`.
### Check: no selfManagedAgents in shipped client code
Fail condition: any `selfManagedAgents={{ ... }}` prop. It's an alias of
`agents__unsafe_dev_only` — same leak.
Fix: same as above.
### Check: publicApiKey / publicLicenseKey are env-sourced and consistent
Both props are supported — `publicApiKey` is canonical and wins when both
are set (`resolvedPublicKey = publicApiKey ?? publicLicenseKey`). Prefer
`publicApiKey` in new code. The only fail condition here is a hardcoded
string literal — see "Check: publicApiKey is env-sourced, not hardcoded"
above. See `copilotkit/v1-to-v2-migration` for v1 → v2 rename details.
## Common Production Mistakes
### CRITICAL InMemoryAgentRunner behind horizontal scaling
Wrong:
```ts
// Kubernetes 3 replicas, default runner
new CopilotRuntime({ agents });
```
Correct:
```ts
new CopilotRuntime({
agents,
runner: new SqliteAgentRunner({ dbPath: "/var/data/threads.db" }),
});
```
Thread state is per-instance in InMemory; the load balancer may send a
follow-up request to a different replica → `agent_thread_locked` on one
replica and empty state on another.
Source: packages/runtime/src/v2/runtime/runner/in-memory.ts; packages/core/src/core/core.ts:96
### CRITICAL showDevConsole=true in prod
Wrong:
```tsx
<CopilotKitProvider showDevConsole={true} />
```
Correct:
```tsx
<CopilotKitProvider showDevConsole="auto" />
```
Exposes internal error details (stack traces, troubleshooting links) to
end users.
Source: docs/snippets/shared/troubleshooting/error-debugging.mdx:22-24
### HIGH shipping debug:{verbose:true} in prod
Wrong:
```tsx
<CopilotKitProvider debug={{ events: true, lifecycle: true, verbose: true }} />
```
Correct:
```tsx
<CopilotKitProvider debug={process.env.NODE_ENV !== "production"} />
```
`verbose` expands event payloads into logs — can include PII. Large log
volume as a secondary concern.
Source: docs/snippets/shared/troubleshooting/debug-mode.mdx:145-149
### HIGH forgetting credentials:'include' with cookie auth
Wrong:
```tsx
<CopilotKitProvider runtimeUrl="https://api.myapp.com/copilotkit" />
```
Correct:
```tsx
<CopilotKitProvider
runtimeUrl="https://api.myapp.com/copilotkit"
credentials="include"
/>
```
Cross-origin browsers strip cookies by default; `/info` and SSE stream go
unauthenticated.
Source: packages/react-core/src/v2/providers/CopilotKitProvider.tsx:118-120
### HIGH process.env secrets on Cloudflare Workers
Wrong:
```ts
const agent = new BuiltInAgent({ apiKey: process.env.OPENAI_API_KEY });
```
Correct: see `copilotkit/0-to-working-chat` (Cloudflare branch) — use
the `env` binding argument.
Source: examples/v2/runtime/cf-workers/src/index.ts:7-17
## Pre-Deploy Summary
- [ ] Runner is persistent (SQLite or Intelligence) for >1 replica
- [ ] CORS enabled (or proxied) on cross-origin runtime
- [ ] `showDevConsole` is `"auto"` (or omitted)
- [ ] `debug` on provider and runtime is off or dev-gated
- [ ] `credentials="include"` set if runtime is cross-origin and uses cookies
- [ ] Auth / rate-limit / observability wired via `hooks` or middleware
- [ ] `publicApiKey` / `licenseToken` sourced from env vars (not hardcoded)
- [ ] Edge runtimes read secrets from env binding, not `process.env`
- [ ] Cloudflare Workers: runtime + handler hoisted to module scope, not
re-created per-request
- [ ] `agents__unsafe_dev_only` and `selfManagedAgents` absent from bundle
- [ ] Error codes handled: `agent_thread_locked`, `runtime_info_fetch_failed`,
`agent_run_failed` (see `copilotkit/debug-and-troubleshoot`)Signals
Information
- Repository
- CopilotKit/CopilotKit
- Author
- CopilotKit
- Last Sync
- 5/26/2026
- Repo Updated
- 5/26/2026
- Created
- 5/21/2026
Reviews (0)
No reviews yet. Be the first to review this skill!
Related Skills
upgrade-nodejs
Upgrading Bun's Self-Reported Node.js Version
cursorrules
CrewAI Development Rules
README
Agents — Working Implementations
cn-check
Install and run the Continue CLI (`cn`) to execute AI agent checks on local code changes. Use when asked to "run checks", "lint with AI", "review my changes with cn", or set up Continue CI locally.
Related Guides
Bear Notes Claude Skill: Your AI-Powered Note-Taking Assistant
Learn how to use the bear-notes Claude skill. Complete guide with installation instructions and examples.
OpenAI Whisper API Claude Skill: Complete Guide to AI-Powered Audio Transcription
Learn how to use the openai-whisper-api Claude skill. Complete guide with installation instructions and examples.
Mastering the Oracle CLI: A Complete Guide to the Claude Skill for Database Professionals
Learn how to use the oracle Claude skill. Complete guide with installation instructions and examples.