Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Separate pyproject.toml location from root argument #244

Merged
merged 4 commits into from
Dec 27, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 18 additions & 19 deletions deptry/cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
from deptry.compat import metadata
from deptry.config import read_configuration_from_pyproject_toml
from deptry.core import Core
from deptry.utils import PYPROJECT_TOML_PATH, run_within_dir
from deptry.utils import PYPROJECT_TOML_PATH


class CommaSeparatedTupleParamType(click.ParamType):
Expand Down Expand Up @@ -186,7 +186,6 @@ def display_deptry_version(ctx: click.Context, _param: click.Parameter, value: b
help="Path to the pyproject.toml file to read configuration from.",
default=PYPROJECT_TOML_PATH,
expose_value=False,
hidden=True,
)
def deptry(
root: Path,
Expand All @@ -212,20 +211,20 @@ def deptry(
"""

with run_within_dir(root):
Core(
ignore_obsolete=ignore_obsolete,
ignore_missing=ignore_missing,
ignore_transitive=ignore_transitive,
ignore_misplaced_dev=ignore_misplaced_dev,
exclude=exclude,
extend_exclude=extend_exclude,
ignore_notebooks=ignore_notebooks,
skip_obsolete=skip_obsolete,
skip_missing=skip_missing,
skip_transitive=skip_transitive,
skip_misplaced_dev=skip_misplaced_dev,
requirements_txt=requirements_txt,
requirements_txt_dev=requirements_txt_dev,
json_output=json_output,
).run()
Core(
root=root,
ignore_obsolete=ignore_obsolete,
ignore_missing=ignore_missing,
ignore_transitive=ignore_transitive,
ignore_misplaced_dev=ignore_misplaced_dev,
exclude=exclude,
extend_exclude=extend_exclude,
ignore_notebooks=ignore_notebooks,
skip_obsolete=skip_obsolete,
skip_missing=skip_missing,
skip_transitive=skip_transitive,
skip_misplaced_dev=skip_misplaced_dev,
requirements_txt=requirements_txt,
requirements_txt_dev=requirements_txt_dev,
json_output=json_output,
).run()
10 changes: 5 additions & 5 deletions deptry/core.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@

@dataclass
class Core:
root: Path
ignore_obsolete: tuple[str, ...]
ignore_missing: tuple[str, ...]
ignore_transitive: tuple[str, ...]
Expand All @@ -49,7 +50,7 @@ def run(self) -> None:

all_python_files = PythonFileFinder(
exclude=self.exclude + self.extend_exclude, ignore_notebooks=self.ignore_notebooks
).get_all_python_files_in(Path("."))
).get_all_python_files_in(self.root)

local_modules = self._get_local_modules()

Expand Down Expand Up @@ -96,10 +97,9 @@ def _get_dependencies(self, dependency_management_format: DependencyManagementFo
return RequirementsTxtDependencyGetter(self.requirements_txt, self.requirements_txt_dev).get()
raise ValueError("Incorrect dependency manage format. Only poetry, pdm and requirements.txt are supported.")

@staticmethod
def _get_local_modules() -> set[str]:
directories = [f for f in os.listdir() if Path(f).is_dir()]
return {subdir for subdir in directories if "__init__.py" in os.listdir(subdir)}
def _get_local_modules(self) -> set[str]:
directories = [f for f in os.scandir(self.root) if f.is_dir()]
return {subdirectory.name for subdirectory in directories if "__init__.py" in os.listdir(subdirectory)}

def _log_config(self) -> None:
logging.debug("Running with the following configuration:")
Expand Down
24 changes: 1 addition & 23 deletions deptry/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,8 @@

import os
import sys
from contextlib import contextmanager
from pathlib import Path
from typing import Any, Generator
from typing import Any

if sys.version_info >= (3, 11):
import tomllib
Expand All @@ -14,27 +13,6 @@
PYPROJECT_TOML_PATH = "./pyproject.toml"


@contextmanager
def run_within_dir(path: Path) -> Generator[None, None, None]:
"""
Utility function to run some code within a directory, and change back to the current directory afterwards.
Example usage:
```
with run_within_dir(directory):
some_code()
```
"""
oldpwd = os.getcwd()
os.chdir(path)
try:
yield
finally:
os.chdir(oldpwd)


def load_pyproject_toml(pyproject_toml_path: str = PYPROJECT_TOML_PATH) -> dict[str, Any]:
try:
with Path(pyproject_toml_path).open("rb") as pyproject_file:
Expand Down
Empty file added tests/__init__.py
Empty file.
Empty file added tests/cli/__init__.py
Empty file.
2 changes: 1 addition & 1 deletion tests/cli/test_cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
import pytest
from _pytest.tmpdir import TempPathFactory

from deptry.utils import run_within_dir
from tests.utils import run_within_dir


@pytest.fixture(scope="session")
Expand Down
2 changes: 1 addition & 1 deletion tests/cli/test_cli_pdm.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
import pytest
from _pytest.tmpdir import TempPathFactory

from deptry.utils import run_within_dir
from tests.utils import run_within_dir


@pytest.fixture(scope="session")
Expand Down
2 changes: 1 addition & 1 deletion tests/cli/test_cli_pep_621.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
import pytest
from _pytest.tmpdir import TempPathFactory

from deptry.utils import run_within_dir
from tests.utils import run_within_dir


@pytest.fixture(scope="session")
Expand Down
2 changes: 1 addition & 1 deletion tests/cli/test_cli_requirements_txt.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
import pytest
from _pytest.tmpdir import TempPathFactory

from deptry.utils import run_within_dir
from tests.utils import run_within_dir


@pytest.fixture(scope="session")
Expand Down
28 changes: 28 additions & 0 deletions tests/cli/test_cli_src_directory.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import shlex
import shutil
import subprocess
from pathlib import Path

import pytest
from _pytest.tmpdir import TempPathFactory

from tests.utils import run_within_dir


@pytest.fixture(scope="session")
def pep_621_dir_with_src_directory(tmp_path_factory: TempPathFactory) -> Path:
tmp_path_proj = tmp_path_factory.getbasetemp() / "project_with_src_directory"
shutil.copytree("tests/data/project_with_src_directory", str(tmp_path_proj))
with run_within_dir(tmp_path_proj):
assert subprocess.check_call(shlex.split("pip install .")) == 0
return tmp_path_proj


def test_cli_with_src_directory(pep_621_dir_with_src_directory: Path) -> None:
with run_within_dir(pep_621_dir_with_src_directory):
result = subprocess.run(shlex.split("deptry src"), capture_output=True, text=True)
assert result.returncode == 1
assert (
"The project contains obsolete dependencies:\n\n\tisort\n\tmypy\n\tpytest\n\trequests\n\n" in result.stderr
)
assert "There are dependencies missing from the project's list of dependencies:\n\n\twhite\n\n" in result.stderr
30 changes: 30 additions & 0 deletions tests/data/project_with_src_directory/pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
[project]
# PEP 621 project metadata
# See https://www.python.org/dev/peps/pep-0621/
name = "foo"
version = "1.2.3"
requires-python = ">=3.7"
dependencies = [
"toml",
"urllib3>=1.26.12",
"isort>=5.10.1",
"click>=8.1.3",
"requests>=2.28.1",
"pkginfo>=1.8.3",
]

[project.optional-dependencies]
dev = [
"black==22.10.0",
"mypy==0.982",
]
test = [
"pytest==7.2.0",
]

[build-system]
requires = ["setuptools>=61.0.0"]
build-backend = "setuptools.build_meta"

[tool.deptry]
ignore_obsolete = ["pkginfo"]
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from project_with_src_directory.foo import a_local_method
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
from os import chdir, walk
from pathlib import Path

import black
import click
import white as w
from urllib3 import contrib


def a_local_method():
...
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
{
"cells": [
{
"cell_type": "code",
"execution_count": 2,
"id": "9f4924ec-2200-4801-9d49-d4833651cbc4",
"metadata": {},
"outputs": [],
"source": [
"import click\n",
"from urllib3 import contrib\n",
"import toml"
]
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3 (ipykernel)",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.9.11"
}
},
"nbformat": 4,
"nbformat_minor": 5
}
2 changes: 1 addition & 1 deletion tests/dependency_getter/test_pdm.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
from pathlib import Path

from deptry.dependency_getter.pdm import PDMDependencyGetter
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_dependency_getter(tmp_path: Path) -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/dependency_getter/test_pep_621.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
from pathlib import Path

from deptry.dependency_getter.pep_621 import PEP621DependencyGetter
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_dependency_getter(tmp_path: Path) -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/dependency_getter/test_poetry.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
from pathlib import Path

from deptry.dependency_getter.poetry import PoetryDependencyGetter
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_dependency_getter(tmp_path: Path) -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/dependency_getter/test_requirements_txt.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
from pathlib import Path

from deptry.dependency_getter.requirements_txt import RequirementsTxtDependencyGetter
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_parse_requirements_txt(tmp_path: Path) -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/imports/test_extract.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
from _pytest.logging import LogCaptureFixture

from deptry.imports.extract import get_imported_modules_for_list_of_files, get_imported_modules_from_file
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_import_parser_py() -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/test_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
from _pytest.logging import LogCaptureFixture

from deptry.config import read_configuration_from_pyproject_toml
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_read_configuration_from_pyproject_toml_exists(tmp_path: Path) -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/test_dependency_specification_detector.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import pytest

from deptry.dependency_specification_detector import DependencyManagementFormat, DependencySpecificationDetector
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_poetry(tmp_path: Path) -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/test_json_writer.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
from pathlib import Path

from deptry.json_writer import JsonWriter
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def test_simple(tmp_path: Path) -> None:
Expand Down
2 changes: 1 addition & 1 deletion tests/test_python_file_finder.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
from pathlib import Path

from deptry.python_file_finder import PythonFileFinder
from deptry.utils import run_within_dir
from tests.utils import run_within_dir


def create_files_from_list_of_dicts(paths: list[dict[str, str]]) -> None:
Expand Down
25 changes: 25 additions & 0 deletions tests/utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import os
from contextlib import contextmanager
from pathlib import Path
from typing import Generator


@contextmanager
def run_within_dir(path: Path) -> Generator[None, None, None]:
"""
Utility function to run some code within a directory, and change back to the current directory afterwards.
Example usage:
```
with run_within_dir(directory):
some_code()
```
"""
oldpwd = os.getcwd()
os.chdir(path)
try:
yield
finally:
os.chdir(oldpwd)