From ce5cda4b885df167b3de9bd9ca2621550642e486 Mon Sep 17 00:00:00 2001 From: "Axel H." Date: Thu, 26 Sep 2024 16:15:48 +0200 Subject: [PATCH] Test against and fix for `pdm>=2.19` (#43) --- .github/workflows/ci.yml | 2 +- pyproject.toml | 1 + src/sync_pre_commit_lock/pdm_plugin.py | 7 +-- tests/conftest.py | 9 ++++ .../pdm_project/.pre-commit-config.yaml | 6 +++ tests/test_pdm/test_pdm_integration.py | 47 +++++++++++++++++++ tests/test_pdm/test_pdm_plugin.py | 10 ++-- tox.ini | 22 +++++---- 8 files changed, 81 insertions(+), 23 deletions(-) create mode 100644 tests/fixtures/pdm_project/.pre-commit-config.yaml create mode 100644 tests/test_pdm/test_pdm_integration.py diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index d32f9a0..e12a9ba 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -32,7 +32,7 @@ jobs: uses: hynek/build-and-inspect-python-package@v2 with: upload-name-suffix: -${{ matrix.python-version }}-${{ matrix.os }} - attest-build-provenance-github: 'true' + attest-build-provenance-github: ${{ github.event_name != 'pull_request' && !github.event.pull_request.head.repo.fork }} outputs: # Outputs the supported Python versions as a JSON array, from the project classifiers python-versions: ${{ steps.baipp.outputs.supported_python_classifiers_json_array }} diff --git a/pyproject.toml b/pyproject.toml index bc9d7e3..02f2a34 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -104,6 +104,7 @@ max_supported_python = "3.13" minversion = "7.0" testpaths = [ "tests" ] norecursedirs = "*.egg .eggs dist build docs .tox .git __pycache__ node_modules .venv __pypackages__" +addopts = "-ra --log-disable unearth.evaluator --log-disable unearth.collector --log-disable unearth.auth --log-disable pdm.termui" [tool.coverage.paths] source = [ diff --git a/src/sync_pre_commit_lock/pdm_plugin.py b/src/sync_pre_commit_lock/pdm_plugin.py index 8c19727..326f804 100644 --- a/src/sync_pre_commit_lock/pdm_plugin.py +++ b/src/sync_pre_commit_lock/pdm_plugin.py @@ -24,7 +24,6 @@ from collections.abc import Sequence from pathlib import Path - from pdm.cli.hooks import HookManager from pdm.core import Core from pdm.models.candidates import Candidate from pdm.models.repositories.lock import LockedRepository @@ -137,9 +136,7 @@ class PDMSyncPreCommitHooksVersion(SyncPreCommitHooksVersion): @post_install.connect -def on_pdm_install_setup_pre_commit( - project: Project, *, hooks: HookManager, candidates: list[Candidate], dry_run: bool, **_: Any -) -> None: +def on_pdm_install_setup_pre_commit(project: Project, *, dry_run: bool, **_: Any) -> None: printer = PDMPrinter(project.core.ui) project_root: Path = project.root plugin_config: SyncPreCommitLockConfig = load_config(project_root / project.PYPROJECT_FILENAME) @@ -171,7 +168,7 @@ def select_candidate(candidate: Union[Candidate, list[Candidate]]) -> Candidate @post_lock.connect def on_pdm_lock_check_pre_commit( - project: Project, *, resolution: Resolution, dry_run: bool, with_prefix: bool = True, **kwargs: Any + project: Project, *, resolution: Resolution, dry_run: bool, with_prefix: bool = True, **_: Any ) -> None: project_root: Path = project.root plugin_config: SyncPreCommitLockConfig = load_config(project_root / project.PYPROJECT_FILENAME) diff --git a/tests/conftest.py b/tests/conftest.py index 253aab6..c9d2b23 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -1,3 +1,7 @@ +from pathlib import Path + +import pytest + try: import pdm # noqa: F401 except ImportError: @@ -6,3 +10,8 @@ pytest_plugins = [ "pdm.pytest", ] + + +@pytest.fixture +def fixtures() -> Path: + return Path(__file__).parent.joinpath("fixtures") diff --git a/tests/fixtures/pdm_project/.pre-commit-config.yaml b/tests/fixtures/pdm_project/.pre-commit-config.yaml new file mode 100644 index 0000000..a9fd65f --- /dev/null +++ b/tests/fixtures/pdm_project/.pre-commit-config.yaml @@ -0,0 +1,6 @@ +--- +repos: + - repo: https://github.com/astral-sh/ruff-pre-commit + rev: v0.1.0 + hooks: + - id: ruff diff --git a/tests/test_pdm/test_pdm_integration.py b/tests/test_pdm/test_pdm_integration.py new file mode 100644 index 0000000..9f2db6d --- /dev/null +++ b/tests/test_pdm/test_pdm_integration.py @@ -0,0 +1,47 @@ +from __future__ import annotations + +import shutil +from typing import TYPE_CHECKING + +import pytest + +from sync_pre_commit_lock import PRE_COMMIT_CONFIG_FILENAME + +pytest.importorskip("pdm") + +if TYPE_CHECKING: + from pathlib import Path + + from pdm.project import Project + from pdm.pytest import PDMCallable + + +@pytest.fixture +def project(project: Project, fixtures: Path) -> Project: + shutil.copy(fixtures / "pdm_project" / PRE_COMMIT_CONFIG_FILENAME, project.root) + + return project + + +def test_pdm_lock(pdm: PDMCallable, project: Project): + project.pyproject.settings["dev-dependencies"] = {"lint": ["ruff"]} + project.pyproject.write() + + pdm("lock -v", obj=project, strict=True) + + pre_commit_config = (project.root / PRE_COMMIT_CONFIG_FILENAME).read_text() + + assert "rev: v" in pre_commit_config + assert "rev: v0.1.0" not in pre_commit_config + + +def test_pdm_install(pdm: PDMCallable, project: Project): + # Needed by pdm 2.7 + # See: https://github.com/pdm-project/pdm/issues/917 + project.pyproject.metadata["requires-python"] = ">=3.9" + project.pyproject.write() + pdm("add ruff==0.6.7 -v", obj=project, strict=True) + + pre_commit_config = (project.root / PRE_COMMIT_CONFIG_FILENAME).read_text() + + assert "rev: v0.6.7" in pre_commit_config diff --git a/tests/test_pdm/test_pdm_plugin.py b/tests/test_pdm/test_pdm_plugin.py index 6ad3b76..a44bdc5 100644 --- a/tests/test_pdm/test_pdm_plugin.py +++ b/tests/test_pdm/test_pdm_plugin.py @@ -7,9 +7,7 @@ pdm_module = pytest.importorskip("pdm") # ruff: noqa: E402 -from pdm.cli.hooks import HookManager from pdm.core import Core -from pdm.models.candidates import Candidate from pdm.project import Project from pdm.termui import UI @@ -32,8 +30,6 @@ def project() -> Project: return x -hooks_mock = mock.create_autospec(HookManager, instance=True) -candidates_mock = [mock.create_autospec(Candidate, instance=True)] config_mock = mock.create_autospec(SyncPreCommitLockConfig, instance=True) printer_mock = mock.create_autospec(PDMPrinter, instance=True) action_mock = mock.create_autospec(PDMSetupPreCommitHooks, instance=True) @@ -47,7 +43,7 @@ def test_on_pdm_install_setup_pre_commit_auto_install_disabled(project: mock.Mag ): from sync_pre_commit_lock.pdm_plugin import on_pdm_install_setup_pre_commit - on_pdm_install_setup_pre_commit(project, hooks=hooks_mock, candidates=candidates_mock, dry_run=False) + on_pdm_install_setup_pre_commit(project, dry_run=False) printer_mock.debug.assert_any_call("Automatically installing pre-commit hooks is disabled. Skipping.") @@ -61,7 +57,7 @@ def test_on_pdm_install_setup_pre_commit_no_config_file(tmp_path: Path, project: ): from sync_pre_commit_lock.pdm_plugin import on_pdm_install_setup_pre_commit - on_pdm_install_setup_pre_commit(project, hooks=hooks_mock, candidates=candidates_mock, dry_run=False) + on_pdm_install_setup_pre_commit(project, dry_run=False) printer_mock.info.assert_called_once_with("No pre-commit config file found, skipping pre-commit hook check") @@ -77,7 +73,7 @@ def test_on_pdm_install_setup_pre_commit_success(project: Project) -> None: ): from sync_pre_commit_lock.pdm_plugin import on_pdm_install_setup_pre_commit - on_pdm_install_setup_pre_commit(project, hooks=hooks_mock, candidates=candidates_mock, dry_run=False) + on_pdm_install_setup_pre_commit(project, dry_run=False) action_mock.execute.assert_called_once() diff --git a/tox.ini b/tox.ini index 87c9665..5968d7d 100644 --- a/tox.ini +++ b/tox.ini @@ -4,12 +4,12 @@ requires = env_list = clean report - py{313, 312, 311, 310, 39}-pdm{218, 217, 216, 215, 214, 213, 212, 211, 210, 29, 28, 27, HEAD} + py{313, 312, 311, 310, 39}-pdm{219, 218, 217, 216, 215, 214, 213, 212, 211, 210, 29, 28, 27, HEAD} py{313, 312, 311, 310, 39}-poetry{18, 17, 16, HEAD} [testenv] set_env = - py{39,310,311,312,313}-pdm{27,28,29,210,211,212,213,214,215,216,217,218, HEAD}: COVERAGE_FILE = .coverage.{envname} + py{39,310,311,312,313}-pdm{27,28,29,210,211,212,213,214,215,216,217,218, 219, HEAD}: COVERAGE_FILE = .coverage.{envname} py{39,310,311,312,313}-poetry{16, 17, 18, HEAD}: COVERAGE_FILE = .coverage.{envname} commands = pytest --cov --cov-append --cov-report=term-missing {posargs:-vv} --cov-config=pyproject.toml @@ -18,9 +18,9 @@ allowlist_externals = pdm pytest depends = - report: py{313, 312, 311, 310, 39}-pdm{218, 217, 216, 215, 214, 213, 212, 211, 210, 29, 28, 27, HEAD} + report: py{313, 312, 311, 310, 39}-pdm{219, 218, 217, 216, 215, 214, 213, 212, 211, 210, 29, 28, 27, HEAD} report: py{313, 312, 311, 310, 39}-poetry{18, 17, 16, HEAD} - py{313, 312, 311, 310, 39}-pdm{218, 217, 216, 215, 214, 213, 212, 211, 210, 29, 28, 27, HEAD}: clean + py{313, 312, 311, 310, 39}-pdm{219, 218, 217, 216, 215, 214, 213, 212, 211, 210, 29, 28, 27, HEAD}: clean py{313, 312, 311, 310, 39}-poetry{18, 17, 16, HEAD}: clean [testenv:clean] @@ -41,10 +41,11 @@ commands = coverage html coverage xml -[testenv:py{39,310,311,312,313}-pdm{27,28,29,210,211,212,213,214,215,216,217,218,HEAD}] +[testenv:py{39,310,311,312,313}-pdm{27,28,29,210,211,212,213,214,215,216,217,218,219,HEAD}] package = editable deps = -r requirements-tox.txt + py39-pdm27: importlib-metadata<8 pdm210: pdm<2.11,>=2.10 pdm211: pdm<2.12,>=2.11 pdm212: pdm<2.13,>=2.12 @@ -54,6 +55,7 @@ deps = pdm216: pdm<2.17,>=2.16 pdm217: pdm<2.18,>=2.17 pdm218: pdm<2.19,>=2.18 + pdm219: pdm<2.20,>=2.19 pdm27: pdm<2.8,>=2.7 pdm28: pdm<2.9,>=2.8 pdm29: pdm<2.10,>=2.9 @@ -70,9 +72,9 @@ deps = [gh] python = - 3.9= py39-pdm{27,28,29,210,211,212,213,214,215,216,217,218,HEAD},py39-poetry{16, 17, 18, HEAD}, report, clean - 3.10= py310-pdm{27,28,29,210,211,212,213,214,215,216,217,218,HEAD}, py310-poetry{16, 17, 18, HEAD}, report, clean - 3.11= py311-pdm{27,28,29,210,211,212,213,214,215,216,217,218,HEAD}, py311-poetry{16, 17, 18, HEAD}, report, clean - 3.12= py312-pdm{27,28,29,210,211,212,213,214,215,216,217,218,HEAD}, py312-poetry{16, 17, 18, HEAD}, report, clean - 3.13= py313-pdm{27,28,29,210,211,212,213,214,215,216,217,218,HEAD}, py313-poetry{16, 17, 18, HEAD}, report, clean + 3.9= py39-pdm{27,28,29,210,211,212,213,214,215,216,217,218,219, HEAD},py39-poetry{16, 17, 18, HEAD}, report, clean + 3.10= py310-pdm{27,28,29,210,211,212,213,214,215,216,217,218,219,HEAD}, py310-poetry{16, 17, 18, HEAD}, report, clean + 3.11= py311-pdm{27,28,29,210,211,212,213,214,215,216,217,218,219,HEAD}, py311-poetry{16, 17, 18, HEAD}, report, clean + 3.12= py312-pdm{27,28,29,210,211,212,213,214,215,216,217,218,219,HEAD}, py312-poetry{16, 17, 18, HEAD}, report, clean + 3.13= py313-pdm{27,28,29,210,211,212,213,214,215,216,217,218,219,HEAD}, py313-poetry{16, 17, 18, HEAD}, report, clean fail_on_no_env = True