Skip to content

Commit

Permalink
ngr: Add capability to invoke projects using poethepoet task runner
Browse files Browse the repository at this point in the history
  • Loading branch information
amotl committed Nov 24, 2023
1 parent f04eed7 commit 2e4a64b
Show file tree
Hide file tree
Showing 3 changed files with 67 additions and 7 deletions.
1 change: 1 addition & 0 deletions CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
- ngr: Gradle test runner failed to invoke `./gradlew install` because such a
target did not exist.
- ngr: Fix Gradle test runner by only conditionally invoking `gradle wrapper`
- ngr: Add capability to invoke projects using the `poethepoet` task runner

## 2023-11-06 v0.0.3
- ngr: Fix `contextlib.chdir` only available on Python 3.11 and newer
Expand Down
56 changes: 49 additions & 7 deletions pueblo/ngr/runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -443,9 +443,7 @@ def install(self) -> None:
# they will error out like `error: Multiple top-level modules discovered
# in a flat-layout`.
if self.has_pyproject_toml:
pyproject_toml_file = self.path / "pyproject.toml"
pyproject_toml = pyproject_toml_file.read_text()
if "[project]" not in pyproject_toml:
if not self.pyproject_has_string("[project]"):
pip_install = False

if pip_install:
Expand All @@ -455,22 +453,66 @@ def test(self) -> None:
"""
Test a Python thing, based on which test runner is installed.
TODO: Figure out how to invoke target `poe check`, which is popular amongst
users of `pueblo`. It bundles linter/checkstyle and software test targets
into a single entrypoint, similar to what `gradle check` is doing.
First, try a high-level target of some sort of management tool,
discover its targets, and invoke `check` or `test`.
When no high-level tool can be discovered, just invoke `pytest`.
"""

# On Poetry projects, invoke poetry/pytest.
# TODO: Also allow using Poetry with other task runners, see below.
if self.has_poetry_lock:
# TODO: poetry run which pytest
run_command("poetry run pytest --config-file=.")

else:
uses_poe = self.has_pyproject_toml and self.pyproject_has_string("[tool.poe.tasks]")
has_pytest = shutil.which("pytest") is not None
if has_pytest:

# When a `pyproject.toml` file includes `poethepoet` task definitions, try to
# invoke sensible targets like `check` or `test`. This is popular amongst users
# of `pueblo` and friends.
# `poe check` bundles linter/checkstyle and software test targets into a single
# entrypoint, similar to how `gradle check` is doing it.
if uses_poe:
candidates = ["check", "test"]
poe_tasks = self.get_poe_tasks()
success = False
for candidate in candidates:
if candidate in poe_tasks:
run_command(f"poe {candidate}")
success = True
break
if not success:
raise RuntimeError(f"Failed to discover poe task from candidates: {candidates}")

Check warning on line 487 in pueblo/ngr/runner.py

View check run for this annotation

Codecov / codecov/patch

pueblo/ngr/runner.py#L487

Added line #L487 was not covered by tests

elif has_pytest:
run_command("pytest")
else:
raise NotImplementedError("No handler to invoke Python item")

def pyproject_has_string(self, needle: str) -> bool:
"""
Check whether `pyproject.toml` file contains given string.
"""
pyproject_toml_file = self.path / "pyproject.toml"
pyproject_toml = pyproject_toml_file.read_text()
return needle in pyproject_toml

def get_poe_tasks(self) -> t.List[str]:
"""
From `poethepoet._list_tasks`.
"""
try:
from poethepoet.config import PoeConfig

config = PoeConfig()
config.load()
return [task for task in config.tasks.keys() if task and task[0] != "_"]
except Exception as ex: # pylint: disable=broad-except

Check warning on line 512 in pueblo/ngr/runner.py

View check run for this annotation

Codecov / codecov/patch

pueblo/ngr/runner.py#L512

Added line #L512 was not covered by tests
# this happens if there's no pyproject.toml present
raise ValueError(f"Discovering poe task names failed: {ex}") from ex

Check warning on line 514 in pueblo/ngr/runner.py

View check run for this annotation

Codecov / codecov/patch

pueblo/ngr/runner.py#L514

Added line #L514 was not covered by tests


class RubyRunner(RunnerBase):
"""
Expand Down
17 changes: 17 additions & 0 deletions tests/ngr/python-poethepoet/pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
[project]
name = "ngr-python-test-poethepoet"
version = "0.0.1"

dependencies = [
]

[project.optional-dependencies]
test = [
"pytest<8",
"poethepoet<0.25",
]

[tool.poe.tasks]
test = [
{ cmd="python -c \"print('Hallo, Räuber Hotzenplotz.')\"" },
]

0 comments on commit 2e4a64b

Please sign in to comment.