Prepare vcs deps before resolution

- Ensure that VCS dependencies run through the RequirementPreparer
  before we call `get_dist()` on them.
- Fixes #2310

Signed-off-by: Dan Ryan <dan@danryan.co>
This commit is contained in:
Dan Ryan
2018-06-07 00:50:44 -04:00
parent e937d85515
commit cdde5b12bb
4 changed files with 62 additions and 58 deletions
@@ -28,4 +28,5 @@ from .pip_compat import (
get_installed_distributions,
PyPI,
SafeFileCache,
InstallationError,
)
@@ -39,3 +39,4 @@ cmdoptions = do_import('cmdoptions', vendored_name='notpip')
get_installed_distributions = do_import('utils.misc', 'get_installed_distributions', old_path='utils', vendored_name='notpip')
PyPI = do_import('models.index', 'PyPI', vendored_name='notpip')
SafeFileCache = do_import('download', 'SafeFileCache', vendored_name='notpip')
InstallationError = do_import('exceptions', 'InstallationError', vendored_name='notpip')
+21 -18
View File
@@ -19,6 +19,7 @@ from .._compat import (
PyPI,
InstallRequirement,
SafeFileCache,
InstallationError,
)
from notpip._vendor.packaging.requirements import InvalidRequirement, Requirement
@@ -257,24 +258,6 @@ class PyPIRepository(BaseRepository):
if not (ireq.editable or is_pinned_requirement(ireq)):
raise TypeError('Expected pinned or editable InstallRequirement, got {}'.format(ireq))
# Collect setup_requires info from local eggs.
setup_requires = {}
if ireq.editable:
try:
dist = ireq.get_dist()
if dist.has_metadata('requires.txt'):
setup_requires = self.finder.get_extras_links(
dist.get_metadata_lines('requires.txt')
)
# HACK: Sometimes the InstallRequirement doesn't properly get
# these values set on it during the resolution process. It's
# difficult to pin down what is going wrong. This fixes things.
ireq.version = dist.version
ireq.project_name = dist.project_name
ireq.req = dist.as_requirement()
except (TypeError, ValueError):
pass
if ireq not in self._dependencies_cache:
if ireq.editable and (ireq.source_dir and os.path.exists(ireq.source_dir)):
# No download_dir for locally available editable requirements.
@@ -338,6 +321,26 @@ class PyPIRepository(BaseRepository):
)
self.resolver.resolve(reqset)
result = reqset.requirements.values()
# Collect setup_requires info from local eggs.
# Do this after we call the preparer on these reqs to make sure their
# egg info has been created
setup_requires = {}
if ireq.editable:
try:
dist = ireq.get_dist()
if dist.has_metadata('requires.txt'):
setup_requires = self.finder.get_extras_links(
dist.get_metadata_lines('requires.txt')
)
# HACK: Sometimes the InstallRequirement doesn't properly get
# these values set on it during the resolution process. It's
# difficult to pin down what is going wrong. This fixes things.
ireq.version = dist.version
ireq.project_name = dist.project_name
ireq.req = dist.as_requirement()
except (TypeError, ValueError):
pass
# Convert setup_requires dict into a somewhat usable form.
if setup_requires:
for section in setup_requires:
+39 -40
View File
@@ -19,7 +19,7 @@ index 4e6174c..75f9b49 100644
# NOTE
# We used to store the cache dir under ~/.pip-tools, which is not the
diff --git a/pipenv/patched/piptools/repositories/pypi.py b/pipenv/patched/piptools/repositories/pypi.py
index 1c4b943..aae0122 100644
index 1c4b943..ab5a56c 100644
--- a/pipenv/patched/piptools/repositories/pypi.py
+++ b/pipenv/patched/piptools/repositories/pypi.py
@@ -4,6 +4,7 @@ from __future__ import (absolute_import, division, print_function,
@@ -30,7 +30,7 @@ index 1c4b943..aae0122 100644
from contextlib import contextmanager
from shutil import rmtree
@@ -15,13 +16,22 @@ from .._compat import (
@@ -15,13 +16,23 @@ from .._compat import (
Wheel,
FAVORITE_HASH,
TemporaryDirectory,
@@ -38,6 +38,7 @@ index 1c4b943..aae0122 100644
+ PyPI,
+ InstallRequirement,
+ SafeFileCache,
+ InstallationError,
)
+from pip._vendor.packaging.requirements import InvalidRequirement, Requirement
@@ -56,7 +57,7 @@ index 1c4b943..aae0122 100644
from .base import BaseRepository
@@ -37,6 +47,40 @@ except ImportError:
@@ -37,6 +48,40 @@ except ImportError:
from pip.wheel import WheelCache
@@ -97,7 +98,7 @@ index 1c4b943..aae0122 100644
class PyPIRepository(BaseRepository):
DEFAULT_INDEX_URL = PyPI.simple_url
@@ -46,10 +90,11 @@ class PyPIRepository(BaseRepository):
@@ -46,10 +91,11 @@ class PyPIRepository(BaseRepository):
config), but any other PyPI mirror can be used if index_urls is
changed/configured on the Finder.
"""
@@ -111,7 +112,7 @@ index 1c4b943..aae0122 100644
index_urls = [pip_options.index_url] + pip_options.extra_index_urls
if pip_options.no_index:
@@ -74,11 +119,15 @@ class PyPIRepository(BaseRepository):
@@ -74,11 +120,15 @@ class PyPIRepository(BaseRepository):
# of all secondary dependencies for the given requirement, so we
# only have to go to disk once for each requirement
self._dependencies_cache = {}
@@ -129,7 +130,7 @@ index 1c4b943..aae0122 100644
def freshen_build_caches(self):
"""
@@ -114,10 +163,19 @@ class PyPIRepository(BaseRepository):
@@ -114,10 +164,19 @@ class PyPIRepository(BaseRepository):
if ireq.editable:
return ireq # return itself as the best match
@@ -151,7 +152,7 @@ index 1c4b943..aae0122 100644
# Reuses pip's internal candidate sort key to sort
matching_candidates = [candidates_by_version[ver] for ver in matching_versions]
@@ -126,11 +184,71 @@ class PyPIRepository(BaseRepository):
@@ -126,11 +185,71 @@ class PyPIRepository(BaseRepository):
best_candidate = max(matching_candidates, key=self.finder._candidate_sort_key)
# Turn the candidate into a pinned InstallRequirement
@@ -226,32 +227,7 @@ index 1c4b943..aae0122 100644
"""
Given a pinned or an editable InstallRequirement, returns a set of
dependencies (also InstallRequirements, but not necessarily pinned).
@@ -139,6 +257,24 @@ class PyPIRepository(BaseRepository):
if not (ireq.editable or is_pinned_requirement(ireq)):
raise TypeError('Expected pinned or editable InstallRequirement, got {}'.format(ireq))
+ # Collect setup_requires info from local eggs.
+ setup_requires = {}
+ if ireq.editable:
+ try:
+ dist = ireq.get_dist()
+ if dist.has_metadata('requires.txt'):
+ setup_requires = self.finder.get_extras_links(
+ dist.get_metadata_lines('requires.txt')
+ )
+ # HACK: Sometimes the InstallRequirement doesn't properly get
+ # these values set on it during the resolution process. It's
+ # difficult to pin down what is going wrong. This fixes things.
+ ireq.version = dist.version
+ ireq.project_name = dist.project_name
+ ireq.req = dist.as_requirement()
+ except (TypeError, ValueError):
+ pass
+
if ireq not in self._dependencies_cache:
if ireq.editable and (ireq.source_dir and os.path.exists(ireq.source_dir)):
# No download_dir for locally available editable requirements.
@@ -164,11 +300,14 @@ class PyPIRepository(BaseRepository):
@@ -164,11 +283,14 @@ class PyPIRepository(BaseRepository):
download_dir=download_dir,
wheel_download_dir=self._wheel_download_dir,
session=self.session,
@@ -268,7 +244,7 @@ index 1c4b943..aae0122 100644
)
except TypeError:
# Pip >= 10 (new resolver!)
@@ -190,14 +329,44 @@ class PyPIRepository(BaseRepository):
@@ -190,14 +312,64 @@ class PyPIRepository(BaseRepository):
upgrade_strategy="to-satisfy-only",
force_reinstall=False,
ignore_dependencies=False,
@@ -283,6 +259,26 @@ index 1c4b943..aae0122 100644
self.resolver.resolve(reqset)
- self._dependencies_cache[ireq] = reqset.requirements.values()
+ result = reqset.requirements.values()
+
+ # Collect setup_requires info from local eggs.
+ # Do this after we call the preparer on these reqs to make sure their
+ # egg info has been created
+ setup_requires = {}
+ if ireq.editable:
+ try:
+ dist = ireq.get_dist()
+ if dist.has_metadata('requires.txt'):
+ setup_requires = self.finder.get_extras_links(
+ dist.get_metadata_lines('requires.txt')
+ )
+ # HACK: Sometimes the InstallRequirement doesn't properly get
+ # these values set on it during the resolution process. It's
+ # difficult to pin down what is going wrong. This fixes things.
+ ireq.version = dist.version
+ ireq.project_name = dist.project_name
+ ireq.req = dist.as_requirement()
+ except (TypeError, ValueError):
+ pass
+ # Convert setup_requires dict into a somewhat usable form.
+ if setup_requires:
+ for section in setup_requires:
@@ -315,7 +311,7 @@ index 1c4b943..aae0122 100644
reqset.cleanup_files()
return set(self._dependencies_cache[ireq])
@@ -224,17 +393,10 @@ class PyPIRepository(BaseRepository):
@@ -224,17 +396,10 @@ class PyPIRepository(BaseRepository):
matching_candidates = candidates_by_version[matching_versions[0]]
return {
@@ -530,10 +526,10 @@ index fde5816..1d732bf 100644
return line
diff --git a/pipenv/patched/piptools/_compat/pip_compat.py b/pipenv/patched/piptools/_compat/pip_compat.py
index 7e8cdf3..4e4e1b2 100644
index 7e8cdf3..0a0d27d 100644
--- a/pipenv/patched/piptools/_compat/pip_compat.py
+++ b/pipenv/patched/piptools/_compat/pip_compat.py
@@ -1,30 +1,41 @@
@@ -1,30 +1,42 @@
# -*- coding=utf-8 -*-
import importlib
@@ -563,7 +559,7 @@ index 7e8cdf3..4e4e1b2 100644
if subimport:
return getattr(_tmp, subimport, _tmp)
return _tmp
-
-InstallRequirement = do_import('req.req_install', 'InstallRequirement')
-parse_requirements = do_import('req.req_file', 'parse_requirements')
@@ -579,6 +575,7 @@ index 7e8cdf3..4e4e1b2 100644
-cmdoptions = do_import('cmdoptions')
-get_installed_distributions = do_import('utils.misc', 'get_installed_distributions', old_path='utils')
-PyPI = do_import('models.index', 'PyPI')
+
+InstallRequirement = do_import('req.req_install', 'InstallRequirement', vendored_name='notpip')
+parse_requirements = do_import('req.req_file', 'parse_requirements', vendored_name='notpip')
+RequirementSet = do_import('req.req_set', 'RequirementSet', vendored_name='notpip')
@@ -594,15 +591,17 @@ index 7e8cdf3..4e4e1b2 100644
+get_installed_distributions = do_import('utils.misc', 'get_installed_distributions', old_path='utils', vendored_name='notpip')
+PyPI = do_import('models.index', 'PyPI', vendored_name='notpip')
+SafeFileCache = do_import('download', 'SafeFileCache', vendored_name='notpip')
+InstallationError = do_import('exceptions', 'InstallationError', vendored_name='notpip')
diff --git a/pipenv/patched/piptools/_compat/__init__.py b/pipenv/patched/piptools/_compat/__init__.py
index 674674a..4259028 100644
index 674674a..feadad8 100644
--- a/pipenv/patched/piptools/_compat/__init__.py
+++ b/pipenv/patched/piptools/_compat/__init__.py
@@ -27,4 +27,5 @@ from .pip_compat import (
@@ -27,4 +27,6 @@ from .pip_compat import (
cmdoptions,
get_installed_distributions,
PyPI,
+ SafeFileCache,
+ InstallationError,
)
diff --git a/pipenv/patched/pip/_vendor/__init__.py b/pipenv/patched/pip/_vendor/__init__.py
index 774f1bf3..40ce7a01 100644