claude-code

This commit is contained in:
ashutoshpythoncs@gmail.com
2026-03-31 18:58:05 +05:30
parent a2a44a5841
commit b564857c0b
2148 changed files with 564518 additions and 2 deletions

35
prompts/00-overview.md Normal file
View File

@@ -0,0 +1,35 @@
# Build-Out Prompt Index
Run these prompts **in order** in separate chat sessions. Each one is self-contained.
| # | File | What It Does | Depends On |
|---|------|-------------|------------|
| 01 | `01-install-bun-and-deps.md` | Install Bun runtime, install all dependencies | — |
| 02 | `02-runtime-shims.md` | Create `bun:bundle` runtime shim + `MACRO` globals so code runs without Bun's bundler | 01 |
| 03 | `03-build-config.md` | Create esbuild-based build system that bundles the CLI to a single runnable file | 01, 02 |
| 04 | `04-fix-mcp-server.md` | Fix TypeScript errors in `mcp-server/` and make it build | 01 |
| 05 | `05-env-and-auth.md` | Set up `.env` file, API key config, OAuth stubs | 01 |
| 06 | `06-ink-react-terminal-ui.md` | Verify and fix the Ink/React terminal rendering pipeline | 01, 02, 03 |
| 07 | `07-tool-system.md` | Audit and wire up the 40+ tool implementations (BashTool, FileEditTool, etc.) | 0103 |
| 08 | `08-command-system.md` | Audit and wire up the 50+ slash commands (/commit, /review, etc.) | 0103, 07 |
| 09 | `09-query-engine.md` | Get the core LLM call loop (QueryEngine) functional — streaming, tool calls, retries | 0103, 05, 07 |
| 10 | `10-context-and-prompts.md` | Wire up system prompt construction, context gathering, memory system | 0103 |
| 11 | `11-mcp-integration.md` | Get MCP client/server integration working — registry, tool discovery | 0104 |
| 12 | `12-services-layer.md` | Wire up analytics, policy limits, remote settings, session memory | 0103, 05 |
| 13 | `13-bridge-ide.md` | Stub out or implement the VS Code / JetBrains bridge layer | 0103, 09 |
| 14 | `14-dev-runner.md` | Create `npm run dev` / `bun run dev` script that launches the CLI in dev mode | 0103 |
| 15 | `15-production-bundle.md` | Create production build: minified bundle, platform-specific packaging | 03 |
| 16 | `16-testing.md` | Add test infrastructure (vitest), write smoke tests for core subsystems | All |
## Quick Start
1. Open a new Copilot chat
2. Paste the contents of `01-install-bun-and-deps.md`
3. Follow the instructions / let the agent run
4. Repeat for `02`, `03`, etc.
## Notes
- Prompts 0713 can be run somewhat in **parallel** (they touch different subsystems)
- If a prompt fails, fix the issue before moving to the next one
- Each prompt is designed to be **independently verifiable** — it tells you how to confirm it worked

View File

@@ -0,0 +1,38 @@
# Prompt 01: Install Bun Runtime & Dependencies
## Context
You are working in `/workspaces/claude-code`, which contains the leaked source code of Anthropic's Claude Code CLI. It's a TypeScript/TSX project that uses **Bun** as its runtime (not Node.js). The `package.json` specifies `"engines": { "bun": ">=1.1.0" }`.
There is no `bun.lockb` lockfile — it was not included in the leak.
## Task
1. **Install Bun** (if not already installed):
```
curl -fsSL https://bun.sh/install | bash
```
Then ensure `bun` is on the PATH.
2. **Run `bun install`** in the project root (`/workspaces/claude-code`) to install all dependencies. This will generate a `bun.lockb` lockfile.
3. **Verify the install** — confirm that:
- `node_modules/` exists and has the major packages: `@anthropic-ai/sdk`, `react`, `chalk`, `@commander-js/extra-typings`, `ink` (may not exist separately — check `@anthropic-ai/sdk`, `zod`, `@modelcontextprotocol/sdk`)
- `bun --version` returns 1.1.0+
4. **Run the typecheck** to see current state:
```
bun run typecheck
```
Report any errors — don't fix them yet, just capture the output.
5. **Also install deps for the mcp-server sub-project**:
```
cd mcp-server && npm install && cd ..
```
## Verification
- `bun --version` outputs >= 1.1.0
- `ls node_modules/@anthropic-ai/sdk` succeeds
- `bun run typecheck` runs (errors are expected at this stage, just report them)

137
prompts/02-runtime-shims.md Normal file
View File

@@ -0,0 +1,137 @@
# Prompt 02: Runtime Shims for `bun:bundle` Feature Flags & `MACRO` Globals
## Context
You are working in `/workspaces/claude-code`. This is the Claude Code CLI source. It was built to run under **Bun's bundler** which provides two build-time features that don't exist at runtime:
### 1. `bun:bundle` feature flags
Throughout the code you'll find:
```ts
import { feature } from 'bun:bundle'
if (feature('BRIDGE_MODE')) { ... }
```
Bun's bundler replaces `feature('X')` with `true`/`false` at build time for dead-code elimination. Without the bundler, this import fails at runtime.
**Current state**: There's a type stub at `src/types/bun-bundle.d.ts` that satisfies TypeScript, but there's no runtime module. We need a real module.
### 2. `MACRO` global object
The code references a global `MACRO` object with these properties:
- `MACRO.VERSION` — package version string (e.g., `"1.0.53"`)
- `MACRO.PACKAGE_URL` — npm package name (e.g., `"@anthropic-ai/claude-code"`)
- `MACRO.ISSUES_EXPLAINER` — feedback URL/instructions string
These are normally inlined by the bundler. Some files already guard with `typeof MACRO !== 'undefined'`, but most don't.
## Task
### Part A: Create `bun:bundle` runtime module
Create a file at `src/shims/bun-bundle.ts` that exports a `feature()` function. Feature flags should be configurable via environment variables so we can toggle them:
```ts
// src/shims/bun-bundle.ts
// Map of feature flags to their enabled state.
// In production Bun builds, these are compile-time constants.
// For our dev build, we read from env vars with sensible defaults.
const FEATURE_FLAGS: Record<string, boolean> = {
PROACTIVE: envBool('CLAUDE_CODE_PROACTIVE', false),
KAIROS: envBool('CLAUDE_CODE_KAIROS', false),
BRIDGE_MODE: envBool('CLAUDE_CODE_BRIDGE_MODE', false),
DAEMON: envBool('CLAUDE_CODE_DAEMON', false),
VOICE_MODE: envBool('CLAUDE_CODE_VOICE_MODE', false),
AGENT_TRIGGERS: envBool('CLAUDE_CODE_AGENT_TRIGGERS', false),
MONITOR_TOOL: envBool('CLAUDE_CODE_MONITOR_TOOL', false),
COORDINATOR_MODE: envBool('CLAUDE_CODE_COORDINATOR_MODE', false),
ABLATION_BASELINE: false, // always off for external builds
DUMP_SYSTEM_PROMPT: envBool('CLAUDE_CODE_DUMP_SYSTEM_PROMPT', false),
BG_SESSIONS: envBool('CLAUDE_CODE_BG_SESSIONS', false),
}
function envBool(key: string, fallback: boolean): boolean {
const v = process.env[key]
if (v === undefined) return fallback
return v === '1' || v === 'true'
}
export function feature(name: string): boolean {
return FEATURE_FLAGS[name] ?? false
}
```
### Part B: Create `MACRO` global definition
Create a file at `src/shims/macro.ts` that defines and installs the global `MACRO` object:
```ts
// src/shims/macro.ts
// Read version from package.json at startup
import { readFileSync } from 'fs'
import { resolve, dirname } from 'path'
import { fileURLToPath } from 'url'
const __filename = fileURLToPath(import.meta.url)
const pkgPath = resolve(dirname(__filename), '..', '..', 'package.json')
let version = '0.0.0-dev'
try {
const pkg = JSON.parse(readFileSync(pkgPath, 'utf-8'))
version = pkg.version || version
} catch {}
const MACRO_OBJ = {
VERSION: version,
PACKAGE_URL: '@anthropic-ai/claude-code',
ISSUES_EXPLAINER: 'report issues at https://github.com/anthropics/claude-code/issues',
}
// Install as global
;(globalThis as any).MACRO = MACRO_OBJ
export default MACRO_OBJ
```
### Part C: Create a preload/bootstrap file
Create `src/shims/preload.ts` that imports both shims so they're available before any app code runs:
```ts
// src/shims/preload.ts
// Must be loaded before any application code.
// Provides runtime equivalents of Bun bundler build-time features.
import './macro.js'
// bun:bundle is resolved via the build alias, not imported here
```
### Part D: Update tsconfig.json `paths`
The current tsconfig.json has:
```json
"paths": {
"bun:bundle": ["./src/types/bun-bundle.d.ts"]
}
```
This handles type-checking. For runtime, we'll need the build system (Prompt 03) to alias `bun:bundle``src/shims/bun-bundle.ts`. **Don't change tsconfig.json** — the type stub is correct for `tsc`. Just note this for the next prompt.
### Part E: Add global MACRO type declaration
Check if there's already a global type declaration for `MACRO`. If not, add one to `src/types/bun-bundle.d.ts` or a new `src/types/macro.d.ts`:
```ts
declare const MACRO: {
VERSION: string
PACKAGE_URL: string
ISSUES_EXPLAINER: string
}
```
Make sure `tsc --noEmit` still passes after your changes.
## Verification
1. `bun run typecheck` should pass (or have the same errors as before — no new errors)
2. The files `src/shims/bun-bundle.ts`, `src/shims/macro.ts`, `src/shims/preload.ts` exist
3. Running `bun -e "import { feature } from './src/shims/bun-bundle.ts'; console.log(feature('BRIDGE_MODE'))"` should print `false`
4. Running `bun -e "import './src/shims/macro.ts'; console.log(MACRO.VERSION)"` should print the version

