Skip to content

Commit 90b5bc3

Browse files
authored
Allow unmatching "changed" globs (#20505)
If `changed` returns globs that match no files, because they've all been deleted, that is fine! The warnings/errors are intended for user-provided specs that don't match anything, as that is likely user error. These globs are synthesized by Pants based on git data, and so whatever they match or not is an implementation detail, not a user facing concern. Fixes #20503
1 parent 3129951 commit 90b5bc3

File tree

3 files changed

+12
-4
lines changed

3 files changed

+12
-4
lines changed

src/python/pants/init/specs_calculator.py

+6-1
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
import logging
55
from typing import cast
66

7+
from pants.base.glob_match_error_behavior import GlobMatchErrorBehavior
78
from pants.base.specs import AddressLiteralSpec, FileLiteralSpec, RawSpecs, Specs
89
from pants.base.specs_parser import SpecsParser
910
from pants.core.util_rules.environments import determine_bootstrap_environment
@@ -96,7 +97,11 @@ def calculate_specs(
9697
# target-aware vs. target-less goals, e.g. `list` vs `count-loc`.
9798
address_literals=tuple(address_literal_specs),
9899
file_literals=file_literal_specs,
99-
unmatched_glob_behavior=unmatched_cli_globs,
100+
# The globs here are synthesized from VCS data by the `changed` mechanism.
101+
# As such it does not make sense to apply user-facing matching errors to them.
102+
# In particular, they can legitimately not match anything, if entire git
103+
# subtrees were deleted for example.
104+
unmatched_glob_behavior=GlobMatchErrorBehavior.ignore,
100105
filter_by_global_options=True,
101106
from_change_detection=True,
102107
description_of_origin="`--changed-since`",

src/python/pants/vcs/git.py

+3-3
Original file line numberDiff line numberDiff line change
@@ -91,7 +91,7 @@ def changed_files(
9191
committed_changes = self._git_binary._invoke_unsandboxed(
9292
self._create_git_cmdline(committed_cmd)
9393
)
94-
files.update(committed_changes.split())
94+
files.update(committed_changes.splitlines())
9595
if include_untracked:
9696
untracked_cmd = [
9797
"ls-files",
@@ -102,14 +102,14 @@ def changed_files(
102102
untracked = self._git_binary._invoke_unsandboxed(
103103
self._create_git_cmdline(untracked_cmd)
104104
)
105-
files.update(untracked.split())
105+
files.update(untracked.splitlines())
106106
# git will report changed files relative to the worktree: re-relativize to relative_to
107107
return {self._fix_git_relative_path(f, relative_to) for f in files}
108108

109109
def changes_in(self, diffspec: str, relative_to: PurePath | str | None = None) -> set[str]:
110110
relative_to = PurePath(relative_to) if relative_to is not None else self.worktree
111111
cmd = ["diff-tree", "--no-commit-id", "--name-only", "-r", diffspec]
112-
files = self._git_binary._invoke_unsandboxed(self._create_git_cmdline(cmd)).split()
112+
files = self._git_binary._invoke_unsandboxed(self._create_git_cmdline(cmd)).splitlines()
113113
return {self._fix_git_relative_path(f.strip(), relative_to) for f in files}
114114

115115
def _create_git_cmdline(self, args: Iterable[str]) -> list[str]:

src/python/pants/vcs/git_test.py

+3
Original file line numberDiff line numberDiff line change
@@ -139,6 +139,9 @@ def test_integration(worktree: Path, readme_file: Path, git: MutatingGitWorktree
139139
assert {"README"} == git.changed_files()
140140
assert {"README", "INSTALL"} == git.changed_files(include_untracked=True)
141141

142+
(worktree / "WITH SPACE").write_text("space in path")
143+
assert {"README", "INSTALL", "WITH SPACE"} == git.changed_files(include_untracked=True)
144+
142145
# Confirm that files outside of a given relative_to path are ignored
143146
assert set() == git.changed_files(relative_to="non-existent")
144147

0 commit comments

Comments
 (0)