Repository: pypa/pip

Issue:
Rename InstallationCandidate.{location -> link}
In `pip._internal.models.candidate`.

It's more representative of what it really is -- "location" caused confusion whether it's on disk or not. It's not, so `link` is a better name for it IMO.


Discussion:
I had noticed this, too. 👍 

Resolving patch:
diff --git a/src/pip/_internal/commands/list.py b/src/pip/_internal/commands/list.py
--- a/src/pip/_internal/commands/list.py
+++ b/src/pip/_internal/commands/list.py
@@ -197,7 +197,7 @@ def iter_packages_latest_infos(self, packages, options):
                     continue
 
                 remote_version = best_candidate.version
-                if best_candidate.location.is_wheel:
+                if best_candidate.link.is_wheel:
                     typ = 'wheel'
                 else:
                     typ = 'sdist'
diff --git a/src/pip/_internal/index.py b/src/pip/_internal/index.py
--- a/src/pip/_internal/index.py
+++ b/src/pip/_internal/index.py
@@ -477,7 +477,7 @@ def filter_unallowed_hashes(
     non_matches = []
     match_count = 0
     for candidate in candidates:
-        link = candidate.location
+        link = candidate.link
         if not link.has_hash:
             pass
         elif link.is_hash_allowed(hashes=hashes):
@@ -499,7 +499,7 @@ def filter_unallowed_hashes(
     else:
         discard_message = 'discarding {} non-matches:\n  {}'.format(
             len(non_matches),
-            '\n  '.join(str(candidate.location) for candidate in non_matches)
+            '\n  '.join(str(candidate.link) for candidate in non_matches)
         )
 
     logger.debug(
@@ -689,7 +689,7 @@ def _sort_key(self, candidate):
         support_num = len(valid_tags)
         build_tag = tuple()  # type: BuildTag
         binary_preference = 0
-        link = candidate.location
+        link = candidate.link
         if link.is_wheel:
             # can raise InvalidWheelFilename
             wheel = Wheel(link.filename)
@@ -729,7 +729,7 @@ def get_best_candidate(
         best_candidate = max(candidates, key=self._sort_key)
 
         # Log a warning per PEP 592 if necessary before returning.
-        link = best_candidate.location
+        link = best_candidate.link
         if link.is_yanked:
             reason = link.yanked_reason or '<none given>'
             msg = (
@@ -1138,7 +1138,7 @@ def find_all_candidates(self, project_name):
             logger.debug(
                 'Local files found: %s',
                 ', '.join([
-                    url_to_path(candidate.location.url)
+                    url_to_path(candidate.link.url)
                     for candidate in file_versions
                 ])
             )
@@ -1265,7 +1265,7 @@ def _format_versions(cand_iter):
             best_candidate.version,
             _format_versions(candidates.iter_applicable()),
         )
-        return best_candidate.location
+        return best_candidate.link
 
     def _get_pages(self, locations, project_name):
         # type: (Iterable[Link], str) -> Iterable[HTMLPage]
@@ -1327,7 +1327,7 @@ def get_install_candidate(self, link_evaluator, link):
 
         return InstallationCandidate(
             project=link_evaluator.project_name,
-            location=link,
+            link=link,
             # Convert the Text result to str since InstallationCandidate
             # accepts str.
             version=str(result),
diff --git a/src/pip/_internal/models/candidate.py b/src/pip/_internal/models/candidate.py
--- a/src/pip/_internal/models/candidate.py
+++ b/src/pip/_internal/models/candidate.py
@@ -13,24 +13,24 @@ class InstallationCandidate(KeyBasedCompareMixin):
     """Represents a potential "candidate" for installation.
     """
 
-    def __init__(self, project, version, location):
+    def __init__(self, project, version, link):
         # type: (Any, str, Link) -> None
         self.project = project
         self.version = parse_version(version)  # type: _BaseVersion
-        self.location = location
+        self.link = link
 
         super(InstallationCandidate, self).__init__(
-            key=(self.project, self.version, self.location),
+            key=(self.project, self.version, self.link),
             defining_class=InstallationCandidate
         )
 
     def __repr__(self):
         # type: () -> str
         return "<InstallationCandidate({!r}, {!r}, {!r})>".format(
-            self.project, self.version, self.location,
+            self.project, self.version, self.link,
         )
 
     def __str__(self):
         return '{!r} candidate (version {} at {})'.format(
-            self.project, self.version, self.location,
+            self.project, self.version, self.link,
         )


Test patch:
diff --git a/tests/unit/test_finder.py b/tests/unit/test_finder.py
--- a/tests/unit/test_finder.py
+++ b/tests/unit/test_finder.py
@@ -262,8 +262,8 @@ def test_finder_priority_file_over_page(data):
     )
     all_versions = finder.find_all_candidates(req.name)
     # 1 file InstallationCandidate followed by all https ones
-    assert all_versions[0].location.scheme == 'file'
-    assert all(version.location.scheme == 'https'
+    assert all_versions[0].link.scheme == 'file'
+    assert all(version.link.scheme == 'https'
                for version in all_versions[1:]), all_versions
 
     link = finder.find_requirement(req, False)
@@ -279,8 +279,8 @@ def test_finder_priority_nonegg_over_eggfragments():
 
     with patch.object(finder, "_get_pages", lambda x, y: []):
         all_versions = finder.find_all_candidates(req.name)
-        assert all_versions[0].location.url.endswith('tar.gz')
-        assert all_versions[1].location.url.endswith('#egg=bar-1.0')
+        assert all_versions[0].link.url.endswith('tar.gz')
+        assert all_versions[1].link.url.endswith('#egg=bar-1.0')
 
         link = finder.find_requirement(req, False)
 
@@ -291,8 +291,8 @@ def test_finder_priority_nonegg_over_eggfragments():
 
     with patch.object(finder, "_get_pages", lambda x, y: []):
         all_versions = finder.find_all_candidates(req.name)
-        assert all_versions[0].location.url.endswith('tar.gz')
-        assert all_versions[1].location.url.endswith('#egg=bar-1.0')
+        assert all_versions[0].link.url.endswith('tar.gz')
+        assert all_versions[1].link.url.endswith('#egg=bar-1.0')
         link = finder.find_requirement(req, False)
 
     assert link.url.endswith('tar.gz')
diff --git a/tests/unit/test_models.py b/tests/unit/test_models.py
--- a/tests/unit/test_models.py
+++ b/tests/unit/test_models.py
@@ -49,7 +49,7 @@ def test_sets_correct_variables(self):
         )
         assert obj.project == "A"
         assert obj.version == parse_version("1.0.0")
-        assert obj.location == "https://somewhere.com/path/A-1.0.0.tar.gz"
+        assert obj.link == "https://somewhere.com/path/A-1.0.0.tar.gz"
 
     # NOTE: This isn't checking the ordering logic; only the data provided to
     #       it is correct.
@@ -57,4 +57,4 @@ def test_sets_the_right_key(self):
         obj = candidate.InstallationCandidate(
             "A", "1.0.0", "https://somewhere.com/path/A-1.0.0.tar.gz"
         )
-        assert obj._compare_key == (obj.project, obj.version, obj.location)
+        assert obj._compare_key == (obj.project, obj.version, obj.link)