pre-commit-uv 4.2.1__tar.gz → 4.3.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/PKG-INFO +3 -7
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/pyproject.toml +32 -18
- pre_commit_uv-4.3.0/src/pre_commit_uv/__init__.py +174 -0
- pre_commit_uv-4.3.0/tests/test_health_check.py +77 -0
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/tests/test_main.py +8 -8
- pre_commit_uv-4.2.1/src/pre_commit_uv/__init__.py +0 -136
- pre_commit_uv-4.2.1/tox.ini +0 -70
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/.gitignore +0 -0
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/LICENSE.txt +0 -0
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/README.md +0 -0
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/src/pre_commit_uv/py.typed +0 -0
- {pre_commit_uv-4.2.1 → pre_commit_uv-4.3.0}/src/pre_commit_uv_patch.pth +0 -0
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: pre-commit-uv
|
|
3
|
-
Version: 4.
|
|
3
|
+
Version: 4.3.0
|
|
4
4
|
Summary: Run pre-commit with uv
|
|
5
5
|
Project-URL: Bug Tracker, https://github.com/tox-dev/pre-commit-uv/issues
|
|
6
|
-
Project-URL: Changelog, https://github.com/tox-dev/pre-commit-uv/releases
|
|
7
6
|
Project-URL: Source Code, https://github.com/tox-dev/pre-commit-uv
|
|
7
|
+
Project-URL: Changelog, https://github.com/tox-dev/pre-commit-uv/releases
|
|
8
8
|
Project-URL: Documentation, https://github.com/tox-dev/pre-commit-uv/
|
|
9
9
|
Author-email: Bernat Gabor <gaborjbernat@gmail.com>
|
|
10
10
|
License: Permission is hereby granted, free of charge, to any person obtaining a
|
|
@@ -36,14 +36,10 @@ Classifier: Programming Language :: Python :: 3.11
|
|
|
36
36
|
Classifier: Programming Language :: Python :: 3.12
|
|
37
37
|
Classifier: Programming Language :: Python :: 3.13
|
|
38
38
|
Classifier: Programming Language :: Python :: 3.14
|
|
39
|
+
Classifier: Programming Language :: Python :: 3.15
|
|
39
40
|
Requires-Python: >=3.10
|
|
40
41
|
Requires-Dist: pre-commit>=4.3
|
|
41
42
|
Requires-Dist: uv>=0.9.1
|
|
42
|
-
Provides-Extra: testing
|
|
43
|
-
Requires-Dist: covdefaults>=2.3; extra == 'testing'
|
|
44
|
-
Requires-Dist: pytest-cov>=7; extra == 'testing'
|
|
45
|
-
Requires-Dist: pytest-mock>=3.15.1; extra == 'testing'
|
|
46
|
-
Requires-Dist: pytest>=8.4.2; extra == 'testing'
|
|
47
43
|
Description-Content-Type: text/markdown
|
|
48
44
|
|
|
49
45
|
# pre-commit-uv
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
build-backend = "hatchling.build"
|
|
3
3
|
requires = [
|
|
4
4
|
"hatch-vcs>=0.5",
|
|
5
|
-
"hatchling>=1.
|
|
5
|
+
"hatchling>=1.28",
|
|
6
6
|
]
|
|
7
7
|
|
|
8
8
|
[project]
|
|
@@ -28,6 +28,7 @@ classifiers = [
|
|
|
28
28
|
"Programming Language :: Python :: 3.12",
|
|
29
29
|
"Programming Language :: Python :: 3.13",
|
|
30
30
|
"Programming Language :: Python :: 3.14",
|
|
31
|
+
"Programming Language :: Python :: 3.15",
|
|
31
32
|
]
|
|
32
33
|
dynamic = [
|
|
33
34
|
"version",
|
|
@@ -36,18 +37,39 @@ dependencies = [
|
|
|
36
37
|
"pre-commit>=4.3",
|
|
37
38
|
"uv>=0.9.1",
|
|
38
39
|
]
|
|
39
|
-
|
|
40
|
+
urls."Bug Tracker" = "https://github.com/tox-dev/pre-commit-uv/issues"
|
|
41
|
+
urls."Source Code" = "https://github.com/tox-dev/pre-commit-uv"
|
|
42
|
+
urls.Changelog = "https://github.com/tox-dev/pre-commit-uv/releases"
|
|
43
|
+
urls.Documentation = "https://github.com/tox-dev/pre-commit-uv/"
|
|
44
|
+
|
|
45
|
+
[dependency-groups]
|
|
46
|
+
dev = [
|
|
47
|
+
{ include-group = "lint" },
|
|
48
|
+
{ include-group = "pkg-meta" },
|
|
49
|
+
{ include-group = "test" },
|
|
50
|
+
{ include-group = "type" },
|
|
51
|
+
]
|
|
52
|
+
test = [
|
|
40
53
|
"covdefaults>=2.3",
|
|
41
54
|
"pytest>=8.4.2",
|
|
42
55
|
"pytest-cov>=7",
|
|
43
56
|
"pytest-mock>=3.15.1",
|
|
44
57
|
]
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
58
|
+
type = [
|
|
59
|
+
"ty>=0.0.17",
|
|
60
|
+
{ include-group = "test" },
|
|
61
|
+
]
|
|
62
|
+
lint = [
|
|
63
|
+
"pre-commit-uv>=4.2",
|
|
64
|
+
]
|
|
65
|
+
pkg-meta = [
|
|
66
|
+
"check-wheel-contents>=0.6.3",
|
|
67
|
+
"twine>=6.2",
|
|
68
|
+
"uv>=0.10.2",
|
|
69
|
+
]
|
|
49
70
|
|
|
50
71
|
[tool.hatch]
|
|
72
|
+
version.source = "vcs"
|
|
51
73
|
build.dev-mode-dirs = [
|
|
52
74
|
"src",
|
|
53
75
|
]
|
|
@@ -58,7 +80,6 @@ build.targets.sdist.include = [
|
|
|
58
80
|
]
|
|
59
81
|
build.targets.wheel.only-include = [ "src" ]
|
|
60
82
|
build.targets.wheel.sources = [ "src" ]
|
|
61
|
-
version.source = "vcs"
|
|
62
83
|
|
|
63
84
|
[tool.ruff]
|
|
64
85
|
line-length = 120
|
|
@@ -69,7 +90,6 @@ lint.select = [
|
|
|
69
90
|
"ALL",
|
|
70
91
|
]
|
|
71
92
|
lint.ignore = [
|
|
72
|
-
"ANN101", # no type annotation for self
|
|
73
93
|
"ANN401", # allow Any as type annotation
|
|
74
94
|
"COM812", # Conflict with formatter
|
|
75
95
|
"CPY", # No copyright statements
|
|
@@ -103,7 +123,10 @@ builtin = "clear,usage,en-GB_to_en-US"
|
|
|
103
123
|
count = true
|
|
104
124
|
|
|
105
125
|
[tool.pyproject-fmt]
|
|
106
|
-
max_supported_python = "3.
|
|
126
|
+
max_supported_python = "3.15"
|
|
127
|
+
|
|
128
|
+
[tool.ty]
|
|
129
|
+
environment.python-version = "3.14"
|
|
107
130
|
|
|
108
131
|
[tool.pytest]
|
|
109
132
|
ini_options.testpaths = [
|
|
@@ -127,12 +150,3 @@ paths.source = [
|
|
|
127
150
|
report.fail_under = 63
|
|
128
151
|
html.show_contexts = true
|
|
129
152
|
html.skip_covered = false
|
|
130
|
-
|
|
131
|
-
[tool.mypy]
|
|
132
|
-
show_error_codes = true
|
|
133
|
-
strict = true
|
|
134
|
-
overrides = [
|
|
135
|
-
{ module = [
|
|
136
|
-
"pre_commit.*",
|
|
137
|
-
], ignore_missing_imports = true },
|
|
138
|
-
]
|
|
@@ -0,0 +1,174 @@
|
|
|
1
|
+
"""Package root."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
# only import built-ins at top level to avoid interpreter startup overhead
|
|
6
|
+
import os
|
|
7
|
+
import pathlib
|
|
8
|
+
import sys
|
|
9
|
+
from typing import TYPE_CHECKING, cast
|
|
10
|
+
|
|
11
|
+
if TYPE_CHECKING:
|
|
12
|
+
from collections.abc import Callable, Sequence
|
|
13
|
+
from typing import Protocol
|
|
14
|
+
|
|
15
|
+
from pre_commit.prefix import Prefix
|
|
16
|
+
|
|
17
|
+
class _PatchablePython(Protocol):
|
|
18
|
+
install_environment: Callable[[Prefix, str, Sequence[str]], None]
|
|
19
|
+
health_check: Callable[[Prefix, str], str | None]
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
_original_main = None
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
def _is_calling_pre_commit() -> bool:
|
|
26
|
+
if "FORCE_PRE_COMMIT_UV_PATCH" in os.environ:
|
|
27
|
+
return True
|
|
28
|
+
if not sys.argv or not sys.argv[0]:
|
|
29
|
+
return False
|
|
30
|
+
# case when pre-commit is called via python -m pre_commit
|
|
31
|
+
if sys.argv[0] == "-m" and "-m" in sys.orig_argv and "pre_commit" in sys.orig_argv:
|
|
32
|
+
return True
|
|
33
|
+
calling = sys.argv[1] if sys.argv[0] == sys.executable and len(sys.argv) >= 1 else sys.argv[0]
|
|
34
|
+
# case when pre-commit is called directly
|
|
35
|
+
if os.path.split(calling)[1] == f"pre-commit{'.exe' if sys.platform == 'win32' else ''}":
|
|
36
|
+
return True
|
|
37
|
+
# case when pre-commit is called due to a git commit
|
|
38
|
+
return "-m" in sys.argv and "hook-impl" in sys.argv
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
def _patch() -> None:
|
|
42
|
+
global _original_main
|
|
43
|
+
if _original_main is not None: # already patched, nothing more to do
|
|
44
|
+
return
|
|
45
|
+
|
|
46
|
+
if _is_calling_pre_commit() and os.environ.get("DISABLE_PRE_COMMIT_UV_PATCH") is None:
|
|
47
|
+
from pre_commit import main # ruff:ignore[import-outside-top-level]
|
|
48
|
+
|
|
49
|
+
_original_main, main.main = main.main, _new_main # ty: ignore[invalid-assignment]
|
|
50
|
+
if "--version" in sys.argv:
|
|
51
|
+
from importlib.metadata import version as _metadata_version # ruff:ignore[import-outside-top-level]
|
|
52
|
+
|
|
53
|
+
from pre_commit import constants # ruff:ignore[import-outside-top-level]
|
|
54
|
+
|
|
55
|
+
constants.VERSION = (
|
|
56
|
+
f"{constants.VERSION} ("
|
|
57
|
+
f"pre-commit-uv={_metadata_version('pre-commit-uv')}, "
|
|
58
|
+
f"uv={_metadata_version('uv')}"
|
|
59
|
+
f")"
|
|
60
|
+
)
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
def _new_main(argv: Sequence[str] | None = None) -> int:
|
|
64
|
+
# imports applied locally to avoid patching import overhead cost
|
|
65
|
+
from functools import cache # ruff:ignore[import-outside-top-level]
|
|
66
|
+
|
|
67
|
+
from pre_commit.languages import python # ruff:ignore[import-outside-top-level]
|
|
68
|
+
|
|
69
|
+
def _install_environment(
|
|
70
|
+
prefix: Prefix,
|
|
71
|
+
version: str,
|
|
72
|
+
additional_dependencies: Sequence[str],
|
|
73
|
+
) -> None:
|
|
74
|
+
import logging # ruff:ignore[import-outside-top-level]
|
|
75
|
+
|
|
76
|
+
from pre_commit.git import get_root # ruff:ignore[import-outside-top-level]
|
|
77
|
+
from pre_commit.lang_base import environment_dir, setup_cmd # ruff:ignore[import-outside-top-level]
|
|
78
|
+
from pre_commit.util import cmd_output_b # ruff:ignore[import-outside-top-level]
|
|
79
|
+
|
|
80
|
+
project_root_dir = get_root()
|
|
81
|
+
|
|
82
|
+
logger = logging.getLogger("pre_commit")
|
|
83
|
+
logger.info("Using pre-commit with uv %s via pre-commit-uv %s", uv_version(), self_version())
|
|
84
|
+
uv = _uv()
|
|
85
|
+
py = python.norm_version(version) or os.environ.get("UV_PYTHON", sys.executable)
|
|
86
|
+
venv_cmd = [
|
|
87
|
+
uv,
|
|
88
|
+
"--project",
|
|
89
|
+
project_root_dir,
|
|
90
|
+
"venv",
|
|
91
|
+
"--seed",
|
|
92
|
+
environment_dir(prefix, python.ENVIRONMENT_DIR, version),
|
|
93
|
+
"-p",
|
|
94
|
+
py,
|
|
95
|
+
]
|
|
96
|
+
cmd_output_b(*venv_cmd, cwd="/")
|
|
97
|
+
|
|
98
|
+
with python.in_env(prefix, version):
|
|
99
|
+
setup_cmd(
|
|
100
|
+
prefix,
|
|
101
|
+
(
|
|
102
|
+
uv,
|
|
103
|
+
"--project",
|
|
104
|
+
project_root_dir,
|
|
105
|
+
"pip",
|
|
106
|
+
"install",
|
|
107
|
+
".",
|
|
108
|
+
*additional_dependencies,
|
|
109
|
+
),
|
|
110
|
+
)
|
|
111
|
+
|
|
112
|
+
@cache
|
|
113
|
+
def _uv() -> str:
|
|
114
|
+
from uv import find_uv_bin # ruff:ignore[import-outside-top-level]
|
|
115
|
+
|
|
116
|
+
return find_uv_bin()
|
|
117
|
+
|
|
118
|
+
@cache
|
|
119
|
+
def self_version() -> str:
|
|
120
|
+
from importlib.metadata import version as _metadata_version # ruff:ignore[import-outside-top-level]
|
|
121
|
+
|
|
122
|
+
return _metadata_version("pre-commit-uv")
|
|
123
|
+
|
|
124
|
+
@cache
|
|
125
|
+
def uv_version() -> str:
|
|
126
|
+
from importlib.metadata import version as _metadata_version # ruff:ignore[import-outside-top-level]
|
|
127
|
+
|
|
128
|
+
return _metadata_version("uv")
|
|
129
|
+
|
|
130
|
+
patched = cast("_PatchablePython", python)
|
|
131
|
+
patched.install_environment = _install_environment
|
|
132
|
+
patched.health_check = _health_check
|
|
133
|
+
assert _original_main is not None # ruff:ignore[assert]
|
|
134
|
+
return _original_main(argv)
|
|
135
|
+
|
|
136
|
+
|
|
137
|
+
def _version_info(exe: str) -> str:
|
|
138
|
+
from pre_commit.util import CalledProcessError, cmd_output # ruff:ignore[import-outside-top-level]
|
|
139
|
+
|
|
140
|
+
prog = 'import sys;print(".".join(str(p) for p in sys.version_info[0:3]))'
|
|
141
|
+
try:
|
|
142
|
+
return cmd_output(exe, "-S", "-c", prog)[1].strip()
|
|
143
|
+
except CalledProcessError:
|
|
144
|
+
return f"<<error retrieving version from {exe}>>"
|
|
145
|
+
|
|
146
|
+
|
|
147
|
+
def _health_check(prefix: Prefix, version: str) -> str | None:
|
|
148
|
+
# uv may record fewer version components in pyvenv.cfg than pre-commit expects (e.g. "3.14" vs "3.14.6"),
|
|
149
|
+
# so compare only the components uv actually wrote rather than requiring an exact string match
|
|
150
|
+
from pre_commit.lang_base import environment_dir # ruff:ignore[import-outside-top-level]
|
|
151
|
+
from pre_commit.languages import python # ruff:ignore[import-outside-top-level]
|
|
152
|
+
from pre_commit.util import win_exe # ruff:ignore[import-outside-top-level]
|
|
153
|
+
|
|
154
|
+
pyvenv_cfg = pathlib.Path(environment_dir(prefix, python.ENVIRONMENT_DIR, version)) / "pyvenv.cfg"
|
|
155
|
+
if not pyvenv_cfg.exists():
|
|
156
|
+
return "pyvenv.cfg does not exist (old virtualenv?)"
|
|
157
|
+
|
|
158
|
+
cfg = python._read_pyvenv_cfg(str(pyvenv_cfg)) # ruff:ignore[private-member-access]
|
|
159
|
+
if "version_info" not in cfg:
|
|
160
|
+
return "created virtualenv's pyvenv.cfg is missing `version_info`"
|
|
161
|
+
expected = cfg["version_info"].split(".")
|
|
162
|
+
|
|
163
|
+
py_exe = prefix.path(python.bin_dir(str(pyvenv_cfg.parent)), win_exe("python"))
|
|
164
|
+
targets = [("virtualenv python", py_exe)]
|
|
165
|
+
if "base-executable" in cfg:
|
|
166
|
+
targets.append(("base executable", cfg["base-executable"]))
|
|
167
|
+
for label, exe in targets:
|
|
168
|
+
if (actual := _version_info(exe)).split(".")[: len(expected)] != expected:
|
|
169
|
+
return (
|
|
170
|
+
f"{label} version did not match created version:\n"
|
|
171
|
+
f"- actual version: {actual}\n"
|
|
172
|
+
f"- expected version: {cfg['version_info']}\n"
|
|
173
|
+
)
|
|
174
|
+
return None
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import sys
|
|
4
|
+
from typing import TYPE_CHECKING
|
|
5
|
+
|
|
6
|
+
from pre_commit.languages import python
|
|
7
|
+
from pre_commit.prefix import Prefix
|
|
8
|
+
|
|
9
|
+
from pre_commit_uv import _health_check
|
|
10
|
+
|
|
11
|
+
if TYPE_CHECKING:
|
|
12
|
+
from pathlib import Path
|
|
13
|
+
|
|
14
|
+
version = "default"
|
|
15
|
+
major_minor = f"{sys.version_info[0]}.{sys.version_info[1]}"
|
|
16
|
+
full_version = ".".join(str(p) for p in sys.version_info[0:3])
|
|
17
|
+
wrong_version = f"{sys.version_info[0]}.{sys.version_info[1] + 1}"
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
def _make_env(tmp_path: Path, pyvenv_cfg: str | None) -> Prefix:
|
|
21
|
+
envdir = tmp_path / f"py_env-{version}"
|
|
22
|
+
bin_dir = python.bin_dir(str(envdir))
|
|
23
|
+
(tmp_path / bin_dir).mkdir(parents=True)
|
|
24
|
+
(tmp_path / bin_dir / python.win_exe("python")).symlink_to(sys.executable)
|
|
25
|
+
if pyvenv_cfg is not None:
|
|
26
|
+
(envdir / "pyvenv.cfg").write_text(pyvenv_cfg)
|
|
27
|
+
return Prefix(str(tmp_path))
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
def test_health_check_truncated_version_passes(tmp_path: Path) -> None:
|
|
31
|
+
"""uv >=0.11.22 writes only the major.minor into pyvenv.cfg (see issue #152)."""
|
|
32
|
+
prefix = _make_env(tmp_path, f"version_info = {major_minor}\nbase-executable = {sys.executable}\n")
|
|
33
|
+
|
|
34
|
+
assert _health_check(prefix, version) is None
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
def test_health_check_full_version_passes(tmp_path: Path) -> None:
|
|
38
|
+
prefix = _make_env(tmp_path, f"version_info = {full_version}\nbase-executable = {sys.executable}\n")
|
|
39
|
+
|
|
40
|
+
assert _health_check(prefix, version) is None
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
def test_health_check_no_base_executable_passes(tmp_path: Path) -> None:
|
|
44
|
+
prefix = _make_env(tmp_path, f"version_info = {major_minor}\n")
|
|
45
|
+
|
|
46
|
+
assert _health_check(prefix, version) is None
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
def test_health_check_version_mismatch_fails(tmp_path: Path) -> None:
|
|
50
|
+
prefix = _make_env(tmp_path, f"version_info = {wrong_version}\n")
|
|
51
|
+
|
|
52
|
+
result = _health_check(prefix, version)
|
|
53
|
+
|
|
54
|
+
assert result is not None
|
|
55
|
+
assert "virtualenv python version did not match created version" in result
|
|
56
|
+
assert f"- expected version: {wrong_version}" in result
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
def test_health_check_base_executable_mismatch_fails(tmp_path: Path) -> None:
|
|
60
|
+
prefix = _make_env(tmp_path, f"version_info = {major_minor}\nbase-executable = /does/not/exist/python\n")
|
|
61
|
+
|
|
62
|
+
result = _health_check(prefix, version)
|
|
63
|
+
|
|
64
|
+
assert result is not None
|
|
65
|
+
assert "base executable version did not match created version" in result
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
def test_health_check_missing_pyvenv_cfg(tmp_path: Path) -> None:
|
|
69
|
+
prefix = _make_env(tmp_path, None)
|
|
70
|
+
|
|
71
|
+
assert _health_check(prefix, version) == "pyvenv.cfg does not exist (old virtualenv?)"
|
|
72
|
+
|
|
73
|
+
|
|
74
|
+
def test_health_check_missing_version_info(tmp_path: Path) -> None:
|
|
75
|
+
prefix = _make_env(tmp_path, "home = /usr\n")
|
|
76
|
+
|
|
77
|
+
assert _health_check(prefix, version) == "created virtualenv's pyvenv.cfg is missing `version_info`"
|
|
@@ -55,9 +55,9 @@ def test_call_as_module() -> None:
|
|
|
55
55
|
def test_install(git_repo: Path, caplog: pytest.LogCaptureFixture, monkeypatch: pytest.MonkeyPatch) -> None:
|
|
56
56
|
monkeypatch.setenv("FORCE_PRE_COMMIT_UV_PATCH", "1")
|
|
57
57
|
|
|
58
|
-
import pre_commit_uv #
|
|
58
|
+
import pre_commit_uv # ruff:ignore[import-outside-top-level]
|
|
59
59
|
|
|
60
|
-
pre_commit_uv._patch() #
|
|
60
|
+
pre_commit_uv._patch() # ruff:ignore[private-member-access]
|
|
61
61
|
main.main(["install-hooks", "-c", str(git_repo / precommit_file)])
|
|
62
62
|
|
|
63
63
|
assert caplog.messages == [
|
|
@@ -72,9 +72,9 @@ def test_install(git_repo: Path, caplog: pytest.LogCaptureFixture, monkeypatch:
|
|
|
72
72
|
def test_install_seeds_pip(git_repo: Path, monkeypatch: pytest.MonkeyPatch) -> None:
|
|
73
73
|
monkeypatch.setenv("FORCE_PRE_COMMIT_UV_PATCH", "1")
|
|
74
74
|
|
|
75
|
-
import pre_commit_uv #
|
|
75
|
+
import pre_commit_uv # ruff:ignore[import-outside-top-level]
|
|
76
76
|
|
|
77
|
-
pre_commit_uv._patch() #
|
|
77
|
+
pre_commit_uv._patch() # ruff:ignore[private-member-access]
|
|
78
78
|
main.main(["install-hooks", "-c", str(git_repo / precommit_file)])
|
|
79
79
|
|
|
80
80
|
env_dirs = list((git_repo / "store").rglob("py_env-*"))
|
|
@@ -121,9 +121,9 @@ def test_install_with_uv_config(
|
|
|
121
121
|
|
|
122
122
|
monkeypatch.setenv("FORCE_PRE_COMMIT_UV_PATCH", "1")
|
|
123
123
|
|
|
124
|
-
import pre_commit_uv #
|
|
124
|
+
import pre_commit_uv # ruff:ignore[import-outside-top-level]
|
|
125
125
|
|
|
126
|
-
pre_commit_uv._patch() #
|
|
126
|
+
pre_commit_uv._patch() # ruff:ignore[private-member-access]
|
|
127
127
|
main.main(["install-hooks", "-c", str(git_repo / precommit_file)])
|
|
128
128
|
|
|
129
129
|
assert caplog.messages == [
|
|
@@ -169,9 +169,9 @@ def test_install_with_uv_config_raises_error(
|
|
|
169
169
|
|
|
170
170
|
monkeypatch.setenv("FORCE_PRE_COMMIT_UV_PATCH", "1")
|
|
171
171
|
|
|
172
|
-
import pre_commit_uv #
|
|
172
|
+
import pre_commit_uv # ruff:ignore[import-outside-top-level]
|
|
173
173
|
|
|
174
|
-
pre_commit_uv._patch() #
|
|
174
|
+
pre_commit_uv._patch() # ruff:ignore[private-member-access]
|
|
175
175
|
|
|
176
176
|
# would raise SystemExit due to bad config
|
|
177
177
|
with pytest.raises(SystemExit):
|
|
@@ -1,136 +0,0 @@
|
|
|
1
|
-
"""Package root."""
|
|
2
|
-
|
|
3
|
-
from __future__ import annotations
|
|
4
|
-
|
|
5
|
-
# only import built-ins at top level to avoid interpreter startup overhead
|
|
6
|
-
import os
|
|
7
|
-
import sys
|
|
8
|
-
|
|
9
|
-
_original_main = None
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
def _is_calling_pre_commit() -> bool:
|
|
13
|
-
if "FORCE_PRE_COMMIT_UV_PATCH" in os.environ:
|
|
14
|
-
return True
|
|
15
|
-
if not sys.argv or not sys.argv[0]:
|
|
16
|
-
return False
|
|
17
|
-
# case when pre-commit is called via python -m pre_commit
|
|
18
|
-
if sys.argv[0] == "-m" and "-m" in sys.orig_argv and "pre_commit" in sys.orig_argv:
|
|
19
|
-
return True
|
|
20
|
-
calling = sys.argv[1] if sys.argv[0] == sys.executable and len(sys.argv) >= 1 else sys.argv[0]
|
|
21
|
-
# case when pre-commit is called directly
|
|
22
|
-
if os.path.split(calling)[1] == f"pre-commit{'.exe' if sys.platform == 'win32' else ''}":
|
|
23
|
-
return True
|
|
24
|
-
# case when pre-commit is called due to a git commit
|
|
25
|
-
return "-m" in sys.argv and "hook-impl" in sys.argv
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
def _patch() -> None:
|
|
29
|
-
global _original_main
|
|
30
|
-
if _original_main is not None: # already patched, nothing more to do
|
|
31
|
-
return
|
|
32
|
-
|
|
33
|
-
if _is_calling_pre_commit() and os.environ.get("DISABLE_PRE_COMMIT_UV_PATCH") is None:
|
|
34
|
-
from pre_commit import main # noqa: PLC0415
|
|
35
|
-
|
|
36
|
-
_original_main, main.main = main.main, _new_main
|
|
37
|
-
if "--version" in sys.argv:
|
|
38
|
-
from importlib.metadata import version as _metadata_version # noqa: PLC0415
|
|
39
|
-
|
|
40
|
-
from pre_commit import constants # noqa: PLC0415
|
|
41
|
-
|
|
42
|
-
constants.VERSION = (
|
|
43
|
-
f"{constants.VERSION} ("
|
|
44
|
-
f"pre-commit-uv={_metadata_version('pre-commit-uv')}, "
|
|
45
|
-
f"uv={_metadata_version('uv')}"
|
|
46
|
-
f")"
|
|
47
|
-
)
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
def _new_main(argv: list[str] | None = None) -> int:
|
|
51
|
-
# imports applied locally to avoid patching import overhead cost
|
|
52
|
-
from functools import cache # noqa: PLC0415
|
|
53
|
-
from typing import TYPE_CHECKING, cast # noqa: PLC0415
|
|
54
|
-
|
|
55
|
-
from pre_commit.languages import python # noqa: PLC0415
|
|
56
|
-
|
|
57
|
-
if TYPE_CHECKING:
|
|
58
|
-
from collections.abc import Sequence # noqa: PLC0415
|
|
59
|
-
|
|
60
|
-
from pre_commit.prefix import Prefix # noqa: PLC0415
|
|
61
|
-
|
|
62
|
-
def _install_environment(
|
|
63
|
-
prefix: Prefix,
|
|
64
|
-
version: str,
|
|
65
|
-
additional_dependencies: Sequence[str],
|
|
66
|
-
) -> None:
|
|
67
|
-
import logging # noqa: PLC0415
|
|
68
|
-
|
|
69
|
-
from pre_commit.git import get_root # noqa: PLC0415
|
|
70
|
-
from pre_commit.lang_base import environment_dir, setup_cmd # noqa: PLC0415
|
|
71
|
-
from pre_commit.util import cmd_output_b # noqa: PLC0415
|
|
72
|
-
|
|
73
|
-
project_root_dir = get_root()
|
|
74
|
-
|
|
75
|
-
logger = logging.getLogger("pre_commit")
|
|
76
|
-
logger.info("Using pre-commit with uv %s via pre-commit-uv %s", uv_version(), self_version())
|
|
77
|
-
uv = _uv()
|
|
78
|
-
py = python.norm_version(version) or os.environ.get("UV_PYTHON", sys.executable)
|
|
79
|
-
venv_cmd = [
|
|
80
|
-
uv,
|
|
81
|
-
"--project",
|
|
82
|
-
project_root_dir,
|
|
83
|
-
"venv",
|
|
84
|
-
"--seed",
|
|
85
|
-
environment_dir(prefix, python.ENVIRONMENT_DIR, version),
|
|
86
|
-
"-p",
|
|
87
|
-
py,
|
|
88
|
-
]
|
|
89
|
-
cmd_output_b(*venv_cmd, cwd="/")
|
|
90
|
-
|
|
91
|
-
with python.in_env(prefix, version):
|
|
92
|
-
setup_cmd(
|
|
93
|
-
prefix,
|
|
94
|
-
(
|
|
95
|
-
uv,
|
|
96
|
-
"--project",
|
|
97
|
-
project_root_dir,
|
|
98
|
-
"pip",
|
|
99
|
-
"install",
|
|
100
|
-
".",
|
|
101
|
-
*additional_dependencies,
|
|
102
|
-
),
|
|
103
|
-
)
|
|
104
|
-
|
|
105
|
-
@cache
|
|
106
|
-
def _uv() -> str:
|
|
107
|
-
from uv import find_uv_bin # noqa: PLC0415
|
|
108
|
-
|
|
109
|
-
return find_uv_bin()
|
|
110
|
-
|
|
111
|
-
@cache
|
|
112
|
-
def self_version() -> str:
|
|
113
|
-
from importlib.metadata import version as _metadata_version # noqa: PLC0415
|
|
114
|
-
|
|
115
|
-
return _metadata_version("pre-commit-uv")
|
|
116
|
-
|
|
117
|
-
@cache
|
|
118
|
-
def uv_version() -> str:
|
|
119
|
-
from importlib.metadata import version as _metadata_version # noqa: PLC0415
|
|
120
|
-
|
|
121
|
-
return _metadata_version("uv")
|
|
122
|
-
|
|
123
|
-
@cache
|
|
124
|
-
def _version_info(exe: str) -> str:
|
|
125
|
-
from pre_commit.util import CalledProcessError, cmd_output # noqa: PLC0415
|
|
126
|
-
|
|
127
|
-
prog = 'import sys;print(".".join(str(p) for p in sys.version_info[0:3]))'
|
|
128
|
-
try:
|
|
129
|
-
return cast("str", cmd_output(exe, "-S", "-c", prog)[1].strip())
|
|
130
|
-
except CalledProcessError:
|
|
131
|
-
return f"<<error retrieving version from {exe}>>"
|
|
132
|
-
|
|
133
|
-
python.install_environment = _install_environment
|
|
134
|
-
python._version_info = _version_info # noqa: SLF001
|
|
135
|
-
assert _original_main is not None # noqa: S101
|
|
136
|
-
return cast("int", _original_main(argv))
|
pre_commit_uv-4.2.1/tox.ini
DELETED
|
@@ -1,70 +0,0 @@
|
|
|
1
|
-
[tox]
|
|
2
|
-
requires =
|
|
3
|
-
tox>=4.31
|
|
4
|
-
tox-uv>=1.28.1
|
|
5
|
-
env_list =
|
|
6
|
-
fix
|
|
7
|
-
3.14
|
|
8
|
-
3.13
|
|
9
|
-
3.12
|
|
10
|
-
3.11
|
|
11
|
-
3.10
|
|
12
|
-
3.9
|
|
13
|
-
3.8
|
|
14
|
-
type
|
|
15
|
-
pkg_meta
|
|
16
|
-
skip_missing_interpreters = true
|
|
17
|
-
|
|
18
|
-
[testenv]
|
|
19
|
-
description = run the unit tests with pytest under {base_python}
|
|
20
|
-
package = wheel
|
|
21
|
-
wheel_build_env = .pkg
|
|
22
|
-
extras =
|
|
23
|
-
testing
|
|
24
|
-
pass_env =
|
|
25
|
-
PYTEST_*
|
|
26
|
-
set_env =
|
|
27
|
-
COVERAGE_FILE = {work_dir}/.coverage.{env_name}
|
|
28
|
-
commands =
|
|
29
|
-
python -m pytest {tty:--color=yes} {posargs: \
|
|
30
|
-
--cov {env_site_packages_dir}{/}pre_commit_uv --cov {tox_root}{/}tests \
|
|
31
|
-
--cov-config=pyproject.toml --no-cov-on-fail --cov-report term-missing:skip-covered --cov-context=test \
|
|
32
|
-
--cov-report html:{env_tmp_dir}{/}htmlcov --cov-report xml:{work_dir}{/}coverage.{env_name}.xml \
|
|
33
|
-
--junitxml {work_dir}{/}junit.{env_name}.xml \
|
|
34
|
-
tests}
|
|
35
|
-
|
|
36
|
-
[testenv:fix]
|
|
37
|
-
description = format the code base to adhere to our styles, and complain about what we cannot do automatically
|
|
38
|
-
skip_install = true
|
|
39
|
-
deps =
|
|
40
|
-
pre-commit-uv>=4.1.1
|
|
41
|
-
commands =
|
|
42
|
-
pre-commit run --all-files --show-diff-on-failure
|
|
43
|
-
|
|
44
|
-
[testenv:type]
|
|
45
|
-
description = run type check on code base
|
|
46
|
-
deps =
|
|
47
|
-
mypy==1.18.2
|
|
48
|
-
commands =
|
|
49
|
-
mypy src
|
|
50
|
-
mypy tests
|
|
51
|
-
|
|
52
|
-
[testenv:pkg_meta]
|
|
53
|
-
description = check that the long description is valid
|
|
54
|
-
skip_install = true
|
|
55
|
-
deps =
|
|
56
|
-
check-wheel-contents>=0.6.3
|
|
57
|
-
twine>=6.2
|
|
58
|
-
uv>=0.9.1
|
|
59
|
-
commands =
|
|
60
|
-
uv build --sdist --wheel --out-dir {env_tmp_dir} .
|
|
61
|
-
twine check {env_tmp_dir}{/}*
|
|
62
|
-
check-wheel-contents --no-config {env_tmp_dir}
|
|
63
|
-
|
|
64
|
-
[testenv:dev]
|
|
65
|
-
description = generate a DEV environment
|
|
66
|
-
package = editable
|
|
67
|
-
commands =
|
|
68
|
-
uv tree
|
|
69
|
-
python -c 'import sys; print(sys.executable)'
|
|
70
|
-
python task/dev_pth.py {env_site_packages_dir}
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|