2026-05-15: Fix backend crash on desktop launch — npx in stripped PATH
Problem
Section titled “Problem”After v1.2.5 fixed lib.rs, the desktop app passed the Prisma migration step but the backend failed to become healthy:
Backend health check 1/30 ……Backend did not become healthy after 30 attemptsSome services failed to startRoot cause: backend/src/main.ts also calls execSync('npx prisma migrate deploy') inside NestJS bootstrap. When Tauri spawns the backend with macOS stripped PATH (/usr/bin:/bin:/usr/sbin:/sbin), npx is not found → backend crashes immediately → health checks all fail.
There were two separate places calling npx prisma:
src-tauri/src/lib.rs— fixed in v1.2.5backend/src/main.ts— fixed in this release
Replace execSync('npx prisma migrate deploy') with:
const prismaJs = path.join(__dirname, '..', 'node_modules', 'prisma', 'build', 'index.js');execFileSync(process.execPath, [prismaJs, 'migrate', 'deploy'], { stdio: 'inherit', env: { ...process.env },});process.execPath= absolute path to the running node binary (set by Tauri’sfind_node()call) — works without PATHprismaJs= local prisma binary frombackend/node_modules/— works without PATH- Also works in Docker and
npm run start:devmodes (same node binary, same local prisma)
AGENTS.md checklist
Section titled “AGENTS.md checklist”| # | Convention | Check |
|---|---|---|
| 1 | Docs | This plan + execution summary |
| 2 | Test gates | Backend unit + build + tauri:install launch |
| 3 | Self-review | ✅ |
| 4 | Endpoint coverage | N/A |
| 5 | Bug-to-Test | tauri:install + double-click verify |
| 6 | Seed isolation | N/A |
| 7 | Transaction invariants | N/A |
| 8 | Plan history | ✅ this file |
| 9 | Infra test gate | npm run tauri:install + launch verify |
| 10 | Env compat | N/A |
| 11 | Do-no-harm | Docker/dev mode migration still works |
| 12 | Execution summary | Append after done |
| 13 | Doc grep | N/A |
| 14 | Semver release | v1.2.6 patch |
Execution Summary
Section titled “Execution Summary”Commit: 52a118f
Actual changes
Section titled “Actual changes”backend/src/main.ts— replacedexecSync('npx prisma migrate deploy')withexecFileSync(process.execPath, [prismaJs, 'migrate', 'deploy'])using localnode_modules/prisma/build/index.js
Deviations from plan
Section titled “Deviations from plan”None.
Test results
Section titled “Test results”| Gate | Result |
|---|---|
Backend build (nest build) | ✅ success |
Backend unit (npm test) | ✅ 319 tests passed |
npm run tauri:install | ✅ built and installed |
| Double-click launch | ✅ backend healthy on port 3456, dashboard loads |
| Backend e2e | ⏭ not affected |
| Frontend unit / e2e | ⏭ not affected |
Key discoveries
Section titled “Key discoveries”backend/dist/is gitignored — tauri-build.sh rebuilds it from source duringnpm run tauri:install. The fix only needs to be insrc/main.ts.process.execPathin the child NestJS process equals the node binary that Tauri used to spawn it (find_node()result), so the pattern is self-consistent.__dirnamein compiled CJSdist/main.js=backend/dist/, sopath.join(__dirname, '..', 'node_modules', ...)=backend/node_modules/prisma/build/index.js✅