mirror of
https://github.com/codeaashu/claude-code.git
synced 2026-04-08 22:28:48 +03:00
124 lines
3.3 KiB
Markdown
124 lines
3.3 KiB
Markdown
# 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
|