Skip to content

Commit

Permalink
Add --categories option to work with requirements txt files
Browse files Browse the repository at this point in the history
  • Loading branch information
DasaniT committed Aug 14, 2023
1 parent 549c661 commit 29cf63e
Show file tree
Hide file tree
Showing 6 changed files with 79 additions and 7 deletions.
1 change: 1 addition & 0 deletions news/5722.feature.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
The ``--categories`` option now works with requirements.txt file.
8 changes: 7 additions & 1 deletion pipenv/routines/install.py
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ def do_install(
skip_requirements=skip_requirements,
pypi_mirror=pypi_mirror,
site_packages=site_packages,
categories=categories,
)
# Don't attempt to install develop and default packages if Pipfile is missing
if not project.pipfile_exists and not (package_args or dev):
Expand Down Expand Up @@ -131,7 +132,12 @@ def do_install(
err=True,
)
try:
import_requirements(project, r=project.path_to(requirementstxt), dev=dev)
import_requirements(
project,
r=project.path_to(requirementstxt),
dev=dev,
categories=categories,
)
except (UnicodeDecodeError, PipError) as e:
# Don't print the temp file path if remote since it will be deleted.
req_path = requirements_url if remote else project.path_to(requirementstxt)
Expand Down
6 changes: 4 additions & 2 deletions pipenv/utils/pipfile.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,9 @@ def find_pipfile(max_depth=3):
raise RuntimeError("No Pipfile found!")


def ensure_pipfile(project, validate=True, skip_requirements=False, system=False):
def ensure_pipfile(
project, validate=True, skip_requirements=False, system=False, categories=None
):
"""Creates a Pipfile for the project, if it doesn't exist."""

# Assert Pipfile exists.
Expand Down Expand Up @@ -81,7 +83,7 @@ def ensure_pipfile(project, validate=True, skip_requirements=False, system=False
) as st:
# Import requirements.txt.
try:
import_requirements(project)
import_requirements(project, categories=categories)
except Exception:
err.print(environments.PIPENV_SPINNER_FAIL_TEXT.format("Failed..."))
else:
Expand Down
2 changes: 2 additions & 0 deletions pipenv/utils/project.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ def ensure_project(
skip_requirements=False,
pypi_mirror=None,
clear=False,
categories=None,
):
"""Ensures both Pipfile and virtualenv exist for the project."""

Expand Down Expand Up @@ -78,5 +79,6 @@ def ensure_project(
validate=validate,
skip_requirements=skip_requirements,
system=system,
categories=categories,
)
os.environ["PIP_PYTHON_PATH"] = project.python(system=system)
21 changes: 18 additions & 3 deletions pipenv/utils/requirements.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
from pipenv.utils.pip import get_trusted_hosts


def import_requirements(project, r=None, dev=False):
def import_requirements(project, r=None, dev=False, categories=None):
# Parse requirements.txt file with Pip's parser.
# Pip requires a `PipSession` which is a subclass of requests.Session.
# Since we're not making any network calls, it's initialized to nothing.
Expand All @@ -23,6 +23,8 @@ def import_requirements(project, r=None, dev=False):
r = project.requirements_location
with open(r) as f:
contents = f.read()
if categories is None:
categories = []
indexes = []
trusted_hosts = []
# Find and add extra indexes.
Expand Down Expand Up @@ -56,9 +58,22 @@ def import_requirements(project, r=None, dev=False):
package_string = str(package.link._url)
else:
package_string = str(package.link)
project.add_package_to_pipfile(package_string, dev=dev)
if categories:
for category in categories:
project.add_package_to_pipfile(
package_string, dev=dev, category=category
)
else:
project.add_package_to_pipfile(package_string, dev=dev)
else:
project.add_package_to_pipfile(str(package.req), dev=dev)
if categories:
for category in categories:
project.add_package_to_pipfile(
str(package.req), dev=dev, category=category
)
else:
project.add_package_to_pipfile(str(package.req), dev=dev)

for index in indexes:
add_index_to_pipfile(project, index, trusted_hosts)
project.recase_pipfile()
Expand Down
48 changes: 47 additions & 1 deletion tests/integration/test_install_categories.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,29 @@ def test_basic_category_install(pipenv_instance_private_pypi):

@pytest.mark.categories
@pytest.mark.install
@pytest.mark.parametrize('categories', ["prereq other", "prereq, other"])
@pytest.mark.requirements
def test_basic_category_install_from_requirements(pipenv_instance_private_pypi):
with pipenv_instance_private_pypi(pipfile=False) as p:
# Write a requirements file
with open("requirements.txt", "w") as f:
f.write(f"six==1.16.0")

Check failure on line 26 in tests/integration/test_install_categories.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (F541)

tests/integration/test_install_categories.py:26:21: F541 f-string without any placeholders

c = p.pipenv("install --categories prereq")
assert c.returncode == 0
os.unlink("requirements.txt")
print(c.stdout)
print(c.stderr)
# assert stuff in pipfile
assert c.returncode == 0
assert "six" not in p.pipfile["packages"]
assert "six" not in p.lockfile["default"]
assert "six" in p.pipfile["prereq"]
assert "six" in p.lockfile["prereq"]


@pytest.mark.categories
@pytest.mark.install
@pytest.mark.parametrize("categories", ["prereq other", "prereq, other"])
def test_multiple_category_install(pipenv_instance_private_pypi, categories):
with pipenv_instance_private_pypi() as p:
c = p.pipenv('install six --categories="prereq other"')
Expand All @@ -31,6 +53,30 @@ def test_multiple_category_install(pipenv_instance_private_pypi, categories):
assert "six" in p.lockfile["other"]


@pytest.mark.categories
@pytest.mark.install
@pytest.mark.requirements
def test_multiple_category_install_from_requirements(pipenv_instance_private_pypi):
with pipenv_instance_private_pypi(pipfile=False) as p:
# Write a requirements file
with open("requirements.txt", "w") as f:
f.write("six==1.16.0")

c = p.pipenv('install --categories="prereq other"')
assert c.returncode == 0
os.unlink("requirements.txt")
print(c.stdout)
print(c.stderr)
# assert stuff in pipfile
assert c.returncode == 0
assert "six" not in p.pipfile["packages"]
assert "six" not in p.lockfile["default"]
assert "six" in p.pipfile["prereq"]
assert "six" in p.lockfile["prereq"]
assert "six" in p.pipfile["other"]
assert "six" in p.lockfile["other"]


@pytest.mark.extras
@pytest.mark.install
@pytest.mark.local
Expand Down

0 comments on commit 29cf63e

Please sign in to comment.