165
prompts/03-build-config.md Normal file
View File

@@ -0,0 +1,165 @@
# Prompt 03: Create esbuild-Based Build System
## Context
You are working in `/workspaces/claude-code`. This is the Claude Code CLI — a TypeScript/TSX terminal app using React + Ink. It was originally built using **Bun's bundler** with feature flags, but that build config wasn't included in the leak.
We need to create a build system that:
1. Bundles the entire `src/` tree into a runnable output
2. Aliases `bun:bundle` → our shim at `src/shims/bun-bundle.ts`
3. Injects the `MACRO` global (via `src/shims/macro.ts` preload)
4. Handles TSX/JSX (React)
5. Handles ESM `.js` extension imports (the code uses `import from './foo.js'` which maps to `./foo.ts`)
6. Produces output that can run under **Bun** (primary) or **Node.js 20+** (secondary)
## Existing Files
- `src/shims/bun-bundle.ts` — runtime `feature()` function (created in Prompt 02)
- `src/shims/macro.ts` — global `MACRO` object (created in Prompt 02)
- `src/shims/preload.ts` — preload bootstrap (created in Prompt 02)
- `src/entrypoints/cli.tsx` — main entrypoint
- `tsconfig.json` — has `"jsx": "react-jsx"`, `"module": "ESNext"`, `"moduleResolution": "bundler"`
## Task
### Part A: Install esbuild
```bash
bun add -d esbuild
```
### Part B: Create build script
Create `scripts/build-bundle.ts` (a Bun-runnable build script):
```ts
// scripts/build-bundle.ts
// Usage: bun scripts/build-bundle.ts [--watch] [--minify]
import * as esbuild from 'esbuild'
import { resolve } from 'path'
const ROOT = resolve(import.meta.dir, '..')
const watch = process.argv.includes('--watch')
const minify = process.argv.includes('--minify')
const buildOptions: esbuild.BuildOptions = {
entryPoints: [resolve(ROOT, 'src/entrypoints/cli.tsx')],
bundle: true,
platform: 'node',
target: 'node20',
format: 'esm',
outdir: resolve(ROOT, 'dist'),
outExtension: { '.js': '.mjs' },
// Inject the MACRO global before all other code
inject: [resolve(ROOT, 'src/shims/macro.ts')],
// Alias bun:bundle to our runtime shim
alias: {
'bun:bundle': resolve(ROOT, 'src/shims/bun-bundle.ts'),
},
// Don't bundle node built-ins or native packages
external: [
// Node built-ins
'fs', 'path', 'os', 'crypto', 'child_process', 'http', 'https',
'net', 'tls', 'url', 'util', 'stream', 'events', 'buffer',
'querystring', 'readline', 'zlib', 'assert', 'tty', 'worker_threads',
'perf_hooks', 'async_hooks', 'dns', 'dgram', 'cluster',
'node:*',
// Native addons that can't be bundled
'fsevents',
],
jsx: 'automatic',
// Source maps for debugging
sourcemap: true,
minify,
// Banner: shebang for CLI + preload the MACRO global
banner: {
js: '#!/usr/bin/env node\n',
},
// Handle the .js → .ts resolution that the codebase uses
resolveExtensions: ['.tsx', '.ts', '.jsx', '.js', '.json'],
logLevel: 'info',
}
async function main() {
if (watch) {
const ctx = await esbuild.context(buildOptions)
await ctx.watch()
console.log('Watching for changes...')
} else {
const result = await esbuild.build(buildOptions)
if (result.errors.length > 0) {
console.error('Build failed')
process.exit(1)
}
console.log('Build complete → dist/')
}
}
main().catch(err => {
console.error(err)
process.exit(1)
})
```
**Important**: This is a starting point. You will likely need to iterate on the externals list and alias configuration. The codebase has ~1,900 files — some imports may need special handling. When you run the build:
1. Run it: `bun scripts/build-bundle.ts`
2. Look at the errors
3. Fix them (add externals, fix aliases, etc.)
4. Repeat until it bundles successfully
Common issues you'll hit:
- **npm packages that use native modules** → add to `external`
- **Dynamic `require()` calls** behind `process.env.USER_TYPE === 'ant'` → these are Anthropic-internal, wrap them or stub them
- **Circular dependencies** → esbuild handles these but may warn
- **Re-exports from barrel files** → should work but watch for issues
### Part C: Add npm scripts
Add these to `package.json` `"scripts"`:
```json
{
"build": "bun scripts/build-bundle.ts",
"build:watch": "bun scripts/build-bundle.ts --watch",
"build:prod": "bun scripts/build-bundle.ts --minify"
}
```
### Part D: Create dist output directory
Add `dist/` to `.gitignore` (create one if it doesn't exist).
### Part E: Iterate on build errors
Run the build and fix whatever comes up. The goal is a clean `bun scripts/build-bundle.ts` that produces `dist/cli.mjs`.
**Strategy for unresolvable modules**: If modules reference Anthropic-internal packages or Bun-specific APIs (like `Bun.hash`, `Bun.file`), create minimal stubs in `src/shims/` that provide compatible fallbacks.
### Part F: Test the output
After a successful build:
```bash
node dist/cli.mjs --version
# or
bun dist/cli.mjs --version
```
This should print the version. It will likely crash after that because no API key is configured — that's fine for now.
## Verification
1. `bun scripts/build-bundle.ts` completes without errors
2. `dist/cli.mjs` exists
3. `bun dist/cli.mjs --version` or `node dist/cli.mjs --version` prints a version string
4. `package.json` has `build`, `build:watch`, `build:prod` scripts

View File

@@ -0,0 +1,85 @@
# Prompt 04: Fix MCP Server Build
## Context
You are working in `/workspaces/claude-code/mcp-server/`. This is a separate sub-project that provides an MCP (Model Context Protocol) server for exploring the Claude Code source. It's a simpler, self-contained TypeScript project.
Currently `npm run build` (which runs `tsc`) fails with TypeScript errors.
## Task
1. **Run the build and capture errors**:
```bash
cd /workspaces/claude-code/mcp-server
npm run build 2>&1
```
2. **Fix all TypeScript errors** in `mcp-server/src/server.ts` and `mcp-server/src/index.ts`. Common issues include:
- Duplicate function implementations
- Missing imports
- Type mismatches with the MCP SDK types
3. **Verify the fix**:
```bash
npm run build
```
Should complete with zero errors and produce output in `mcp-server/dist/`.
4. **Test the MCP server runs**:
```bash
node dist/index.js --help 2>&1 || node dist/index.js 2>&1 | head -5
```
It may hang waiting for stdio input (that's normal for an MCP server) — just verify it starts without crashing.
## Key Files
- `mcp-server/package.json` — build script and dependencies
- `mcp-server/tsconfig.json` — TypeScript config
- `mcp-server/src/server.ts` — Main server logic (tools, resources, prompts)
- `mcp-server/src/index.ts` — Entrypoint (stdio transport)
## Verification
1. `cd mcp-server && npm run build` succeeds with zero errors
2. `ls mcp-server/dist/` shows compiled `.js` files
3. `node mcp-server/dist/index.js` starts without immediate crash
---
## Fix: GitHub Push Protection Blocked Push
`git push origin main` is rejected because commits `5e99ad6` and `7adaa5d` contain a **GitHub OAuth token** in `.mcpregistry_github_token`. The file was deleted from disk but still exists in git history. You must rewrite history to remove it.
### Step 1: Scrub secrets from history
```bash
git filter-branch --force --index-filter \
'git rm --cached --ignore-unmatch .mcpregistry_github_token .mcpregistry_registry_token mcp-server/.mcpregistry_github_token mcp-server/.mcpregistry_registry_token' \
--prune-empty HEAD~5..HEAD
```
### Step 2: Push
```bash
git push origin main
```
### Alternative: Interactive rebase
```bash
git rebase -i HEAD~5
# Change "pick" to "edit" for commits 5e99ad6 and 7adaa5d
# At each stop, run:
git rm --cached .mcpregistry_github_token .mcpregistry_registry_token 2>/dev/null
git rm --cached mcp-server/.mcpregistry_github_token mcp-server/.mcpregistry_registry_token 2>/dev/null
git commit --amend --no-edit
git rebase --continue
```
### Step 3: Prevent future leaks
```bash
echo ".mcpregistry_github_token" >> .gitignore
echo ".mcpregistry_registry_token" >> .gitignore
git add .gitignore && git commit -m "chore: gitignore token files"
```

100
prompts/05-env-and-auth.md Normal file
View File

@@ -0,0 +1,100 @@
# Prompt 05: Environment Configuration & API Authentication
## Context
You are working in `/workspaces/claude-code`. The CLI needs an Anthropic API key to function. The auth system supports multiple backends:
- **Direct API** (`ANTHROPIC_API_KEY`) — simplest
- **OAuth** (Claude.ai subscription) — complex browser flow
- **AWS Bedrock** — `AWS_*` env vars
- **Google Vertex AI** — GCP credentials
- **Azure Foundry** — `ANTHROPIC_FOUNDRY_API_KEY`
## Task
### Part A: Create `.env` file from the existing code
Search the codebase for all environment variables used. Key files to check:
- `src/entrypoints/cli.tsx` (reads env vars at top level)
- `src/services/api/client.ts` (API client construction)
- `src/utils/auth.ts` (authentication)
- `src/utils/config.ts` (config loading)
- `src/constants/` (any hardcoded config)
- `src/entrypoints/init.ts` (initialization reads)
Create a `.env.example` file (or update the existing one if it exists) with ALL discoverable env vars, organized by category, with documentation comments. At minimum include:
```env
# ─── Authentication ───
ANTHROPIC_API_KEY= # Required: Your Anthropic API key (sk-ant-...)
# ─── API Configuration ───
ANTHROPIC_BASE_URL= # Custom API endpoint (default: https://api.anthropic.com)
ANTHROPIC_MODEL= # Override default model (e.g., claude-sonnet-4-20250514)
ANTHROPIC_SMALL_FAST_MODEL= # Model for fast/cheap operations (e.g., claude-haiku)
# ─── Feature Flags (used by bun:bundle shim) ───
CLAUDE_CODE_PROACTIVE=false
CLAUDE_CODE_BRIDGE_MODE=false
CLAUDE_CODE_COORDINATOR_MODE=false
CLAUDE_CODE_VOICE_MODE=false
# ─── Debug ───
CLAUDE_CODE_DEBUG_LOG_LEVEL= # debug, info, warn, error
DEBUG=false
```
### Part B: Trace the API client setup
Read `src/services/api/client.ts` to understand how the Anthropic SDK is initialized. Document:
1. What env vars it reads
2. How it selects between API backends (direct, Bedrock, Vertex, etc.)
3. Where the API key comes from (env var? keychain? OAuth token?)
Create a comment block at the top of `.env.example` explaining how auth works.
### Part C: Create a minimal auth test
Create `scripts/test-auth.ts`:
```ts
// scripts/test-auth.ts
// Quick test that the API key is configured and can reach Anthropic
// Usage: bun scripts/test-auth.ts
import Anthropic from '@anthropic-ai/sdk'
const client = new Anthropic({
apiKey: process.env.ANTHROPIC_API_KEY,
})
async function main() {
try {
const msg = await client.messages.create({
model: process.env.ANTHROPIC_MODEL || 'claude-sonnet-4-20250514',
max_tokens: 50,
messages: [{ role: 'user', content: 'Say "hello" and nothing else.' }],
})
console.log('✅ API connection successful!')
console.log('Response:', msg.content[0].type === 'text' ? msg.content[0].text : msg.content[0])
} catch (err: any) {
console.error('❌ API connection failed:', err.message)
process.exit(1)
}
}
main()
```
### Part D: Stub OAuth for development
The OAuth flow (`src/services/oauth/`) requires browser interaction and Anthropic's OAuth endpoints. For development, we want to bypass it.
Search for where the auth decision is made (likely in `src/utils/auth.ts` or `src/entrypoints/init.ts`). Document what would need to be stubbed to skip OAuth and use only `ANTHROPIC_API_KEY`.
Don't modify source files yet — just document findings in a comment at the bottom of `.env.example`.
## Verification
1. `.env.example` exists with comprehensive env var documentation
2. `scripts/test-auth.ts` exists
3. With a valid `ANTHROPIC_API_KEY` set: `bun scripts/test-auth.ts` prints success
4. Without an API key: `bun scripts/test-auth.ts` prints a clear error

View File

@@ -0,0 +1,110 @@
# Prompt 06: Verify and Fix the Ink/React Terminal UI Pipeline
## Context
You are working in `/workspaces/claude-code`. The CLI renders its UI using **React + Ink** — a framework that renders React components to the terminal (not a browser). This project includes a **custom fork of Ink** embedded directly in `src/ink/`.
Key files:
- `src/ink.ts` — Public API (re-exports `render()` and `createRoot()`, wraps with `ThemeProvider`)
- `src/ink/root.ts` — Ink's root renderer
- `src/ink/ink.tsx` — Core Ink component
- `src/ink/reconciler.ts` — React reconciler for terminal output
- `src/ink/dom.ts` — Terminal DOM implementation
- `src/ink/renderer.ts` — Renders virtual DOM to terminal strings
- `src/ink/components/` — Built-in Ink components (Box, Text, etc.)
- `src/components/` — Claude Code's ~140 custom components
## Task
### Part A: Trace the render pipeline
Read these files in order and document the rendering flow:
1. `src/ink.ts` → how `render()` and `createRoot()` work
2. `src/ink/root.ts` → how Ink creates a root and mounts React
3. `src/ink/reconciler.ts` → what React reconciler is used
4. `src/ink/renderer.ts` → how the virtual DOM becomes terminal output
5. `src/ink/dom.ts` → what the "DOM nodes" look like
Create a brief architecture doc in a comment block or README section.
### Part B: Verify Ink components compile
Check that the core Ink components are self-contained:
```
src/ink/components/
```
List them all and verify they don't have missing imports.
### Part C: Check the ThemeProvider
Read `src/components/design-system/ThemeProvider.tsx` (or wherever it lives). Verify it:
1. Exists
2. Exports a `ThemeProvider` component
3. The theme system doesn't depend on external resources
### Part D: Create a minimal render test
Create `scripts/test-ink.tsx`:
```tsx
// scripts/test-ink.tsx
// Minimal test that the Ink terminal UI renders
// Usage: bun scripts/test-ink.tsx
import React from 'react'
// We need the shims loaded first
import './src/shims/preload.js'
// Now try to use Ink
import { render } from './src/ink.js'
// Minimal component
function Hello() {
return <Text>Hello from Claude Code Ink UI!</Text>
}
// Need to import Text from Ink
import { Text } from './src/ink/components/Text.js'
async function main() {
const instance = await render(<Hello />)
// Give it a moment to render
setTimeout(() => {
instance.unmount()
process.exit(0)
}, 500)
}
main().catch(err => {
console.error('Ink render test failed:', err)
process.exit(1)
})
```
Adjust the imports based on what you find — the Text component path may differ.
### Part E: Fix any issues
If Ink rendering fails, the common issues are:
1. **Missing `yoga-wasm-web` or `yoga-layout`** — Ink uses Yoga for flexbox layout. Check if there's a Yoga dependency or if it's embedded.
2. **React version mismatch** — The code uses React 19. Verify the reconciler is compatible.
3. **Terminal detection** — Ink checks if stdout is a TTY. In some environments this may need to be forced.
4. **Missing chalk/ansi dependency** — Terminal colors.
Fix whatever you find to make the test render successfully.
### Part F: Verify component imports
Check that `src/components/` components can import from the Ink system without errors. Pick 3-5 key components:
- `src/components/MessageResponse.tsx` (or similar — the main chat message renderer)
- `src/components/ToolUseResult.tsx` (or similar — tool output display)
- `src/components/PermissionRequest.tsx` (or similar — permission modal)
Read their imports and verify nothing is missing.
## Verification
1. `scripts/test-ink.tsx` renders "Hello from Claude Code Ink UI!" to the terminal
2. No new TypeScript errors introduced
3. You've documented the render pipeline flow

104
prompts/07-tool-system.md Normal file
View File

@@ -0,0 +1,104 @@
# Prompt 07: Audit and Wire Up the Tool System
## Context
You are working in `/workspaces/claude-code`. The Claude Code CLI has ~40 tools that the LLM can invoke during conversations. Each tool is in `src/tools/<ToolName>/` and follows a consistent pattern.
Key files:
- `src/Tool.ts` (~29K lines) — Tool type definitions, `ToolUseContext`, `PermissionResult`, etc.
- `src/tools.ts` — Tool registry (`getTools()` function that returns all available tools)
- `src/tools/` — Individual tool directories
## Task
### Part A: Understand the Tool interface
Read `src/Tool.ts` and document the `Tool` interface. Key questions:
1. What fields does a `Tool` have? (name, description, inputSchema, execute, etc.)
2. What is `ToolUseContext`? What does it provide to tool execution?
3. How do tool permissions work? (`PermissionResult`, `needsPermission`)
4. How do tools declare their input schema? (JSON Schema / Zod)
### Part B: Audit the tool registry
Read `src/tools.ts` fully. It dynamically imports tools behind feature flags and env checks:
```ts
const REPLTool = process.env.USER_TYPE === 'ant' ? ... : null
const SleepTool = feature('PROACTIVE') || feature('KAIROS') ? ... : null
```
Create a complete inventory of:
1. **Always-available tools** — imported unconditionally
2. **Feature-gated tools** — which feature flag enables them
3. **Ant-only tools** — gated behind `USER_TYPE === 'ant'` (Anthropic internal)
4. **Broken/missing tools** — any tools referenced but not found
### Part C: Verify each tool compiles
For each tool directory in `src/tools/`, check:
1. Does it have an `index.ts` or main file?
2. Does it export a tool definition matching the `Tool` interface?
3. Are its imports resolvable?
Focus on the **core 10 tools** that are essential for basic operation:
- `BashTool` — shell command execution
- `FileReadTool` — read files
- `FileWriteTool` — write files
- `FileEditTool` — edit files (search & replace)
- `GlobTool` — find files by pattern
- `GrepTool` — search file contents
- `AgentTool` — spawn sub-agent
- `WebFetchTool` — HTTP requests
- `AskUserQuestionTool` — ask the user for input
- `TodoWriteTool` — todo list management
### Part D: Fix import issues
The tool registry (`src/tools.ts`) uses dynamic imports with `bun:bundle` feature flags. With our runtime shim, these should work — but verify:
1. Feature-gated imports resolve when the flag is `false` (should be skipped)
2. Feature-gated imports resolve when the flag is `true` (should load)
3. Ant-only tools gracefully handle `process.env.USER_TYPE !== 'ant'`
Fix any import resolution errors.
### Part E: Create a tool smoke test
Create `scripts/test-tools.ts`:
```ts
// scripts/test-tools.ts
// Verify all tools load without errors
// Usage: bun scripts/test-tools.ts
import './src/shims/preload.js'
async function main() {
const { getTools } = await import('./src/tools.js')
// getTools() may need arguments — check its signature
const tools = getTools(/* ... */)
console.log(`Loaded ${tools.length} tools:\n`)
for (const tool of tools) {
console.log(`${tool.name}`)
}
}
main().catch(err => {
console.error('Tool loading failed:', err)
process.exit(1)
})
```
Adapt the script to match the actual `getTools()` signature.
### Part F: Stub Anthropic-internal tools
Any tools gated behind `USER_TYPE === 'ant'` should be cleanly excluded. Verify the null checks work and don't cause runtime errors when these tools are missing from the registry.
## Verification
1. `scripts/test-tools.ts` runs and lists all available tools without errors
2. The core 10 tools listed above are all present
3. No TypeScript errors in `src/tools/` or `src/tools.ts`
4. Ant-only tools are cleanly excluded (no crashes)

View File

@@ -0,0 +1,90 @@
# Prompt 08: Audit and Wire Up the Command System
## Context
You are working in `/workspaces/claude-code`. The CLI has ~50 slash commands (e.g., `/commit`, `/review`, `/init`, `/config`). These are registered in `src/commands.ts` and implemented in `src/commands/`.
Key files:
- `src/commands.ts` (~25K lines) — Command registry (`getCommands()`)
- `src/commands/` — Individual command implementations
- `src/types/command.ts` — Command type definition
## Task
### Part A: Understand the Command interface
Read `src/types/command.ts` and the top of `src/commands.ts`. Document:
1. The `Command` type (name, description, execute, args, etc.)
2. How commands are registered
3. How command execution is triggered (from the REPL? from CLI args?)
### Part B: Audit the command registry
Read `src/commands.ts` fully. Create a complete inventory of all commands, organized by category:
**Essential commands** (needed for basic operation):
- `/help` — show help
- `/config` — view/edit configuration
- `/init` — initialize a project
- `/commit` — git commit
- `/review` — code review
**Feature-gated commands** (behind feature flags or USER_TYPE):
- List which flag enables each
**Potentially broken commands** (reference missing imports or services):
- List any that can't resolve their imports
### Part C: Verify core commands compile
For the essential commands listed above, read their implementations and check:
1. All imports resolve
2. They don't depend on unavailable services
3. The function signatures match the Command type
### Part D: Fix import issues
Similar to the tool system, commands may have:
- Feature-gated imports that need the `bun:bundle` shim
- Ant-only code paths
- Dynamic imports that need correct paths
Fix whatever is broken.
### Part E: Handle "moved to plugin" commands
There's a file `src/commands/createMovedToPluginCommand.ts`. Read it — some commands have been migrated to the plugin system. These should gracefully tell the user the command has moved, not crash.
### Part F: Create a command smoke test
Create `scripts/test-commands.ts`:
```ts
// scripts/test-commands.ts
// Verify all commands load without errors
// Usage: bun scripts/test-commands.ts
import './src/shims/preload.js'
async function main() {
const { getCommands } = await import('./src/commands.js')
const commands = getCommands(/* check signature */)
console.log(`Loaded ${commands.length} commands:\n`)
for (const cmd of commands) {
console.log(` /${cmd.name}${cmd.description || '(no description)'}`)
}
}
main().catch(err => {
console.error('Command loading failed:', err)
process.exit(1)
})
```
## Verification
1. `scripts/test-commands.ts` lists all available commands
2. Core commands (`/help`, `/config`, `/init`, `/commit`) are present
3. No runtime crashes from missing imports
4. Moved-to-plugin commands show a friendly message instead of crashing

118
prompts/09-query-engine.md Normal file
View File

@@ -0,0 +1,118 @@
# Prompt 09: Get the QueryEngine (Core LLM Loop) Functional
## Context
You are working in `/workspaces/claude-code`. The `QueryEngine` (`src/QueryEngine.ts`, ~46K lines) is the heart of the CLI — it:
1. Sends messages to the Anthropic API (streaming)
2. Processes streaming responses (text, thinking, tool_use blocks)
3. Executes tools when the LLM requests them (tool loop)
4. Handles retries, rate limits, and errors
5. Tracks token usage and costs
6. Manages conversation context (message history)
This is the most complex single file. The goal is to get it functional enough for a basic conversation loop.
## Key Dependencies
The QueryEngine depends on:
- `src/services/api/client.ts` — Anthropic SDK client
- `src/services/api/claude.ts` — Message API wrapper
- `src/Tool.ts` — Tool definitions
- `src/tools.ts` — Tool registry
- `src/context.ts` — System context
- `src/constants/prompts.ts` — System prompt
- Token counting utilities
- Streaming event handlers
## Task
### Part A: Map the QueryEngine architecture
Read `src/QueryEngine.ts` and create a structural map:
1. **Class structure** — What classes/interfaces are defined?
2. **Public API** — What method starts a query? What does it return?
3. **Message flow** — How does a user message become an API call?
4. **Tool loop** — How are tool calls detected, executed, and fed back?
5. **Streaming** — How are streaming events processed?
6. **Retry logic** — How are API errors handled?
### Part B: Trace the API call path
Follow the chain from QueryEngine → API client:
1. Read `src/services/api/client.ts` — how is the Anthropic SDK client created?
2. Read `src/services/api/claude.ts` — what's the message creation wrapper?
3. What parameters are passed? (model, max_tokens, system prompt, tools, messages)
4. How is streaming handled? (SSE? SDK streaming?)
### Part C: Identify and fix blockers
The QueryEngine will have dependencies on many subsystems. For each dependency:
- **If it's essential** (API client, tool execution) → make sure it works
- **If it's optional** (analytics, telemetry, policy limits) → stub or skip it
Common blockers:
1. **Missing API configuration** → needs `ANTHROPIC_API_KEY` (Prompt 05)
2. **Policy limits service** → may block execution, needs stubbing
3. **GrowthBook/analytics** → needs stubbing or graceful failure
4. **Remote managed settings** → needs stubbing
5. **Bootstrap data fetch** → may need to be optional
### Part D: Create a minimal conversation test
Create `scripts/test-query.ts` that exercises the QueryEngine directly:
```ts
// scripts/test-query.ts
// Minimal test of the QueryEngine — single query, no REPL
// Usage: ANTHROPIC_API_KEY=sk-ant-... bun scripts/test-query.ts "What is 2+2?"
import './src/shims/preload.js'
async function main() {
const query = process.argv[2] || 'What is 2+2?'
// Import and set up minimal dependencies
// You'll need to figure out the exact imports and initialization
// by reading src/QueryEngine.ts, src/query.ts, and src/replLauncher.tsx
// The basic flow should be:
// 1. Create API client
// 2. Build system prompt
// 3. Create QueryEngine instance
// 4. Send a query
// 5. Print the response
console.log(`Query: ${query}`)
console.log('---')
// TODO: Wire up the actual QueryEngine call
// This is the hardest part — document what you need to do
}
main().catch(err => {
console.error('Query test failed:', err)
process.exit(1)
})
```
### Part E: Handle the streaming response
The QueryEngine likely uses the Anthropic SDK's streaming interface. Make sure:
1. Text content is printed to stdout as it streams
2. Thinking blocks are handled (displayed or hidden based on config)
3. Tool use blocks trigger tool execution
4. The tool loop feeds results back and continues
### Part F: Document what's still broken
After getting a basic query working, document:
1. Which features work
2. Which features are stubbed
3. What would need to happen for full functionality
## Verification
1. `ANTHROPIC_API_KEY=sk-ant-... bun scripts/test-query.ts "What is 2+2?"` gets a response
2. Streaming output appears in real-time
3. No unhandled crashes (graceful error messages are fine)
4. Architecture is documented

View File

@@ -0,0 +1,100 @@
# Prompt 10: Wire Up System Prompt, Context Gathering & Memory System
## Context
You are working in `/workspaces/claude-code`. The CLI constructs a detailed system prompt before each conversation. This prompt includes:
1. **Static instructions** — core behavior rules (from `src/constants/prompts.ts`)
2. **Dynamic context** — OS, shell, git status, working directory (from `src/context.ts`)
3. **Tool descriptions** — auto-generated from tool schemas
4. **Memory** — persistent `.claude.md` files (from `src/memdir/`)
5. **User context** — config, preferences, project settings
## Key Files
- `src/constants/prompts.ts` — System prompt construction
- `src/constants/system.ts` — System identity strings
- `src/context.ts` — OS/shell/git context collection
- `src/context/` — Additional context modules
- `src/memdir/` — Memory directory system (reads `.claude.md`, `CLAUDE.md` files)
- `src/utils/messages.ts` — Message construction helpers
## Task
### Part A: Trace the system prompt construction
Read `src/constants/prompts.ts` and map:
1. What is `getSystemPrompt()`'s signature and return type?
2. What sections does the system prompt contain?
3. How are tools described in the prompt?
4. What model-specific variations exist?
5. Where does the `MACRO.ISSUES_EXPLAINER` reference resolve to?
### Part B: Fix the context gathering
Read `src/context.ts` and:
1. Understand `getSystemContext()` and `getUserContext()`
2. These collect OS info, shell version, git status, etc.
3. Verify they work on Linux (this codebase was likely developed on macOS, so some paths may be macOS-specific)
4. Fix any platform-specific issues
### Part C: Wire up the memory system
Read `src/memdir/` directory:
1. How does it find `.claude.md` / `CLAUDE.md` files?
2. How is memory content injected into the system prompt?
3. Does it support project-level, user-level, and session-level memory?
Verify it works by:
1. Creating a test `CLAUDE.md` in the project root
2. Running the system prompt builder
3. Checking the memory appears in the output
### Part D: Create a prompt inspection script
Create `scripts/test-prompt.ts`:
```ts
// scripts/test-prompt.ts
// Dump the full system prompt that would be sent to the API
// Usage: bun scripts/test-prompt.ts
import './src/shims/preload.js'
async function main() {
// Import the prompt builder
const { getSystemPrompt } = await import('./src/constants/prompts.js')
// May need to pass tools list and model name
// Check the function signature
const prompt = await getSystemPrompt([], 'claude-sonnet-4-20250514')
console.log('=== SYSTEM PROMPT ===')
console.log(prompt.join('\n'))
console.log('=== END ===')
console.log(`\nTotal length: ${prompt.join('\n').length} characters`)
}
main().catch(err => {
console.error('Prompt test failed:', err)
process.exit(1)
})
```
### Part E: Fix MACRO references in prompts
The prompt system references `MACRO.ISSUES_EXPLAINER`. Make sure our `MACRO` global (from `src/shims/macro.ts`) provides this value. If the prompt references other `MACRO` fields, add them too.
### Part F: Context module audit
Check `src/context/` for additional context modules:
- Project detection (language, framework)
- Git integration (branch, status, recent commits)
- Environment detection (CI, container, SSH)
Verify these work in our dev environment.
## Verification
1. `bun scripts/test-prompt.ts` dumps a complete system prompt
2. The prompt includes: tool descriptions, OS context, memory content
3. No `undefined` or `MACRO.` references in the output
4. Memory system reads `.claude.md` from the project root

View File

@@ -0,0 +1,113 @@
# Prompt 11: MCP Client/Server Integration
## Context
You are working in `/workspaces/claude-code`. The CLI has built-in MCP (Model Context Protocol) support:
- **MCP Client** — connects to external MCP servers (tools, resources)
- **MCP Server** — exposes Claude Code itself as an MCP server
MCP lets the CLI use tools provided by external servers and lets other clients use Claude Code as a tool provider.
## Key Files
- `src/services/mcp/` — MCP client implementation
- `src/services/mcp/types.ts` — MCP config types
- `src/entrypoints/mcp.ts` — MCP server mode entrypoint
- `src/tools/MCPTool/` — Tool that calls MCP servers
- `src/tools/ListMcpResourcesTool/` — Lists MCP resources
- `src/tools/ReadMcpResourceTool/` — Reads MCP resources
- `src/tools/McpAuthTool/` — MCP server authentication
- `mcp-server/` — Standalone MCP server sub-project (from Prompt 04)
## Task
### Part A: Understand MCP client architecture
Read `src/services/mcp/` directory:
1. How are MCP servers discovered? (`.mcp.json` config file?)
2. How are MCP server connections established? (stdio, HTTP, SSE?)
3. How are MCP tools registered and made available?
4. What is the `ScopedMcpServerConfig` type?
### Part B: Understand MCP config format
Search for `.mcp.json` or MCP config loading code. Document:
1. Where does the config file live? (`~/.claude/.mcp.json`? project root?)
2. What's the config schema? (server name, command, args, env?)
3. How are multiple servers configured?
Example config you might find:
```json
{
"mcpServers": {
"my-server": {
"command": "node",
"args": ["path/to/server.js"],
"env": {}
}
}
}
```
### Part C: Verify MCP SDK integration
The project uses `@modelcontextprotocol/sdk` (^1.12.1). Check:
1. Is it installed in `node_modules/`?
2. Does the import work: `import { Client } from '@modelcontextprotocol/sdk/client/index.js'`
3. Are there version compatibility issues?
### Part D: Test MCP client with our own server
Create a test that:
1. Starts the `mcp-server/` we fixed in Prompt 04 as a child process
2. Connects to it via stdio using the MCP client from `src/services/mcp/`
3. Lists available tools
4. Calls one tool (e.g., `list_files` or `search_code`)
Create `scripts/test-mcp.ts`:
```ts
// scripts/test-mcp.ts
// Test MCP client/server roundtrip
// Usage: bun scripts/test-mcp.ts
import './src/shims/preload.js'
// TODO:
// 1. Spawn mcp-server as a child process (stdio transport)
// 2. Create MCP client from src/services/mcp/
// 3. Connect client to server
// 4. List tools
// 5. Call a tool
// 6. Print results
```
### Part E: Test MCP server mode
The CLI can run as an MCP server itself (`src/entrypoints/mcp.ts`). Read this file and verify:
1. What tools does it expose?
2. What resources does it provide?
3. Can it be started with `bun src/entrypoints/mcp.ts`?
### Part F: Create sample MCP config
Create a `.mcp.json` in the project root (or wherever the app looks for it) that configures the local MCP server:
```json
{
"mcpServers": {
"claude-code-explorer": {
"command": "node",
"args": ["mcp-server/dist/index.js"],
"env": {
"CLAUDE_CODE_SRC_ROOT": "./src"
}
}
}
}
```
## Verification
1. MCP client code in `src/services/mcp/` loads without errors
2. MCP server mode (`src/entrypoints/mcp.ts`) starts without crashing
3. A roundtrip test (client → server → response) works
4. `.mcp.json` config file is created and parseable

View File

@@ -0,0 +1,123 @@
# Prompt 12: Wire Up Services Layer (Analytics, Policy, Settings, Sessions)
## Context
You are working in `/workspaces/claude-code`. The CLI has several background services that run during operation:
- **Analytics/Telemetry** — GrowthBook feature flags, OpenTelemetry traces
- **Policy Limits** — rate limiting, quota enforcement from Anthropic backend
- **Remote Managed Settings** — server-pushed configuration
- **Session Memory** — persistent conversation history across invocations
- **Bootstrap Data** — initial config fetched from API on startup
Most of these talk to Anthropic's backend servers and will fail in our dev build. The goal is to make them fail gracefully (not crash the app) or provide stubs.
## Key Files
- `src/services/analytics/growthbook.ts` — GrowthBook feature flag client
- `src/services/analytics/` — Telemetry, event logging
- `src/services/policyLimits/` — Rate limit enforcement
- `src/services/remoteManagedSettings/` — Server-pushed settings
- `src/services/SessionMemory/` — Conversation persistence
- `src/services/api/bootstrap.ts` — Initial data fetch
- `src/entrypoints/init.ts` — Where most services are initialized
- `src/cost-tracker.ts` — Token usage and cost tracking
## Task
### Part A: Map the initialization sequence
Read `src/entrypoints/init.ts` carefully. Document:
1. What services are initialized, in what order?
2. Which are blocking (must complete before app starts)?
3. Which are fire-and-forget (async, can fail silently)?
4. What happens if each one fails?
### Part B: Make GrowthBook optional
Read `src/services/analytics/growthbook.ts`:
1. How is GrowthBook initialized?
2. Where is it called from? (feature flag checks throughout the codebase)
3. What happens if initialization fails?
**Goal**: Make GrowthBook fail silently — all feature flag checks should return `false` (default) if GrowthBook is unavailable. This may already be handled, but verify it.
### Part C: Stub policy limits
Read `src/services/policyLimits/`:
1. What limits does it enforce? (messages per minute, tokens per day, etc.)
2. What happens when a limit is hit?
3. Where is `loadPolicyLimits()` called?
**Goal**: Make the app work without policy limits. Either:
- Stub the service to return "no limits" (allow everything)
- Or catch and ignore errors from the API call
### Part D: Make remote settings optional
Read `src/services/remoteManagedSettings/`:
1. What settings does it manage?
2. What's the fallback when the server is unreachable?
**Goal**: Ensure the app works with default settings when the remote endpoint fails.
### Part E: Handle bootstrap data
Read `src/services/api/bootstrap.ts`:
1. What data does it fetch?
2. What uses this data?
3. What happens if the fetch fails?
**Goal**: Provide sensible defaults when bootstrap fails (no API key = no bootstrap).
### Part F: Verify session memory
Read `src/services/SessionMemory/`:
1. Where is session data stored? (filesystem path)
2. How are sessions identified?
3. Does it work with the local filesystem?
**Goal**: Session memory should work out of the box since it's local filesystem.
### Part G: Wire up cost tracking
Read `src/cost-tracker.ts`:
1. How are costs calculated?
2. Where is usage reported?
3. Does it persist across sessions?
**Goal**: Cost tracking should work locally (just display, no remote reporting needed).
### Part H: Create a services smoke test
Create `scripts/test-services.ts`:
```ts
// scripts/test-services.ts
// Test that all services initialize without crashing
// Usage: bun scripts/test-services.ts
import './src/shims/preload.js'
async function main() {
console.log('Testing service initialization...')
// Try to run the init sequence
try {
const { init } = await import('./src/entrypoints/init.js')
await init()
console.log('✅ Services initialized')
} catch (err: any) {
console.error('❌ Init failed:', err.message)
// Document which service failed and why
}
}
main()
```
## Verification
1. `bun scripts/test-services.ts` completes without crashing (warnings are fine)
2. Missing remote services log warnings, not crashes
3. Session memory reads/writes to the local filesystem
4. Cost tracking displays locally
5. The app can start even when Anthropic's backend is unreachable (with just an API key)

75
prompts/13-bridge-ide.md Normal file
View File

@@ -0,0 +1,75 @@
# Prompt 13: Bridge Layer (VS Code / JetBrains IDE Integration)
## Context
You are working in `/workspaces/claude-code`. The "Bridge" is the subsystem that connects Claude Code to IDE extensions (VS Code, JetBrains). It enables:
- Remote control of Claude Code from an IDE
- Sharing file context between IDE and CLI
- Permission approvals from the IDE UI
- Session management across IDE and terminal
The Bridge is **gated behind `feature('BRIDGE_MODE')`** and is the most complex optional subsystem (~30 files in `src/bridge/`).
## Key Files
- `src/bridge/bridgeMain.ts` — Main bridge orchestration
- `src/bridge/bridgeApi.ts` — Bridge API endpoints
- `src/bridge/bridgeMessaging.ts` — WebSocket/HTTP messaging
- `src/bridge/bridgeConfig.ts` — Bridge configuration
- `src/bridge/bridgeUI.ts` — Bridge UI rendering
- `src/bridge/jwtUtils.ts` — JWT authentication for bridge connections
- `src/bridge/types.ts` — Bridge types
- `src/bridge/initReplBridge.ts` — REPL integration
- `src/bridge/replBridge.ts` — REPL bridge handle
## Task
### Part A: Understand the bridge architecture
Read `src/bridge/types.ts` and `src/bridge/bridgeMain.ts` (first 100 lines). Document:
1. What protocols does the bridge use? (WebSocket, HTTP polling, etc.)
2. How does authentication work? (JWT)
3. What messages flow between IDE and CLI?
4. How is the bridge lifecycle managed?
### Part B: Assess what's needed vs. what can be deferred
The bridge is a **nice-to-have** for initial build-out. Categorize:
1. **Must work**: Feature flag gate (`feature('BRIDGE_MODE')` returns `false` → bridge code is skipped)
2. **Can defer**: Full bridge functionality
3. **Might break**: Code paths that assume bridge is available even when disabled
### Part C: Verify the feature gate works
Ensure that when `CLAUDE_CODE_BRIDGE_MODE=false` (or unset):
1. Bridge code is not imported
2. Bridge initialization is skipped
3. No bridge-related errors appear
4. The CLI works normally in terminal-only mode
### Part D: Stub the bridge for safety
If any code paths reference bridge functionality outside the feature gate:
1. Create `src/bridge/stub.ts` with no-op implementations
2. Make sure imports from `src/bridge/` resolve without crashing
3. Ensure the REPL works without bridge
### Part E: Document bridge activation
For future work, document what would be needed to enable the bridge:
1. Set `CLAUDE_CODE_BRIDGE_MODE=true`
2. What IDE extension is needed?
3. What authentication setup is required?
4. What ports/sockets does it use?
### Part F: Check the Chrome extension bridge
There's a `--claude-in-chrome-mcp` and `--chrome-native-host` mode referenced in `src/entrypoints/cli.tsx`. Read these paths and document what they do. These can be deferred — just make sure they don't crash when not in use.
## Verification
1. CLI works normally with bridge disabled (default)
2. No bridge-related errors in stdout/stderr
3. `feature('BRIDGE_MODE')` correctly returns `false`
4. Bridge architecture is documented for future enablement
5. No dangling imports that crash when bridge is off

137
prompts/14-dev-runner.md Normal file
View File

@@ -0,0 +1,137 @@
# Prompt 14: Create Development Runner
## Context
You are working in `/workspaces/claude-code`. By now you should have:
- Bun installed (Prompt 01)
- Runtime shims for `bun:bundle` and `MACRO` (Prompt 02)
- A build system (Prompt 03)
- Environment config (Prompt 05)
Now we need a way to **run the CLI in development mode** — quickly launching it without a full production build.
## Task
### Part A: Create `bun run dev` script
Bun can run TypeScript directly without compilation. Create a development launcher.
**Option 1: Direct Bun execution** (preferred)
Create `scripts/dev.ts`:
```ts
// scripts/dev.ts
// Development launcher — runs the CLI directly via Bun
// Usage: bun scripts/dev.ts [args...]
// Or: bun run dev [args...]
// Load shims first
import '../src/shims/preload.js'
// Register bun:bundle module resolver
// Since Bun natively supports the module, we may need to
// register our shim. Check if this is needed.
// Launch the CLI
await import('../src/entrypoints/cli.js')
```
**Option 2: Bun with preload**
Use Bun's `--preload` flag:
```bash
bun --preload ./src/shims/preload.ts src/entrypoints/cli.tsx
```
**Investigate which approach works** with the `bun:bundle` import. The tricky part is that `bun:bundle` is a special Bun module name — at runtime (without the bundler), Bun may not recognize it. You'll need to either:
1. Use Bun's `bunfig.toml` to create a module alias
2. Use a loader/plugin to intercept the import
3. Use a pre-transform step to rewrite imports
### Part B: Handle the `bun:bundle` import at runtime
This is the critical challenge. Options to investigate:
**Option A: `bunfig.toml` alias**
```toml
[resolve]
alias = { "bun:bundle" = "./src/shims/bun-bundle.ts" }
```
**Option B: Bun plugin**
Create a Bun plugin that intercepts `bun:bundle`:
```ts
// scripts/bun-plugin-shims.ts
import { plugin } from 'bun'
plugin({
name: 'bun-bundle-shim',
setup(build) {
build.onResolve({ filter: /^bun:bundle$/ }, () => ({
path: resolve(import.meta.dir, '../src/shims/bun-bundle.ts'),
}))
},
})
```
Then reference it in `bunfig.toml`:
```toml
preload = ["./scripts/bun-plugin-shims.ts"]
```
**Option C: Patch at build time**
If runtime aliasing doesn't work, use a quick pre-build transform that replaces `from 'bun:bundle'` with `from '../shims/bun-bundle.js'` across all files, outputting to a temp directory.
**Try the options in order** and go with whichever works.
### Part C: Add npm scripts
Add to `package.json`:
```json
{
"scripts": {
"dev": "bun scripts/dev.ts",
"dev:repl": "bun scripts/dev.ts --repl",
"start": "bun scripts/dev.ts"
}
}
```
### Part D: Create a `.env` loader
If the dev script doesn't automatically load `.env`, add dotenv support:
```bash
bun add -d dotenv-cli
```
Then wrap the dev command:
```json
"dev": "dotenv -e .env -- bun scripts/dev.ts"
```
Or use Bun's built-in `.env` loading (Bun automatically reads `.env` files).
### Part E: Test the development runner
1. Set `ANTHROPIC_API_KEY` in `.env`
2. Run `bun run dev --version` → should print version
3. Run `bun run dev --help` → should print help text
4. Run `bun run dev` → should start the interactive REPL (will need working Ink UI)
5. Run `ANTHROPIC_API_KEY=sk-ant-... bun run dev -p "say hello"` → should make one API call and print response
### Part F: Add debug mode
Add a debug script that enables verbose logging:
```json
{
"scripts": {
"dev:debug": "CLAUDE_CODE_DEBUG_LOG_LEVEL=debug bun scripts/dev.ts"
}
}
```
## Verification
1. `bun run dev --version` prints the version
2. `bun run dev --help` prints help without errors
3. The `bun:bundle` import resolves correctly at runtime
4. `.env` variables are loaded
5. No module resolution errors on startup

View File

@@ -0,0 +1,123 @@
# Prompt 15: Production Bundle & Packaging
## Context
You are working in `/workspaces/claude-code`. By now you should have a working development runner (Prompt 14) and build system (Prompt 03). This prompt focuses on creating a production-quality bundle.
## Task
### Part A: Optimize the esbuild configuration
Update `scripts/build-bundle.ts` for production:
1. **Tree shaking** — esbuild does this by default, but verify:
- Feature-gated code with `if (feature('X'))` where X is `false` should be eliminated
- `process.env.USER_TYPE === 'ant'` branches should be eliminated (set `define` to replace with `false`)
2. **Define replacements** — Inline constants at build time:
```ts
define: {
'process.env.USER_TYPE': '"external"', // Not 'ant' (Anthropic internal)
'process.env.NODE_ENV': '"production"',
}
```
3. **Minification** — Enable for production (`--minify` flag)
4. **Source maps** — External source maps for production debugging
5. **Target** — Ensure compatibility with both Bun 1.1+ and Node.js 20+
### Part B: Handle chunking/splitting
The full bundle will be large (~2-5 MB minified). Consider:
1. **Single file** — Simplest, works everywhere (recommended for CLI tools)
2. **Code splitting** — Multiple chunks, only useful if we want lazy loading
Go with single file unless it causes issues.
### Part C: Create the executable
After bundling to `dist/cli.mjs`:
1. **Add shebang** — `#!/usr/bin/env node` (already in banner)
2. **Make executable** — `chmod +x dist/cli.mjs`
3. **Test it runs** — `./dist/cli.mjs --version`
### Part D: Platform packaging
Create packaging scripts for distribution:
**npm package** (`scripts/package-npm.ts`):
```ts
// Generate a publishable npm package in dist/npm/
// - package.json with bin, main, version
// - The bundled CLI file
// - README.md
```
**Standalone binary** (optional, via Bun):
```bash
bun build --compile src/entrypoints/cli.tsx --outfile dist/claude
```
This creates a single binary with Bun runtime embedded. Not all features will work, but it's worth testing.
### Part E: Docker build
Update the existing `Dockerfile` to produce a runnable container:
```dockerfile
FROM oven/bun:1-alpine AS builder
WORKDIR /app
COPY package.json bun.lockb* ./
RUN bun install --frozen-lockfile || bun install
COPY . .
RUN bun run build:prod
FROM oven/bun:1-alpine
WORKDIR /app
COPY --from=builder /app/dist/cli.mjs /app/
RUN apk add --no-cache git ripgrep
ENTRYPOINT ["bun", "/app/cli.mjs"]
```
### Part F: Verify production build
1. `bun run build:prod` succeeds
2. `ls -lh dist/cli.mjs` — check file size
3. `node dist/cli.mjs --version` — works with Node.js
4. `bun dist/cli.mjs --version` — works with Bun
5. `ANTHROPIC_API_KEY=... node dist/cli.mjs -p "hello"` — end-to-end works
### Part G: CI build script
Create `scripts/ci-build.sh`:
```bash
#!/bin/bash
set -euo pipefail
echo "=== Installing dependencies ==="
bun install
echo "=== Type checking ==="
bun run typecheck
echo "=== Linting ==="
bun run lint
echo "=== Building ==="
bun run build:prod
echo "=== Verifying build ==="
node dist/cli.mjs --version
echo "=== Done ==="
```
## Verification
1. `bun run build:prod` produces `dist/cli.mjs`
2. The bundle is < 10 MB (ideally < 5 MB)
3. `node dist/cli.mjs --version` works
4. `docker build .` succeeds (if Docker is available)
5. CI script runs end-to-end without errors

125
prompts/16-testing.md Normal file
View File

@@ -0,0 +1,125 @@
# Prompt 16: Add Test Infrastructure & Smoke Tests
## Context
You are working in `/workspaces/claude-code`. The leaked source does not include any test files or test configuration (they were presumably in a separate directory or repo). We need to add a test framework and write smoke tests for core subsystems.
## Task
### Part A: Set up Vitest
```bash
bun add -d vitest @types/node
```
Create `vitest.config.ts`:
```ts
import { defineConfig } from 'vitest/config'
import { resolve } from 'path'
export default defineConfig({
test: {
globals: true,
environment: 'node',
include: ['tests/**/*.test.ts'],
setupFiles: ['tests/setup.ts'],
testTimeout: 30000,
},
resolve: {
alias: {
'bun:bundle': resolve(__dirname, 'src/shims/bun-bundle.ts'),
},
},
})
```
Create `tests/setup.ts`:
```ts
// Global test setup
import '../src/shims/preload.js'
```
Add to `package.json`:
```json
{
"scripts": {
"test": "vitest run",
"test:watch": "vitest"
}
}
```
### Part B: Write unit tests for shims
`tests/shims/bun-bundle.test.ts`:
- Test `feature()` returns `false` for unknown flags
- Test `feature()` returns `false` for disabled flags
- Test `feature()` returns `true` when env var is set
- Test `feature('ABLATION_BASELINE')` always returns `false`
`tests/shims/macro.test.ts`:
- Test `MACRO.VERSION` is a string
- Test `MACRO.PACKAGE_URL` is set
- Test `MACRO.ISSUES_EXPLAINER` is set
### Part C: Write smoke tests for core modules
`tests/smoke/tools.test.ts`:
- Test that `getTools()` returns an array
- Test that each tool has: name, description, inputSchema
- Test that BashTool, FileReadTool, FileWriteTool are present
`tests/smoke/commands.test.ts`:
- Test that `getCommands()` returns an array
- Test that each command has: name, execute function
- Test that /help and /config commands exist
`tests/smoke/context.test.ts`:
- Test that `getSystemContext()` returns OS info
- Test that git status can be collected
- Test that platform detection works on Linux
`tests/smoke/prompt.test.ts`:
- Test that `getSystemPrompt()` returns a non-empty array
- Test that the prompt includes tool descriptions
- Test that MACRO references are resolved (no `undefined`)
### Part D: Write integration tests (if API key available)
`tests/integration/api.test.ts`:
- Skip if `ANTHROPIC_API_KEY` is not set
- Test API client creation
- Test a simple message (hello world)
- Test streaming works
- Test tool use (calculator-style tool call)
`tests/integration/mcp.test.ts`:
- Test MCP server starts
- Test MCP client connects
- Test tool listing
- Test tool execution roundtrip
### Part E: Write build tests
`tests/build/bundle.test.ts`:
- Test that `dist/cli.mjs` exists after build
- Test that it has a shebang
- Test that it's not empty
- Test that `node dist/cli.mjs --version` exits cleanly
### Part F: Add pre-commit hook (optional)
If the project uses git hooks, add:
```bash
# In package.json or a git hook
bun run typecheck && bun run test
```
## Verification
1. `bun run test` runs all tests
2. Shim tests pass
3. Smoke tests pass (tools, commands, context, prompts load)
4. Integration tests are skipped when no API key is set
5. Integration tests pass when API key is available
6. Test output is clear and readable