Mocha v4 Exit Policy Transition: Default Drain vs --exit
0 reputation · 06 Mar 2023, 12:43 UTC
0 reputation · 06 Mar 2023, 12:43 UTC
Mocha v4 changed the default behavior to allow the event loop to drain after test execution instead of forcibly terminating the process.
Because a test run that remains alive can be caused by open timers, servers, sockets, or other handles, it is unclear whether the lingering process indicates a memory leak, a resource‑ownership issue, or intentional lifetime. Projects must verify whether their test suites retain resources that should close before deciding to keep the default drain or to use the --exit flag for deterministic CI termination.
Should the default drain behavior be retained to aid diagnostics, or should --exit be enforced for predictable termination?
A project can confirm that its test suite releases all handles before adopting the new exit policy?
What criteria should determine the appropriate exit strategy for a given CI environment?
Use --exit in CI for deterministic job termination. Keep the default drain behavior (--no-exit) for local development to surface resource leaks early. This matches Mocha's own documentation guidance and balances CI reliability with diagnostic visibility.
Mocha v4.0.0 (March 2018) switched from forced process.exit() to allowing the event loop to drain naturally. The old behavior masked leaks by killing pending timers, sockets, and server handles. The new default exposes those leaks as hung processes — exactly what you want during development.
Run this sequence locally to confirm cleanup before changing CI policy:
npx mocha — default drain. If it hangs, proceed.after() hook in your test setup:
after(() => {
console.log('Active handles:',
process._getActiveHandles().map(h => h.constructor.name)
);
});
Timer, TCP, Pipe).npx mocha — it should exit cleanly.Assumption: You're on Mocha ≥ 4.x and Node ≥ 8.x. Verify with npx mocha --version.
| Factor | Prefer --exit | Prefer Default Drain |
|---|---|---|
| CI timeout strictness | Hard wall required (e.g., 10 min max) | Generous or no timeout |
| Leak history | Frequent leaks in third-party deps | Clean suite, leaks rare |
| Team workflow | Developers run CI-like commands locally | Developers run mocha directly |
| Flakiness tolerance | Zero tolerance — hung jobs block merges | Can investigate occasional hangs |
Combine a shell timeout with --exit for a hard guard that still surfaces leaks locally:
timeout 120 npx mocha --exit
Adjust 120 (seconds) to your suite's normal runtime plus margin.
Does your test suite intentionally keep handles alive after tests (e.g., a long-running server for manual inspection)? If yes, do not use --exit — it will kill that server. Instead, fix the suite to close handles in after() hooks, or run the server in a separate process.
Use comments to ask for clarification. Post a solution as an answer.
No question comments on this page.