Skip to content

fix(fs): 文件树 ignore 规则限定在工作空间自身的 git 仓库内 - #838

Open
AlphaCatMeow wants to merge 1 commit into
Stack-Cairn:developfrom
AlphaCatMeow:fix/file-tree-gitignore-scope-develop
Open

AlphaCatMeow wants to merge 1 commit into
Stack-Cairn:developfrom
AlphaCatMeow:fix/file-tree-gitignore-scope-develop

Conversation

@AlphaCatMeow

Copy link
Copy Markdown
Contributor

Fixes #820

本 PR 是 #821 改 base 到 develop 的重提,补丁内容与 #821 完全一致(git patch-id 相同),在 develop 上 cherry-pick 无冲突。合并后 #821 可关闭。

问题

文件树(及 fs_glob/fs_grep/fs_mention_list)的目录遍历在"显示隐藏文件"关闭时误吞条目,用户可见症状为数字开头文件夹不显示、资源管理器新建的文件夹在文件树看不到(#820)。根因有两处:

  1. require_git(false):非 git 目录里的 .gitignore(以及全局 excludesFile)也生效;
  2. 未调用 .parents(false)WalkBuilder 默认向上读取祖先目录的 ignore 文件,工作空间外部的规则泄漏进来。

两处均已用同版本 ignore crate (=0.4.27) 独立复现确认。

修复

build_workspace_walker(所有 fs 遍历命令的唯一入口):

  • parents(false):工作空间根是文件视图的语义边界,外部 ignore 规则不再套用;
  • require_git(true):gitignore 族过滤只在真实 git 仓库内生效。

行为变化说明:workspace 是 monorepo 子目录时,仓库根的 .gitignore 不再作用于文件树——对文件视图而言"少隐藏"比"条目凭空消失"更安全,且与用户在"显示隐藏文件"开关下的心智一致。

测试

  • 现有依赖 gitignore 过滤的 fixture 增加 init_fake_git_repo(空 .git 目录即可满足 require_git(true));
  • mention_list_respects_gitignore_without_git_repository 更名为 ..._inside_git_repository(语义随修复反转);
  • 新增两个回归测试:
    • list_ignores_gitignore_outside_git_repository:非仓库 + [0-9]* 规则,数字目录必须出现;
    • list_ignores_ancestor_gitignore_outside_workspace_root:父目录的仓库规则不得过滤子工作空间。

验证(在 develop 基线上重新跑):cargo test -p liveagent --lib fs::tests 43/43 通过。

用户侧临时绕过(未升级前)

  • 打开文件树"显示隐藏文件"开关,被过滤条目以半透明显示;
  • git check-ignore -v --no-index <名字> 可定位具体命中的规则与文件。

The file views walker (fs_list/fs_glob/fs_grep/fs_mention_list) applied
gitignore rules even when the workspace is not a git repository
(require_git(false)) and also honored ignore files in ancestor
directories outside the workspace root (WalkBuilder's default
parents(true)). Entries matching such rules silently vanished from the
file tree - e.g. digit-leading folders matched by a stray [0-9]* rule,
or folders created in Explorer that matched an ancestor's gitignore.

- parents(false): the workspace root is the semantic boundary; outside
  ignore rules no longer leak in.
- require_git(true): gitignore/global/exclude filtering only applies
  inside an actual git repository.
- Existing gitignore-dependent test fixtures now initialize a fake .git
  directory; two regression tests cover the non-repo and ancestor-leak
  cases.

Fixes Stack-Cairn#820
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