Skip to content

fix(app): surface uninstall failures instead of reporting false success#1973

Draft
martin-helmich wants to merge 1 commit into
masterfrom
fix/1970-uninstall-false-success
Draft

fix(app): surface uninstall failures instead of reporting false success#1973
martin-helmich wants to merge 1 commit into
masterfrom
fix/1970-uninstall-false-success

Conversation

@martin-helmich

Copy link
Copy Markdown
Member

Problem

mw app uninstall <id> --force printed both an error and Process completed successfully, and appeared to exit 0, even when the uninstall actually failed with HTTP 412 (the app has a linked primary database). Scripts could not detect the failure, and the reason was not surfaced.

Root cause

DeleteBaseCommand.exec() caught errors thrown by deleteResource() and marked the step as failed, but then still called process.complete(...). The SimpleProcessRenderer (used in non-TTY/CI contexts) unconditionally writes Completed: Process completed successfully in complete(), so a failed deletion was reported as a success.

Fix

  • DeleteBaseCommand now calls process.error(err) in the catch branch instead of process.complete(...), so the failure is surfaced. It keeps ux.exit(1) to guarantee a non-zero exit code. This corrects all delete commands.
  • app uninstall now maps the HTTP 412 (linked primary database) to an actionable message — "cannot uninstall: app has a linked primary database — unlink or repurpose it first ..." — while passing every other error through unchanged (with the original error attached as cause).

Tests

  • src/lib/basecommands/DeleteBaseCommand.test.tsx — asserts that on a failing deletion the command does not report success, surfaces the error via process.error, and exits non-zero (ExitError with oclif.exit === 1); and that a successful deletion still reports success and does not exit non-zero.
  • src/commands/app/uninstall.test.ts — covers the 412 → primary-database message mapping and pass-through of other errors.

Closes #1970

🤖 Generated with Claude Code

DeleteBaseCommand caught errors thrown by deleteResource() but then still
called process.complete(), which made the SimpleProcessRenderer print
"Process completed successfully" even though the deletion had failed. The
command therefore reported success (and appeared to exit 0) when e.g.
`app uninstall` was rejected with HTTP 412.

The catch branch now calls process.error() so the failure is surfaced, and
keeps ux.exit(1) to guarantee a non-zero exit code for scripts.

Additionally, `app uninstall` now maps the HTTP 412 that the API returns for
an app with a linked primary database to an actionable message instead of a
raw Axios error, while passing all other errors through unchanged.

Closes #1970
@martin-helmich martin-helmich marked this pull request as draft July 2, 2026 19:44
* unchanged so they are not accidentally swallowed.
*/
export function mapUninstallError(err: unknown): unknown {
if (axios.isAxiosError(err) && err.response?.status === 412) {

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unsure if this can't be done more elegantly. Also don't know if there are other conditions in which a 412 status code might arise. Should investigate if there's a more specific error code in the response body that we could filter for.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

mw app uninstall reports success despite failing with HTTP 412 (linked primary DB)

2 participants