Skip to content

fix(web-ui): clear sidebar-close timeout on unmount#486

Merged
AbirAbbas merged 2 commits intomainfrom
fix/flaky-workflowdag-unmount-timeout
Apr 20, 2026
Merged

fix(web-ui): clear sidebar-close timeout on unmount#486
AbirAbbas merged 2 commits intomainfrom
fix/flaky-workflowdag-unmount-timeout

Conversation

@AbirAbbas
Copy link
Copy Markdown
Contributor

Summary

  • handleCloseSidebar in WorkflowDAG/index.tsx:771 scheduled a 300ms setTimeout(() => setSelectedNode(null)) to clear the selected node after the slide-out animation, but never tracked the handle
  • If the component unmounted inside the 300ms window — routine in tests — the timer still fired, called setState on an unmounted component, and React's internals threw ReferenceError: window is not defined after the vitest env was torn down
  • Surfaced as a flaky coverage (web-ui) job; example failure on refactor(control-plane): split handlers/nodes.go into 5 focused files #481 here. Tests themselves all passed (583/583); the unhandled error is what failed the job
  • Fix: track the timeout handle in a ref, clear it on re-invocation, and clear it on unmount via a useEffect cleanup

Test plan

  • npm test -- --run src/test/components/WorkflowDAG/workflowDagSupplemental.test.tsx passes with no unhandled errors
  • Full WorkflowDAG/ test directory: pre-existing TZ-dependent failure in workflowDagNodeWrapperLine.test.tsx reproduces on clean main and is unrelated
  • CI green on coverage (web-ui)

handleCloseSidebar scheduled a 300ms setTimeout to clear the selected
node after the close animation, but never tracked the handle. If the
component unmounted within that window — common in tests — the timer
still fired, called setState on an unmounted component, and React's
internals threw "ReferenceError: window is not defined" after the test
environment was torn down. Track the handle in a ref, clear on
re-invocation, and clear on unmount.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@AbirAbbas AbirAbbas requested a review from a team as a code owner April 20, 2026 13:05
@github-actions
Copy link
Copy Markdown
Contributor

github-actions bot commented Apr 20, 2026

📊 Coverage gate

Thresholds from .coverage-gate.toml: per-surface ≥ 86%, aggregate ≥ 88%, max per-surface regression ≤ 1.0 pp, max aggregate regression ≤ 0.50 pp.

Surface Current Baseline Δ
control-plane 87.20% 87.30% ↓ -0.10 pp 🟡
sdk-go 90.70% 90.70% → +0.00 pp 🟢
sdk-python 93.63% 93.63% ↑ +0.00 pp 🟢
sdk-typescript 92.63% 92.56% ↑ +0.07 pp 🟢
web-ui 90.03% 90.01% ↑ +0.02 pp 🟢
aggregate 88.99% 89.01% ↓ -0.02 pp 🟡

✅ Gate passed

No surface regressed past the allowed threshold and the aggregate stayed above the floor.

@github-actions
Copy link
Copy Markdown
Contributor

github-actions bot commented Apr 20, 2026

📐 Patch coverage gate

Threshold: 80% on lines this PR touches vs origin/main (from .coverage-gate.toml:thresholds.min_patch).

Surface Touched lines Patch coverage Status
control-plane 0 ➖ no changes
sdk-go 0 ➖ no changes
sdk-python 0 ➖ no changes
sdk-typescript 0 ➖ no changes
web-ui 17 100.00%

✅ Patch gate passed

Every surface whose lines were touched by this PR has patch coverage at or above the threshold.

Adds a test that opens, closes, reopens, and recloses the sidebar to
exercise the clearTimeout branch on a pending handle, then waits long
enough for the deferred setSelectedNode(null) callback to actually
execute. Brings patch coverage on this PR's touched lines from 76% to
100%.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@AbirAbbas AbirAbbas merged commit 0c5fa96 into main Apr 20, 2026
18 checks passed
@AbirAbbas AbirAbbas deleted the fix/flaky-workflowdag-unmount-timeout branch April 20, 2026 13:27
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.

1 participant