Commit 64dcc31
authored
🤖 fix: allow ask_user_question back navigation (#1192)
Fix `ask_user_question` back-navigation for single-select answers.
- Removed effect-based auto-advance that re-triggered when navigating
back to an answered question.
- Auto-advance now happens only on the user’s selection event
(single-select, selecting, non-`Other`).
- Added Storybook play test covering: select → advances; click back →
stays; change answer → advances.
Also includes small test-suite stabilizations uncovered while running
`make test-unit`:
- Gate `web_fetch` internet tests behind `TEST_INTEGRATION=1`.
- Reduce timing-based flakiness in background process output tests.
- Guard telemetry client for window-less test environments.
- Skip URL-hash sync in Storybook preview (avoids test-runner navigation
retries).
---
<details>
<summary>📋 Implementation Plan</summary>
# Fix: `ask_user_question` can’t navigate back after answering
(single‑select)
## Diagnosis (why it happens)
In `src/browser/components/tools/AskUserQuestionToolCall.tsx`, there’s a
`useEffect` that **auto-advances** whenever the *current* question is
single-select and has exactly one non-`Other` selection.
Because this effect runs any time `activeIndex` / `currentQuestion`
changes, when you click a previous “section” (the header buttons like
`Approach`, `Platforms`) **you briefly land on that question and then
the effect immediately pushes you forward again**. Result: you can’t
stay on a previously-answered single-select question to edit it.
## Recommended fix (keep auto-advance, but only on the user action)
**Net LoC (product code): ~-10 to -25** (remove effect + ref; add a
small in-handler advance).
1. **Remove the `useEffect`-based auto-advance** and the
`hasUserInteracted` ref.
2. Move auto-advance into the option `toggle()` handler for
**single-select** questions:
- Only advance when the user is **selecting** (not de-selecting) an
option.
- Only advance for **non-`Other`** selections.
- Advance to `activeIndex + 1` (which will naturally hit “Summary” after
the last question).
This preserves the “fast path” UX for single-select while allowing users
to click back to previous sections and change answers.
### Suggested implementation sketch
- In `toggle()`:
- detect `const isSelecting = !checked;`
- after calling `setDraftAnswers(...)`, if `!currentQuestion.multiSelect
&& isSelecting && opt.label !== OTHER_VALUE`, call `setActiveIndex((i)
=> i + 1)`.
- Delete the auto-advance `useEffect` entirely.
## Tests (prevent regression)
### Storybook interaction test (preferred for UI)
1. Add a `play` function to the existing `AskUserQuestionPending` story
(or create a new focused story, e.g. `AskUserQuestionBackNavigation`).
2. Steps in `play`:
- Click an option in the first single-select question → verify the UI
advances to the next question.
- Click the previous section button (`Approach`) → verify the first
question remains visible (i.e., it does **not** auto-jump forward
again).
- Optionally: change the selection and confirm it advances again.
This will run in CI via the existing **“Test / Storybook”** GitHub
Actions job.
### (Optional) unit test if we want belt + suspenders
If you’d like a unit test that runs in `bun test src` too, extract the
“should auto-advance” logic into a small pure helper (e.g.
`shouldAutoAdvanceSingleSelect(...)`) and test:
- navigating back to an already-answered question does **not**
auto-advance
- selecting a new non-`Other` option does
(But the Storybook interaction test should be sufficient and closer to
the real bug.)
## Validation checklist
- Repro the original issue locally (answer single-select → attempt to
click back).
- After fix: you can click back to `Approach` and stay there.
- Run:
- `make test-unit`
- `make storybook-build && make test-storybook`
<details>
<summary>Alternatives considered</summary>
1. **Keep the `useEffect` but add guards** (track “last auto-advanced
question+answer” in a ref).
- Works, but is more stateful and easier to re-break.
2. **Disable auto-advance entirely**.
- Simplest, but changes UX (users must always click Next).
The in-handler auto-advance is the smallest change that preserves
existing intent.
</details>
</details>
---
_Generated with `mux` • Model: `openai:gpt-5.2` • Thinking: `xhigh`_1 parent 4893bc9 commit 64dcc31
File tree
11 files changed
+235
-116
lines changed- .github/workflows
- src
- browser
- components/tools
- stories
- common/telemetry
- node
- orpc
- services
- tools
11 files changed
+235
-116
lines changed| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
75 | 75 | | |
76 | 76 | | |
77 | 77 | | |
78 | | - | |
| 78 | + | |
| 79 | + | |
| 80 | + | |
79 | 81 | | |
80 | 82 | | |
81 | 83 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
54 | 54 | | |
55 | 55 | | |
56 | 56 | | |
| 57 | + | |
| 58 | + | |
| 59 | + | |
| 60 | + | |
57 | 61 | | |
58 | 62 | | |
59 | 63 | | |
| |||
139 | 143 | | |
140 | 144 | | |
141 | 145 | | |
| 146 | + | |
| 147 | + | |
| 148 | + | |
| 149 | + | |
142 | 150 | | |
143 | 151 | | |
144 | | - | |
145 | | - | |
146 | | - | |
| 152 | + | |
| 153 | + | |
| 154 | + | |
| 155 | + | |
| 156 | + | |
147 | 157 | | |
148 | 158 | | |
149 | 159 | | |
| |||
155 | 165 | | |
156 | 166 | | |
157 | 167 | | |
158 | | - | |
| 168 | + | |
159 | 169 | | |
160 | 170 | | |
161 | 171 | | |
| |||
174 | 184 | | |
175 | 185 | | |
176 | 186 | | |
177 | | - | |
| 187 | + | |
178 | 188 | | |
179 | 189 | | |
180 | 190 | | |
| |||
Lines changed: 13 additions & 27 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
1 | 1 | | |
2 | 2 | | |
3 | | - | |
| 3 | + | |
4 | 4 | | |
5 | 5 | | |
6 | 6 | | |
| |||
247 | 247 | | |
248 | 248 | | |
249 | 249 | | |
250 | | - | |
251 | | - | |
252 | | - | |
253 | | - | |
254 | | - | |
255 | | - | |
256 | | - | |
257 | | - | |
258 | | - | |
259 | | - | |
260 | | - | |
261 | | - | |
262 | | - | |
263 | | - | |
264 | | - | |
265 | | - | |
266 | | - | |
267 | | - | |
268 | | - | |
269 | | - | |
270 | | - | |
271 | | - | |
272 | | - | |
273 | | - | |
274 | | - | |
275 | 250 | | |
276 | 251 | | |
277 | 252 | | |
| |||
425 | 400 | | |
426 | 401 | | |
427 | 402 | | |
428 | | - | |
| 403 | + | |
| 404 | + | |
429 | 405 | | |
430 | 406 | | |
431 | 407 | | |
| |||
458 | 434 | | |
459 | 435 | | |
460 | 436 | | |
| 437 | + | |
| 438 | + | |
| 439 | + | |
| 440 | + | |
| 441 | + | |
| 442 | + | |
| 443 | + | |
| 444 | + | |
| 445 | + | |
| 446 | + | |
461 | 447 | | |
462 | 448 | | |
463 | 449 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
13 | 13 | | |
14 | 14 | | |
15 | 15 | | |
| 16 | + | |
16 | 17 | | |
17 | 18 | | |
18 | 19 | | |
| |||
275 | 276 | | |
276 | 277 | | |
277 | 278 | | |
278 | | - | |
| 279 | + | |
279 | 280 | | |
280 | 281 | | |
281 | 282 | | |
282 | 283 | | |
283 | 284 | | |
284 | | - | |
285 | | - | |
286 | | - | |
287 | | - | |
288 | | - | |
289 | | - | |
290 | | - | |
291 | | - | |
292 | | - | |
293 | | - | |
294 | | - | |
295 | | - | |
296 | | - | |
297 | | - | |
298 | | - | |
299 | | - | |
300 | | - | |
301 | | - | |
302 | | - | |
303 | | - | |
304 | | - | |
305 | | - | |
306 | | - | |
307 | | - | |
308 | | - | |
| 285 | + | |
| 286 | + | |
| 287 | + | |
| 288 | + | |
| 289 | + | |
| 290 | + | |
| 291 | + | |
| 292 | + | |
| 293 | + | |
| 294 | + | |
| 295 | + | |
| 296 | + | |
| 297 | + | |
| 298 | + | |
| 299 | + | |
| 300 | + | |
| 301 | + | |
| 302 | + | |
| 303 | + | |
| 304 | + | |
| 305 | + | |
| 306 | + | |
| 307 | + | |
| 308 | + | |
| 309 | + | |
309 | 310 | | |
310 | | - | |
311 | | - | |
| 311 | + | |
312 | 312 | | |
313 | | - | |
314 | | - | |
| 313 | + | |
| 314 | + | |
315 | 315 | | |
316 | 316 | | |
317 | 317 | | |
318 | 318 | | |
319 | 319 | | |
| 320 | + | |
| 321 | + | |
| 322 | + | |
| 323 | + | |
| 324 | + | |
| 325 | + | |
| 326 | + | |
| 327 | + | |
| 328 | + | |
| 329 | + | |
| 330 | + | |
| 331 | + | |
| 332 | + | |
| 333 | + | |
| 334 | + | |
| 335 | + | |
| 336 | + | |
| 337 | + | |
| 338 | + | |
| 339 | + | |
| 340 | + | |
| 341 | + | |
| 342 | + | |
| 343 | + | |
| 344 | + | |
| 345 | + | |
| 346 | + | |
| 347 | + | |
| 348 | + | |
| 349 | + | |
| 350 | + | |
| 351 | + | |
| 352 | + | |
| 353 | + | |
| 354 | + | |
| 355 | + | |
| 356 | + | |
| 357 | + | |
| 358 | + | |
| 359 | + | |
| 360 | + | |
| 361 | + | |
| 362 | + | |
| 363 | + | |
| 364 | + | |
| 365 | + | |
| 366 | + | |
| 367 | + | |
| 368 | + | |
| 369 | + | |
| 370 | + | |
| 371 | + | |
| 372 | + | |
| 373 | + | |
320 | 374 | | |
321 | 375 | | |
322 | 376 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
59 | 59 | | |
60 | 60 | | |
61 | 61 | | |
62 | | - | |
63 | | - | |
64 | | - | |
65 | | - | |
66 | | - | |
67 | | - | |
68 | | - | |
69 | | - | |
70 | | - | |
71 | 62 | | |
72 | 63 | | |
73 | 64 | | |
| |||
82 | 73 | | |
83 | 74 | | |
84 | 75 | | |
| 76 | + | |
| 77 | + | |
| 78 | + | |
| 79 | + | |
| 80 | + | |
| 81 | + | |
85 | 82 | | |
| 83 | + | |
86 | 84 | | |
87 | 85 | | |
88 | | - | |
| 86 | + | |
89 | 87 | | |
90 | 88 | | |
91 | 89 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
1 | 1 | | |
2 | 2 | | |
3 | 3 | | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
4 | 9 | | |
5 | 10 | | |
6 | 11 | | |
| |||
26 | 31 | | |
27 | 32 | | |
28 | 33 | | |
29 | | - | |
30 | | - | |
31 | | - | |
| 34 | + | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
32 | 38 | | |
33 | 39 | | |
34 | 40 | | |
| |||
41 | 47 | | |
42 | 48 | | |
43 | 49 | | |
44 | | - | |
| 50 | + | |
45 | 51 | | |
46 | 52 | | |
47 | 53 | | |
48 | 54 | | |
49 | | - | |
50 | 55 | | |
51 | | - | |
| 56 | + | |
| 57 | + | |
| 58 | + | |
52 | 59 | | |
53 | 60 | | |
54 | 61 | | |
55 | | - | |
56 | | - | |
| 62 | + | |
| 63 | + | |
57 | 64 | | |
58 | 65 | | |
59 | 66 | | |
| |||
65 | 72 | | |
66 | 73 | | |
67 | 74 | | |
68 | | - | |
69 | | - | |
| 75 | + | |
| 76 | + | |
70 | 77 | | |
71 | 78 | | |
72 | 79 | | |
73 | 80 | | |
74 | | - | |
| 81 | + | |
75 | 82 | | |
76 | 83 | | |
77 | 84 | | |
| |||
0 commit comments