Skip to content

Commit 02804cd

Browse files
authored
Ensure that we also lint files from git submodules (#3431)
1 parent b78abe5 commit 02804cd

File tree

6 files changed

+63
-33
lines changed

6 files changed

+63
-33
lines changed

.pre-commit-config.yaml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -151,6 +151,7 @@ repos:
151151
- cryptography>=39.0.1
152152
- filelock
153153
- jinja2
154+
- pytest-mock
154155
- pytest>=7.2.2
155156
- rich>=13.2.0
156157
- ruamel-yaml>=0.17.26
@@ -180,6 +181,7 @@ repos:
180181
- docutils
181182
- filelock
182183
- jsonschema>=4.9.0
184+
- pytest-mock
183185
- pytest>=7.2.2
184186
- pyyaml
185187
- rich>=13.2.0

src/ansiblelint/file_utils.py

Lines changed: 51 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -422,36 +422,60 @@ def discover_lintables(options: Options) -> dict[str, Any]:
422422
under current user and absolute for everything else.
423423
"""
424424
# git is preferred as it also considers .gitignore
425-
git_command_present = [
426-
*GIT_CMD,
427-
"ls-files",
428-
"--cached",
429-
"--others",
430-
"--exclude-standard",
431-
"-z",
432-
]
433-
git_command_absent = [*GIT_CMD, "ls-files", "--deleted", "-z"]
434-
out = None
425+
# As --recurse-submodules is incompatible with --others we need to run
426+
# twice to get combined results.
427+
commands = {
428+
"tracked": {
429+
"cmd": [
430+
*GIT_CMD,
431+
"ls-files",
432+
"--cached",
433+
"--exclude-standard",
434+
"--recurse-submodules",
435+
"-z",
436+
],
437+
"remove": False,
438+
},
439+
"others": {
440+
"cmd": [
441+
*GIT_CMD,
442+
"ls-files",
443+
"--cached",
444+
"--others",
445+
"--exclude-standard",
446+
"-z",
447+
],
448+
"remove": False,
449+
},
450+
"absent": {
451+
"cmd": [
452+
*GIT_CMD,
453+
"ls-files",
454+
"--deleted",
455+
"-z",
456+
],
457+
"remove": True,
458+
},
459+
}
435460

461+
out: set[str] = set()
436462
try:
437-
out_present = subprocess.check_output(
438-
git_command_present, # noqa: S603
439-
stderr=subprocess.STDOUT,
440-
text=True,
441-
).split("\x00")[:-1]
442-
_logger.info(
443-
"Discovered files to lint using: %s",
444-
" ".join(git_command_present),
445-
)
446-
447-
out_absent = subprocess.check_output(
448-
git_command_absent, # noqa: S603
449-
stderr=subprocess.STDOUT,
450-
text=True,
451-
).split("\x00")[:-1]
452-
_logger.info("Excluded removed files using: %s", " ".join(git_command_absent))
463+
for k, value in commands.items():
464+
if not isinstance(value["cmd"], list):
465+
msg = f"Expected list but got {type(value['cmd'])}"
466+
raise TypeError(msg)
467+
result = subprocess.check_output(
468+
value["cmd"], # noqa: S603
469+
stderr=subprocess.STDOUT,
470+
text=True,
471+
).split("\x00")[:-1]
472+
_logger.info(
473+
"Discovered files to lint using git (%s): %s",
474+
k,
475+
" ".join(value["cmd"]),
476+
)
477+
out = out.union(result) if not value["remove"] else out - set(result)
453478

454-
out = set(out_present) - set(out_absent)
455479
except subprocess.CalledProcessError as exc:
456480
if not (exc.returncode == 128 and "fatal: not a git repository" in exc.output):
457481
err = exc.output.rstrip("\n")

src/ansiblelint/schemas/__store__.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@
2424
"url": "https://raw.githubusercontent.com/ansible/ansible-lint/main/src/ansiblelint/schemas/inventory.json"
2525
},
2626
"meta": {
27-
"etag": "7cbcda4e9454961d843f5b2b37349bafdf387d01e8ad6772e0a4c89868aaa55c",
27+
"etag": "24aa044eddbf2fc92e31775bcc625fd8e7689cb14542ac59c0e3b94d9a9b163a",
2828
"url": "https://raw.githubusercontent.com/ansible/ansible-lint/main/src/ansiblelint/schemas/meta.json"
2929
},
3030
"meta-runtime": {

test/test_main.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,9 @@
55
import sys
66
import time
77
from pathlib import Path
8-
from typing import Any
98

109
import pytest
10+
from pytest_mock import MockerFixture
1111

1212
from ansiblelint.config import get_version_warning
1313

@@ -58,7 +58,7 @@ def test_call_from_outside_venv(expected_warning: bool) -> None:
5858
),
5959
)
6060
def test_get_version_warning(
61-
mocker: Any,
61+
mocker: MockerFixture,
6262
ver_diff: str,
6363
found: bool,
6464
check: str,

test/test_mockings.py

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,17 @@
11
"""Test mockings module."""
2+
from typing import Any
3+
24
import pytest
35

46
from ansiblelint._mockings import _make_module_stub
7+
from ansiblelint.config import options
58
from ansiblelint.constants import RC
69

710

8-
def test_make_module_stub() -> None:
11+
def test_make_module_stub(mocker: Any) -> None:
912
"""Test make module stub."""
13+
mocker.patch("ansiblelint.config.options.cache_dir", return_value=".")
14+
assert options.cache_dir is not None
1015
with pytest.raises(SystemExit) as exc:
1116
_make_module_stub("")
1217
assert exc.type == SystemExit

test/test_utils.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -301,8 +301,7 @@ def test_cli_auto_detect(capfd: CaptureFixture[str]) -> None:
301301
out, err = capfd.readouterr()
302302

303303
# Confirmation that it runs in auto-detect mode
304-
assert "Discovered files to lint using: git" in err
305-
assert "Excluded removed files using: git" in err
304+
assert "Discovered files to lint using git" in err
306305
# An expected rule match from our examples
307306
assert (
308307
"examples/playbooks/empty_playbook.yml:1:1: "

0 commit comments

Comments
 (0)