---
number: 12148
title: 'fix(build): bootstrapWorktree CLI resolves projectRoot to repo root (#12147)'
author: neo-opus-ada
state: MERGED
createdAt: '2026-05-28T19:50:23Z'
updatedAt: '2026-05-28T20:14:29Z'
closedAt: '2026-05-28T20:14:23Z'
mergedAt: '2026-05-28T20:14:23Z'
head: fix/bootstrap-projectroot-12147
base: dev
url: 'https://github.com/neomjs/neo/pull/12148'
---
Resolves #12147

Authored by Claude Opus 4.7 (Claude Code). Session efd8dc2e-2052-4089-814a-ab22cd8c6a62.

FAIR-band: operator-directed quick-win — surfaced and greenlit by @tobiu during #12145; FAIR-band self-selection is N/A for directed work.

Evidence: L2 (unit-tested helper resolves `<root>/ai/scripts/migrations` → `<root>` + a regression guard; 35/35 bootstrapWorktree spec passing) → L2 sufficient (pure path-math fix, fully unit-covered). A post-merge L3 CLI run is optional confirmation.

## Summary

The `isMain` CLI block computed `path.resolve(__dirname, '..', '..')`, but the script lives at `ai/scripts/migrations/` (3 levels deep) — two `..` climbs only to `<root>/ai`, not the repo root. Config copies then landed in `<root>/ai/ai/`, the real `ai/config.mjs` never materialized, and worktree bootstrap left every `ai/services.mjs` consumer at `ERR_MODULE_NOT_FOUND`. The comment ("ai/scripts/ → ai/ → root") was stale from before the file moved into `migrations/`.

- Extract `resolveCliProjectRoot(moduleDir)` (three `..`), exported so the CLI `projectRoot` computation is unit-testable.
- `isMain` uses the helper; corrected the stale comment.
- Spec asserts the helper resolves to root + a regression guard for the prior 2-level mislanding.

## Deltas from ticket (if any)

None — implementation matches the ticket's prescription (extract + correct + test).

## Test Evidence

`npm run test-unit -- test/playwright/unit/ai/scripts/migrations/bootstrapWorktree.spec.mjs` → **35/35 passing**, including the new `resolveCliProjectRoot` case.

## Post-Merge Validation
- [ ] `node ai/scripts/migrations/bootstrapWorktree.mjs` in a fresh worktree hydrates `config.mjs` files at the repo root (no `ai/ai/` stray).

## Commits
- `d7f19c07d` — `resolveCliProjectRoot` helper + corrected level count + spec coverage
