84 lines
2.5 KiB
JavaScript
84 lines
2.5 KiB
JavaScript
#!/usr/bin/env node
|
|
|
|
import fs from 'node:fs'
|
|
import path from 'node:path'
|
|
import { spawnSync } from 'node:child_process'
|
|
import { fileURLToPath } from 'node:url'
|
|
|
|
function runOrExit(cmd, args, options = {}) {
|
|
const result = spawnSync(cmd, args, {
|
|
stdio: 'inherit',
|
|
...options,
|
|
})
|
|
|
|
if (result.error) {
|
|
console.error(`Failed to run ${cmd}: ${result.error.message}`)
|
|
process.exit(1)
|
|
}
|
|
|
|
if (result.status !== 0) {
|
|
process.exit(result.status ?? 1)
|
|
}
|
|
}
|
|
|
|
function readPackageManagerCommand(repoRoot) {
|
|
const packageJsonPath = path.join(repoRoot, 'package.json')
|
|
const rawPackageJson = fs.readFileSync(packageJsonPath, 'utf8')
|
|
const packageJson = JSON.parse(rawPackageJson)
|
|
const rawPackageManager = packageJson.packageManager
|
|
|
|
if (typeof rawPackageManager !== 'string' || rawPackageManager.trim().length === 0) {
|
|
return 'pnpm'
|
|
}
|
|
|
|
const [packageManagerName] = rawPackageManager.trim().split('@', 1)
|
|
if (!packageManagerName) {
|
|
return 'pnpm'
|
|
}
|
|
|
|
return packageManagerName
|
|
}
|
|
|
|
const scriptDir = path.dirname(fileURLToPath(import.meta.url))
|
|
const uiRepoRoot = path.resolve(scriptDir, '..')
|
|
// Keep the dev runtime target explicit. This workspace can contain multiple
|
|
// sibling repos with the same package name, so auto-discovery is ambiguous and
|
|
// can silently point the UI at the wrong runtime after branch switches.
|
|
const runtimeRepoRoot = process.env.CLAUDE_DEV_RUNTIME_ROOT?.trim()
|
|
|
|
if (!runtimeRepoRoot) {
|
|
console.error(
|
|
'CLAUDE_DEV_RUNTIME_ROOT is required for pnpm dev. ' +
|
|
'Point it at the runtime repo root you want the UI to use in dev.',
|
|
)
|
|
process.exit(1)
|
|
}
|
|
|
|
const runtimePackageJsonPath = path.join(runtimeRepoRoot, 'package.json')
|
|
if (!fs.existsSync(runtimePackageJsonPath)) {
|
|
console.error(
|
|
`CLAUDE_DEV_RUNTIME_ROOT does not look like a repo root: ${runtimeRepoRoot}`,
|
|
)
|
|
process.exit(1)
|
|
}
|
|
|
|
const runtimePackageManager = readPackageManagerCommand(runtimeRepoRoot)
|
|
|
|
if (process.argv.includes('--print-runtime-path')) {
|
|
process.stdout.write(`${runtimeRepoRoot}\n`)
|
|
process.exit(0)
|
|
}
|
|
|
|
// Respect the runtime repo's own package manager. The UI repo uses pnpm, but
|
|
// the runtime may legitimately be a Bun workspace, and forcing pnpm there can
|
|
// fail before the build even starts.
|
|
runOrExit(runtimePackageManager, ['run', 'build:dev'], { cwd: runtimeRepoRoot })
|
|
|
|
const runtimeCliPath = path.join(runtimeRepoRoot, 'cli-dev')
|
|
runOrExit('pnpm', ['run', 'dev:ui'], {
|
|
cwd: uiRepoRoot,
|
|
env: {
|
|
...process.env,
|
|
CLAUDE_CLI_PATH: runtimeCliPath,
|
|
},
|
|
})
|