#15306: fix: explicit exit after onboarding command completes
stale
size: XS
Cluster:
CLI Enhancements and Fixes
# Fix explicit exit after onboarding command completes
## Summary
Add an explicit process exit after the [onboard](file://src/commands/onboard.ts#12-81) command finishes. This fixes an issue where the CLI process would hang indefinitely after completing the wizard, blocking automated setup scripts (like [docker-setup.sh](file://docker-setup.sh)) which wait for the CLI container to exit before starting the gateway service.
## Underlying Issue
The [onboardCommand](file://src/commands/onboard.ts#12-81) logic completes successfully but leaves lingering event loop handles (e.g., active database connections or intervals), preventing the Node.js process from exiting naturally.
## Changes
- **src/cli/program/register.onboard.ts**: Added `defaultRuntime.exit(0)` to the end of the [onboard](file://src/commands/onboard.ts#12-81) command handler.
- This ensures the process terminates immediately upon successful completion of the wizard.
- The exit call is placed in the CLI handler rather than the reusable [onboardCommand](file://src/commands/onboard.ts#12-81) function to avoid side effects when [onboardCommand](file://src/commands/onboard.ts#12-81) is used by other commands (like `openclaw setup`).
## Verification
- Verified that [docker-setup.sh](file://docker-setup.sh) now proceeds correctly past the onboarding step and starts the `openclaw-gateway` service without hanging.
- Verified that `openclaw setup` continues to work (as [onboardCommand](file://src/commands/onboard.ts#12-81) itself does not exit).
<!-- greptile_comment -->
<h2>Greptile Overview</h2>
<h3>Greptile Summary</h3>
Refactored CLI exit logic from command-specific handler to global entry point. Previously, `defaultRuntime.exit(0)` was called directly in the onboard command handler. Now, a `.then(() => { process.exit(0); })` is attached to `program.parseAsync()` in `src/index.ts`, ensuring all CLI commands exit cleanly after completion. This change maintains correct behavior for both short-lived commands (which complete and trigger the global exit) and long-running commands like `gateway run` (which manage their own lifecycle via signal handlers and never resolve parseAsync).
<h3>Confidence Score: 5/5</h3>
- This PR is safe to merge with minimal risk
- The refactoring is a clean architectural improvement that centralizes CLI exit logic. The change correctly handles both short-lived commands (which complete and exit via the global handler) and long-running commands (which manage their own lifecycle). Test modifications confirm the new behavior is properly validated. The commit history shows this is an intentional evolution from a command-specific fix to a global solution.
- No files require special attention
<sub>Last reviewed commit: 24a927a</sub>
<!-- greptile_other_comments_section -->
<sub>(3/5) Reply to the agent's comments like "Can you suggest a fix for this @greptileai?" or ask follow-up questions!</sub>
<!-- /greptile_comment -->
Most Similar PRs
#12987: fix(cli): exit process after successful command completion
by omair445 · 2026-02-10
84.1%
#8260: fix(macOS): gateway readiness detection + reversible Configure later
by xksteven · 2026-02-03
80.8%
#5823: fix(config): exit cleanly on invalid config instead of high CPU loop
by gavinbmoore · 2026-02-01
80.4%
#17916: [ fix ] : correct config directory path during onboarding
by Dijo-404 · 2026-02-16
79.3%
#6776: fix: CLI commands hang/fail on Fly.io deployments
by jckw · 2026-02-02
78.3%
#11455: fix(gateway): default gateway.mode to local when unset
by AnonO6 · 2026-02-07
77.2%
#16685: Fix cli agents/approvals/discord routing edge cases
by craftowen · 2026-02-15
77.2%
#5496: Fix: Windows path separators stripped in Gateway scheduled task
by giuliozelante · 2026-01-31
77.1%
#4695: Fixed the default CLI image to use published GHCR image
by TASMAYU · 2026-01-30
76.9%
#22658: Fix onboard ignoring OPENCLAW_GATEWAY_TOKEN env var
by Clawborn · 2026-02-21
76.7%