Skip to content

Commit 10be5b9

Browse files
authored
Include the package name in the information to the resolver (#5930)
* Include the package name in the information to the resolver * Fix unit tests * fix unit tests
1 parent 539f96d commit 10be5b9

File tree

4 files changed

+34
-39
lines changed

4 files changed

+34
-39
lines changed

pipenv/resolver.py

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,11 @@ def handle_parsed_args(parsed):
8383
with open(parsed.constraints_file) as constraints:
8484
file_constraints = constraints.read().strip().split("\n")
8585
os.unlink(parsed.constraints_file)
86-
parsed.packages += sorted(file_constraints)
86+
packages = {}
87+
for line in file_constraints:
88+
dep_name, pip_line = line.split(",", 1)
89+
packages[dep_name] = pip_line
90+
parsed.packages = packages
8791
return parsed
8892

8993

@@ -579,12 +583,8 @@ def resolve_packages(
579583
else None
580584
)
581585

582-
if not isinstance(packages, set):
583-
packages = set(packages)
584-
if not isinstance(constraints, set):
585-
constraints = set(constraints) if constraints else set()
586586
if constraints:
587-
packages |= constraints
587+
packages.update(constraints)
588588

589589
def resolve(
590590
packages, pre, project, sources, clear, system, category, requirements_dir=None

pipenv/utils/dependencies.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -467,14 +467,14 @@ def convert_deps_to_pip(
467467
include_index=False,
468468
):
469469
""" "Converts a Pipfile-formatted dependency to a pip-formatted one."""
470-
dependencies = []
470+
dependencies = {}
471471
if indexes is None:
472472
indexes = []
473473
for dep_name, dep in deps.items():
474474
req = dependency_as_pip_install_line(
475475
dep_name, dep, include_hashes, include_markers, include_index, indexes
476476
)
477-
dependencies.append(req)
477+
dependencies[dep_name] = req
478478
return dependencies
479479

480480

@@ -942,7 +942,7 @@ def expansive_install_req_from_line(
942942
:return: A tuple of the InstallRequirement and the name of the package (if determined).
943943
"""
944944
name = None
945-
pip_line = pip_line.strip("'")
945+
pip_line = pip_line.strip("'").lstrip(" ")
946946
for new_req_symbol in ("@ ", " @ "): # Check for new style pip lines
947947
if new_req_symbol in pip_line:
948948
pip_line_parts = pip_line.split(new_req_symbol, 1)

pipenv/utils/resolver.py

Lines changed: 7 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
import warnings
88
from functools import lru_cache
99
from pathlib import Path
10-
from typing import Dict, List, Optional, Set
10+
from typing import Dict, List, Optional
1111

1212
from pipenv import environments, resolver
1313
from pipenv.exceptions import ResolutionFailure
@@ -40,7 +40,6 @@
4040
from .dependencies import (
4141
HackedPythonVersion,
4242
convert_deps_to_pip,
43-
determine_package_name,
4443
expansive_install_req_from_line,
4544
get_constraints_from_deps,
4645
get_lockfile_section_using_pipfile_category,
@@ -174,7 +173,7 @@ def check_if_package_req_skipped(
174173
@classmethod
175174
def create(
176175
cls,
177-
deps: Set[str],
176+
deps: Dict[str, str],
178177
project: Project,
179178
index_lookup: Dict[str, str] = None,
180179
markers_lookup: Dict[str, str] = None,
@@ -198,15 +197,11 @@ def create(
198197
sources = project.sources
199198
packages = project.get_pipfile_section(category)
200199
constraints = set()
201-
for dep in deps: # Build up the index and markers lookups
200+
for package_name, dep in deps.items(): # Build up the index and markers lookups
202201
if not dep:
203202
continue
204203
is_constraint = True
205-
install_req, package_name = expansive_install_req_from_line(
206-
dep, expand_env=True
207-
)
208-
if package_name is None:
209-
package_name = determine_package_name(install_req)
204+
install_req, _ = expansive_install_req_from_line(dep, expand_env=True)
210205
original_deps[package_name] = dep
211206
install_reqs[package_name] = install_req
212207
index, extra_index, trust_host, remainder = parse_indexes(dep)
@@ -782,7 +777,6 @@ def venv_resolve_deps(
782777
deps = convert_deps_to_pip(
783778
deps, project.pipfile_sources(), include_index=True
784779
)
785-
constraints = set(deps)
786780
# Useful for debugging and hitting breakpoints in the resolver
787781
if project.s.PIPENV_RESOLVER_PARENT_PYTHON:
788782
try:
@@ -795,7 +789,7 @@ def venv_resolve_deps(
795789
requirements_dir=req_dir,
796790
packages=deps,
797791
category=category,
798-
constraints=constraints,
792+
constraints=deps,
799793
)
800794
if results:
801795
st.console.print(
@@ -831,7 +825,8 @@ def venv_resolve_deps(
831825
with tempfile.NamedTemporaryFile(
832826
mode="w+", prefix="pipenv", suffix="constraints.txt", delete=False
833827
) as constraints_file:
834-
constraints_file.write(str("\n".join(constraints)))
828+
for dep_name, pip_line in deps.items():
829+
constraints_file.write(f"{dep_name}, {pip_line}\n")
835830
cmd.append("--constraints-file")
836831
cmd.append(constraints_file.name)
837832
st.console.print("Resolving dependencies...")

tests/unit/test_utils.py

Lines changed: 18 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,10 @@
1313

1414
# Pipfile format <-> requirements.txt format.
1515
DEP_PIP_PAIRS = [
16-
({"django": ">1.10"}, "django>1.10"),
17-
({"Django": ">1.10"}, "Django>1.10"),
18-
({"requests": {"extras": ["socks"], "version": ">1.10"}}, "requests[socks]>1.10"),
19-
({"requests": {"extras": ["socks"], "version": "==1.10"}}, "requests[socks]==1.10"),
16+
({"django": ">1.10"}, {"django": "django>1.10"}),
17+
({"Django": ">1.10"}, {"Django": "Django>1.10"}),
18+
({"requests": {"extras": ["socks"], "version": ">1.10"}}, {"requests": "requests[socks]>1.10"}),
19+
({"requests": {"extras": ["socks"], "version": "==1.10"}}, {"requests": "requests[socks]==1.10"}),
2020
(
2121
{
2222
"dataclasses-json": {
@@ -25,11 +25,11 @@
2525
"editable": True,
2626
}
2727
},
28-
"dataclasses-json@ git+https://github.com/lidatong/dataclasses-json.git@v0.5.7",
28+
{"dataclasses-json": "dataclasses-json@ git+https://github.com/lidatong/dataclasses-json.git@v0.5.7"},
2929
),
3030
(
3131
{"dataclasses-json": {"git": "https://github.com/lidatong/dataclasses-json.git", "ref": "v0.5.7"}},
32-
"dataclasses-json@ git+https://github.com/lidatong/dataclasses-json.git@v0.5.7",
32+
{"dataclasses-json": "dataclasses-json@ git+https://github.com/lidatong/dataclasses-json.git@v0.5.7"},
3333
),
3434
(
3535
# Extras in url
@@ -39,7 +39,7 @@
3939
"extras": ["pipenv"],
4040
}
4141
},
42-
"dparse[pipenv] @ https://github.com/oz123/dparse/archive/refs/heads/master.zip",
42+
{"dparse": "dparse[pipenv] @ https://github.com/oz123/dparse/archive/refs/heads/master.zip"},
4343
),
4444
(
4545
{
@@ -50,7 +50,7 @@
5050
"editable": False,
5151
}
5252
},
53-
"requests[security]@ git+https://github.com/requests/requests.git@main",
53+
{"requests": "requests[security]@ git+https://github.com/requests/requests.git@main"},
5454
),
5555
]
5656

@@ -64,23 +64,23 @@ def mock_unpack(link, source_dir, download_dir, only_download=False, session=Non
6464
@pytest.mark.parametrize("deps, expected", DEP_PIP_PAIRS)
6565
@pytest.mark.needs_internet
6666
def test_convert_deps_to_pip(deps, expected):
67-
assert dependencies.convert_deps_to_pip(deps) == [expected]
67+
assert dependencies.convert_deps_to_pip(deps) == expected
6868

6969

7070
@pytest.mark.utils
7171
@pytest.mark.needs_internet
7272
def test_convert_deps_to_pip_star_specifier():
7373
deps = {"uvicorn": "*"}
74-
expected = "uvicorn"
75-
assert dependencies.convert_deps_to_pip(deps) == [expected]
74+
expected = {"uvicorn": "uvicorn"}
75+
assert dependencies.convert_deps_to_pip(deps) == expected
7676

7777

7878
@pytest.mark.utils
7979
@pytest.mark.needs_internet
8080
def test_convert_deps_to_pip_extras_no_version():
8181
deps = {"uvicorn": {"extras": ["standard"], "version": "*"}}
82-
expected = "uvicorn[standard]"
83-
assert dependencies.convert_deps_to_pip(deps) == [expected]
82+
expected = {"uvicorn": "uvicorn[standard]"}
83+
assert dependencies.convert_deps_to_pip(deps) == expected
8484

8585

8686
@pytest.mark.utils
@@ -95,7 +95,7 @@ def test_convert_deps_to_pip_extras_no_version():
9595
"hash": "sha256:2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824",
9696
}
9797
},
98-
"FooProject==1.2 --hash=sha256:2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824",
98+
{"FooProject": "FooProject==1.2 --hash=sha256:2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824"},
9999
),
100100
(
101101
{
@@ -105,7 +105,7 @@ def test_convert_deps_to_pip_extras_no_version():
105105
"hash": "sha256:2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824",
106106
}
107107
},
108-
"FooProject[stuff]==1.2 --hash=sha256:2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824",
108+
{"FooProject": "FooProject[stuff]==1.2 --hash=sha256:2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824"},
109109
),
110110
(
111111
{
@@ -115,7 +115,7 @@ def test_convert_deps_to_pip_extras_no_version():
115115
"extras": ["standard"],
116116
}
117117
},
118-
"git+https://github.com/encode/uvicorn.git@master#egg=uvicorn[standard]",
118+
{"uvicorn": "git+https://github.com/encode/uvicorn.git@master#egg=uvicorn[standard]"},
119119
),
120120
],
121121
)
@@ -126,8 +126,8 @@ def test_convert_deps_to_pip_one_way(deps, expected):
126126
@pytest.mark.utils
127127
def test_convert_deps_to_pip_one_way():
128128
deps = {"uvicorn": {}}
129-
expected = "uvicorn"
130-
assert dependencies.convert_deps_to_pip(deps) == [expected.lower()]
129+
expected = {"uvicorn": "uvicorn"}
130+
assert dependencies.convert_deps_to_pip(deps) == expected
131131

132132

133133
@pytest.mark.utils

0 commit comments

Comments
 (0)