Skip to content

fix(FR-2852): resolve react-doctor error-level findings#7325

Draft
yomybaby wants to merge 1 commit into
mainfrom
fix/FR-2852-react-doctor-errors
Draft

fix(FR-2852): resolve react-doctor error-level findings#7325
yomybaby wants to merge 1 commit into
mainfrom
fix/FR-2852-react-doctor-errors

Conversation

@yomybaby
Copy link
Copy Markdown
Member

@yomybaby yomybaby commented May 9, 2026

Resolves #7323 (FR-2852)

Summary

  • Fix 7 react-doctor/effect-needs-cleanup errors by returning proper cleanup functions for setTimeout / addEventListener registrations:
    • react/src/components/InputNumberWithSlider.tsx
    • react/src/components/NetworkStatusBanner.tsx (both event listeners)
    • react/src/components/ServiceValidationView.tsx (track timeout via ref since it is created inside an async .then)
    • react/src/components/DefaultProviders.tsx
    • packages/backend.ai-ui/src/components/BAIDynamicStepInputNumber.tsx
    • packages/backend.ai-ui/src/components/BAIDynamicUnitInputNumberWithSlider.tsx
    • packages/backend.ai-ui/src/components/BAIFetchKeyButton.tsx (track in-flight turn-off setTimeout via ref so re-runs cancel any pending hide)
  • Fix 1 jsx-a11y/alt-text error: add alt="Run on Backend.AI" to the badge <img> in react/src/components/ImportNotebookForm.tsx.
  • Suppress 4 react-doctor/no-mutable-in-deps false positives. The rule treats any location.* in deps as a mutable global, but location here comes from react-router useLocation(), which is reactive across navigations. Inline react-doctor-disable-next-line keeps the rule active for genuine ref.current / window.location mistakes.
    • react/src/pages/StartPage.tsx
    • react/src/components/MainLayout/MainLayout.tsx
    • react/src/components/MainLayout/WebUISider.tsx
    • react/src/components/PluginLoader.tsx

No behavior changes for the 4 useLocation deps — they were already reactive. Cleanup additions remove real listener / timer leaks.

Test plan

  • bash scripts/verify.sh — Relay / Lint / Format pass; no new TypeScript errors (pre-existing failures in backend.ai-client and DeleteForeverVFolderModalV2.tsx are unrelated).
  • npx -y react-doctor@latest .effect-needs-cleanup, no-mutable-in-deps, and jsx-a11y/alt-text errors all resolved.
  • Manual smoke: navigate between admin / non-admin pages and confirm sider go-back path still updates correctly (WebUISider).
  • Manual smoke: open ServiceValidationView, unmount during validation, confirm no "CannotValidateNow" toast fires post-unmount.

Copy link
Copy Markdown
Member Author

yomybaby commented May 9, 2026


How to use the Graphite Merge Queue

Add either label to this PR to merge it via the merge queue:

  • flow:merge-queue - adds this PR to the back of the merge queue
  • flow:hotfix - for urgent changes, fast-track this PR to the front of the merge queue

You must have a Graphite account in order to use the merge queue. Sign up using this link.

An organization admin has required the Graphite Merge Queue in this repository.

Please do not merge from GitHub as this will restart CI on PRs being processed by the merge queue.

This stack of pull requests is managed by Graphite. Learn more about stacking.

@github-actions github-actions Bot added the size:M 30~100 LoC label May 9, 2026
@yomybaby yomybaby marked this pull request as ready for review May 11, 2026 11:00
@yomybaby yomybaby requested review from Copilot and ironAiken2 May 11, 2026 11:00
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

This PR addresses React Doctor error-level findings across the WebUI and backend.ai-ui package by adding missing useEffect cleanups for timers/listeners, adding missing alt text for an image, and suppressing known false-positives for react-router’s useLocation() values in dependency arrays.

Changes:

  • Added proper cleanup functions for setTimeout and addEventListener registrations to prevent leaks and post-unmount side effects.
  • Added alt="Run on Backend.AI" to the notebook badge image to satisfy jsx-a11y/alt-text.
  • Added targeted react-doctor/no-mutable-in-deps suppressions for useLocation()-derived deps.

Reviewed changes

Copilot reviewed 12 out of 12 changed files in this pull request and generated 4 comments.

Show a summary per file
File Description
react/src/pages/StartPage.tsx Suppresses react-doctor/no-mutable-in-deps for location.search derived from useLocation().
react/src/components/ServiceValidationView.tsx Tracks validation timeout via ref and clears it on unmount.
react/src/components/PluginLoader.tsx Suppresses react-doctor/no-mutable-in-deps for location.pathname derived from useLocation().
react/src/components/NetworkStatusBanner.tsx Adds cleanup removing custom document event listeners.
react/src/components/MainLayout/WebUISider.tsx Suppresses react-doctor/no-mutable-in-deps for location.pathname derived from useLocation().
react/src/components/MainLayout/MainLayout.tsx Suppresses react-doctor/no-mutable-in-deps for location.pathname derived from useLocation().
react/src/components/InputNumberWithSlider.tsx Captures timeout id and clears it in effect cleanup.
react/src/components/ImportNotebookForm.tsx Adds alt text to the Backend.AI badge <img>.
react/src/components/DefaultProviders.tsx Captures and clears the i18n initialization timeout in effect cleanup.
packages/backend.ai-ui/src/components/BAIFetchKeyButton.tsx Introduces timeout ref to manage “min loading display time” behavior.
packages/backend.ai-ui/src/components/BAIDynamicUnitInputNumberWithSlider.tsx Captures timeout id and clears it in effect cleanup.
packages/backend.ai-ui/src/components/BAIDynamicStepInputNumber.tsx Captures timeout id and clears it in effect cleanup.

Comment on lines +80 to 84
turnOffTimeoutRef.current = setTimeout(() => {
setDisplayLoading(false);
turnOffTimeoutRef.current = null;
}, remainingTime);
};
Comment on lines +218 to +222
return () => {
if (validationTimeoutRef.current !== null) {
clearTimeout(validationTimeoutRef.current);
validationTimeoutRef.current = null;
}
Comment on lines +87 to 89
// `location` is from react-router useLocation() — pathname/search are reactive across navigations.
// react-doctor-disable-next-line react-doctor/no-mutable-in-deps
}, [location.search, queryParams.type]);
Comment on lines +362 to 364
// `location` is from react-router useLocation() — pathname is reactive across navigations.
// react-doctor-disable-next-line react-doctor/no-mutable-in-deps
}, [location.pathname]);
@yomybaby yomybaby marked this pull request as draft May 11, 2026 11:30
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size:M 30~100 LoC

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Fix React Doctor error-level findings (effect cleanups, alt-text)

2 participants