fix(init): tag wizard.outcome on all early-exit paths#1005
Merged
Conversation
Several paths exited without setting wizard.outcome, leaving runs with no outcome tag in Sentry and making the funnel gap unanalyzable: - ctrl+c during a spinner (InkUI.requestCancel) → "abandoned" - user said no at the welcome/confirm prompt (preamble) → "bailed" - user selected "No, exit" at the experimental warning → "bailed" - git status check bailed → "bailed" - resolveInitContext returned null → "bailed" The preamble paths flush cleanly (event loop drains, beforeExit fires) so their tags will reliably reach Sentry. The InkUI path calls process.exit(130) which skips beforeExit, but setting the tag before the setImmediate tick gives the SDK its best chance to flush. Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
Contributor
|
… never-equals check
maskToken("*") must return "*" (the "short tokens are fully masked"
property requires all-asterisk output), which means the "output never
equals original input" property is unsatisfiable for inputs that are
already entirely asterisks. These two constraints are in fundamental
conflict for that edge case.
Fix: add a .filter() pre-condition to exclude all-asterisk tokens from
the never-equals property. Real auth tokens never consist entirely of
asterisks, so this doesn't weaken the practical guarantee.
Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
Contributor
Codecov Results 📊✅ Patch coverage is 100.00%. Project has 4234 uncovered lines. Coverage diff@@ Coverage Diff @@
## main #PR +/-##
==========================================
+ Coverage 81.85% 81.87% +0.02%
==========================================
Files 328 328 —
Lines 23347 23351 +4
Branches 15114 15114 —
==========================================
+ Hits 19109 19117 +8
- Misses 4238 4234 -4
- Partials 1621 1620 -1Generated by Codecov Action |
…al prompt The !confirmed branch in preamble() was the one uncovered line in the patch (75% patch coverage). Adds a test that responds "exit" to the generic continue/exit select so that path executes. Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
…gration vitest requires .rejects.toThrow() to be awaited; bun:test did not. The missing await at the 404 test caused "expected undefined to be defined" in CI after PR #997 landed. Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Without this, a meaningful chunk of wizard runs land in Sentry with no
wizard.outcometag, making the funnel gap unanalyzable. The dashboardshows e.g. 15 started / 5 completed / 5 bailed / 4 errored = 1 missing,
and the missing ones are invisible.
What was happening
Five paths exited the wizard without ever calling
setTag("wizard.outcome", ...):ink-ui.tsrequestCancel()→process.exit(130)ink-ui.tsprocess.exit(130)wizard-runner.tsWizardCancelledErrorinpreamble()wizard-runner.ts!confirmedinpreamble()wizard-runner.ts!gitOkinpreamble()resolveInitContextreturned nullwizard-runner.ts!contextinrunWizard()Changes
ink-ui.ts: importsetTagfrom@sentry/node-core/light, callsetTag("wizard.outcome", "abandoned")before bothprocess.exit(130)calls. Sentry is guaranteed initialized by the time InkUI runs (it's
wrapped by
withTelemetry). The tag is set synchronously before thesetImmediatetick so the SDK has its best shot at flushing it.wizard-runner.ts: addsetTag("wizard.outcome", "bailed")to thefour preamble/context early-return paths. These exit cleanly (event
loop drains,
beforeExitfires, Sentry flushes) so their tags willreliably reach Sentry.
Outcome taxonomy
abandoned— process was hard-killed mid-wizard (ctrl+c during spinner)bailed— user deliberately stopped before the wizard did any workerrored— wizard ran but failed (already tracked)completed— success (already tracked)