fix(cli): sync footer branch name on filesystems without fs.watch events#28012
fix(cli): sync footer branch name on filesystems without fs.watch events#28012manumishra12 wants to merge 5 commits into
Conversation
The footer "Branch" item is driven by useGitBranchName, which watches the git directory with fs.watch and re-fetches the branch when HEAD changes. fs.watch relies on the OS notification layer (inotify/FSEvents), which delivers no events on some filesystems — most notably WSL mounts of Windows drives and network shares — so `git checkout` never updates the displayed branch in those environments. Add a stat-based fs.watchFile poll on HEAD as a reliable fallback alongside the existing fs.watch, refresh through a shared debounced helper, and tear the poll down on unmount. Extend the tests to cover the polling path and its cleanup. Fixes google-gemini#27957
Summary of ChangesHello, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed! This pull request addresses an issue where the CLI's git branch indicator fails to update after a checkout on specific filesystems that do not support standard OS-level file watch events. By introducing a lightweight stat-based polling fallback for the Highlights
Using Gemini Code AssistThe full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips. Invoking Gemini You can request assistance from Gemini at any point by creating a comment using either
Customization To customize the Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a Limitations & Feedback Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counterproductive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for GitHub and other Google products, sign up here. Footnotes
|
|
📊 PR Size: size/M
|
There was a problem hiding this comment.
Code Review
This pull request introduces a polling fallback mechanism using fs.watchFile on the Git HEAD file to ensure the branch name updates correctly on filesystems where fs.watch does not deliver events (such as WSL mounts or network shares). It also adds corresponding unit tests to verify this behavior and ensure proper cleanup on unmount. The review feedback highlights a critical issue where calling fs.unwatchFile with only the file path removes all listeners for that file across all active hook instances. To prevent this, the reviewer suggests storing and passing the specific listener function to fs.unwatchFile during cleanup, and updating the tests to assert this behavior.
Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>
Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>
Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>
Complete the review change: the named HEAD listener was being declared but never created/stored, so the unmount guard `watchedHeadPath && watchedHeadListener` was always false and fs.unwatchFile never ran (leaking the poll on unmount). Define the listener as a named function, pass it to fs.watchFile, and store it in watchedHeadListener so cleanup removes only this hook instance's listener.
Summary
The footer Branch indicator does not update after a
git checkouton filesystems wherefs.watchdelivers no change events — most notably WSL mounts of Windows drives (/mnt/c/...) and network shares. The displayed branch stays stuck on whatever was checked out when the CLI started.Fixes #27957
Details
useGitBranchNamealready watches the git directory withfs.watchand re-fetches the branch whenHEADchanges. Butfs.watchrelies on the OS notification layer (inotify on Linux, FSEvents on macOS), and on WSL mounts of Windows drives and on many network filesystems that layer delivers no events at all — so the watcher silently never fires and the branch is never refreshed (the environment in #27957 is WSL).This adds a stat-based
fs.watchFilepoll onHEADas a reliable fallback that works regardless of the underlying filesystem, running alongside the existingfs.watch(which remains the fast, event-driven path where it works):scheduleRefresh()helper (no behavior change to the existing fast path).HEAD'smtimeactually changes, so steady state does no work.statof a tiny file; negligible cost).fs.unwatchFile.No changes are needed in the footer component or UI state — they already react to whatever the hook returns.
How to Validate
Manual (on WSL with the repo under
/mnt/<drive>, on a network share, or any affected FS):geminiin a git repo and note the branch shown in the footer.! git checkout -b some-branch(or in another shell).Automated:
npm run --workspace packages/cli test -- src/ui/hooks/useGitBranchName.test.tsxA new test covers the polling fallback (when
fs.watchnever fires), and the cleanup test is extended to assert the poll is removed on unmount.Pre-Merge Checklist
--max-warnings 0) and TypeScript typecheck pass for the changed files.useGitBranchName.test.tsx, plusFooter.test.tsxconsumers).