diff --git a/CLAUDE.md b/CLAUDE.md index 38a98cb..5cfd632 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -5,6 +5,7 @@ This file provides guidance to Kode automation agents (including those compatibl ## Development Commands ### Essential Development Workflow + ```bash # Install dependencies bun install @@ -15,6 +16,9 @@ bun run dev # Build the CLI wrapper for distribution bun run build +# Pre-release integration testing +bun link + # Clean build artifacts bun run clean @@ -30,12 +34,17 @@ bun run format:check ``` ### Build System Details + - **Primary Build Tool**: Bun (required for development) - **Distribution**: Smart CLI wrapper (`cli.js`) that prefers Bun but falls back to Node.js with tsx loader - **Entry Point**: `src/entrypoints/cli.tsx` -- **Build Output**: `cli.js` (executable wrapper) and `.npmrc` (npm configuration) +- **Build Output**: + - `cli.js` - Cross-platform executable wrapper that uses `process.cwd()` as working directory + - `.npmrc` - npm configuration file with `package-lock=false` and `save-exact=true` + - `dist/` - ESM modules compiled from TypeScript sources ### Publishing + ```bash # Publish to npm (requires build first) npm publish @@ -112,6 +121,7 @@ Each tool follows a consistent pattern in `src/tools/[ToolName]/`: - CLI parameter overrides - Multi-model profile management + ### Context Management - **Message Context Manager** (`src/utils/messageContextManager.ts`): Intelligent context window handling - **Memory Tools** (`src/tools/MemoryReadTool/`, `src/tools/MemoryWriteTool/`): Persistent memory across sessions @@ -205,3 +215,23 @@ const description = typeof tool.description === 'function' 2. Place in appropriate directory based on scope 3. Test with `/agents` command 4. Verify tool permissions work correctly + +### Testing in Other Projects +After making changes, test the CLI in different environments: + +1. **Development Testing**: + ```bash + bun run build # Build with updated cli.js wrapper + bun link # Link globally for testing + ``` + +2. **Test in External Project**: + ```bash + cd /path/to/other/project + kode --help # Verify CLI works and uses correct working directory + ``` + +3. **Verify Working Directory**: + - CLI wrapper uses `process.cwd()` to ensure commands run in user's current directory + - Not in Kode's installation directory + - Essential for file operations and project context diff --git a/scripts/build.mjs b/scripts/build.mjs index a1957fe..de0784e 100644 --- a/scripts/build.mjs +++ b/scripts/build.mjs @@ -1,7 +1,7 @@ #!/usr/bin/env node import { build } from 'esbuild' -import { existsSync, mkdirSync, writeFileSync, cpSync, readFileSync, readdirSync, statSync } from 'node:fs' -import { join, extname, dirname } from 'node:path' +import { existsSync, mkdirSync, writeFileSync, cpSync, readFileSync, readdirSync, statSync, chmodSync } from 'node:fs' +import { join } from 'node:path' const SRC_DIR = 'src' const OUT_DIR = 'dist' @@ -100,12 +100,93 @@ import('./entrypoints/cli.js').catch(err => { console.warn('⚠️ Could not copy yoga.wasm:', err.message) } + // Create cross-platform CLI wrapper + const cliWrapper = `#!/usr/bin/env node + +// Cross-platform CLI wrapper for Kode +// Prefers Bun but falls back to Node.js with tsx loader + +const { spawn } = require('child_process'); +const { existsSync } = require('fs'); +const path = require('path'); + +// Get the directory where this CLI script is installed +const kodeDir = __dirname; +const distPath = path.join(kodeDir, 'dist', 'index.js'); + +// Check if we have a built version +if (!existsSync(distPath)) { + console.error('❌ Built files not found. Run "bun run build" first.'); + process.exit(1); +} + +// Try to use Bun first, then fallback to Node.js with tsx +const runWithBun = () => { + const proc = spawn('bun', ['run', distPath, ...process.argv.slice(2)], { + stdio: 'inherit', + cwd: process.cwd() // Use current working directory, not kode installation directory + }); + + proc.on('error', (err) => { + if (err.code === 'ENOENT') { + // Bun not found, try Node.js + runWithNode(); + } else { + console.error('❌ Failed to start with Bun:', err.message); + process.exit(1); + } + }); + + proc.on('close', (code) => { + process.exit(code); + }); +}; + +const runWithNode = () => { + const proc = spawn('node', [distPath, ...process.argv.slice(2)], { + stdio: 'inherit', + cwd: process.cwd() // Use current working directory, not kode installation directory + }); + + proc.on('error', (err) => { + console.error('❌ Failed to start with Node.js:', err.message); + process.exit(1); + }); + + proc.on('close', (code) => { + process.exit(code); + }); +}; + +// Start with Bun preference +runWithBun(); +`; + + writeFileSync('cli.js', cliWrapper); + + // Make cli.js executable + try { + chmodSync('cli.js', 0o755); + console.log('✅ cli.js made executable'); + } catch (err) { + console.warn('⚠️ Could not make cli.js executable:', err.message); + } + + // Create .npmrc file + const npmrcContent = `# Kode npm configuration +package-lock=false +save-exact=true +`; + + writeFileSync('.npmrc', npmrcContent); + console.log('✅ Build completed for cross-platform compatibility!') console.log('📋 Generated files:') - console.log(' - dist/ (CommonJS modules)') + console.log(' - dist/ (ESM modules)') console.log(' - dist/index.js (main entrypoint)') console.log(' - dist/entrypoints/cli.js (CLI main)') console.log(' - cli.js (cross-platform wrapper)') + console.log(' - .npmrc (npm configuration)') } main().catch(err => {