Harmonize type signature of VersionControl.get_remote_url() subclasses

In the base class, the signature is defined as:

    type: (str) -> str

Further, the docstring says:

    Raises RemoteNotFoundError if the repository does not have a remote
    url configured.

However, some subclasses were returning None instead of raising
RemoteNotFoundError. This violated the type signature and forced calling
code to handle multiple error paradigms.

Now, all subclasses implement the base's signature.

This allowed simplifying some call sites as they can assume None will
not be returned.

This mismatch was noticed while trying to remove "mypy:
disallow-untyped-defs=False" comments.
This commit is contained in:
Jon Dufresne 2020-12-25 11:24:38 -08:00
parent f91ba6b348
commit 0b761a164c
9 changed files with 40 additions and 9 deletions

View File

@ -225,8 +225,7 @@ def get_requirement_info(dist):
"falling back to uneditable format", exc
)
else:
if req is not None:
return (req, True, [])
return (req, True, [])
logger.warning(
'Could not determine repository location of %s', location

View File

@ -9,7 +9,7 @@ from pip._internal.utils.misc import display_path, rmtree
from pip._internal.utils.subprocess import make_command
from pip._internal.utils.typing import MYPY_CHECK_RUNNING
from pip._internal.utils.urls import path_to_url
from pip._internal.vcs.versioncontrol import VersionControl, vcs
from pip._internal.vcs.versioncontrol import RemoteNotFoundError, VersionControl, vcs
if MYPY_CHECK_RUNNING:
from typing import Optional, Tuple
@ -89,6 +89,7 @@ class Bazaar(VersionControl):
@classmethod
def get_remote_url(cls, location):
# type: (str) -> str
urls = cls.run_command(['info'], cwd=location)
for line in urls.splitlines():
line = line.strip()
@ -99,7 +100,7 @@ class Bazaar(VersionControl):
if cls._is_local_repository(repo):
return path_to_url(repo)
return repo
return None
raise RemoteNotFoundError
@classmethod
def get_revision(cls, location):

View File

@ -303,6 +303,7 @@ class Git(VersionControl):
@classmethod
def get_remote_url(cls, location):
# type: (str) -> str
"""
Return URL of the first remote encountered.

View File

@ -87,6 +87,7 @@ class Mercurial(VersionControl):
@classmethod
def get_remote_url(cls, location):
# type: (str) -> str
url = cls.run_command(
['showconfig', 'paths.default'],
cwd=location).strip()

View File

@ -14,7 +14,7 @@ from pip._internal.utils.misc import (
)
from pip._internal.utils.subprocess import make_command
from pip._internal.utils.typing import MYPY_CHECK_RUNNING
from pip._internal.vcs.versioncontrol import VersionControl, vcs
from pip._internal.vcs.versioncontrol import RemoteNotFoundError, VersionControl, vcs
_svn_xml_url_re = re.compile('url="([^"]+)"')
_svn_rev_re = re.compile(r'committed-rev="(\d+)"')
@ -110,6 +110,7 @@ class Subversion(VersionControl):
@classmethod
def get_remote_url(cls, location):
# type: (str) -> str
# In cases where the source is in a subdirectory, not alongside
# setup.py we have to look up in the location until we find a real
# setup.py
@ -125,7 +126,7 @@ class Subversion(VersionControl):
"parent directories)",
orig_location,
)
return None
raise RemoteNotFoundError
return cls._get_svn_url_rev(location)[0]

View File

@ -410,7 +410,7 @@ class VersionControl(object):
@classmethod
def get_src_requirement(cls, repo_dir, project_name):
# type: (str, str) -> Optional[str]
# type: (str, str) -> str
"""
Return the requirement string to use to redownload the files
currently at the given repository directory.
@ -423,8 +423,6 @@ class VersionControl(object):
{repository_url}@{revision}#egg={project_name}
"""
repo_url = cls.get_remote_url(repo_dir)
if repo_url is None:
return None
if cls.should_add_vcs_url_prefix(repo_url):
repo_url = '{}+{}'.format(cls.name, repo_url)

View File

@ -8,6 +8,7 @@ import pytest
from pip._internal.utils.misc import hide_url
from pip._internal.vcs.bazaar import Bazaar
from pip._internal.vcs.versioncontrol import RemoteNotFoundError
from tests.lib import (
_test_path_to_file_url,
_vcs_add,
@ -65,3 +66,15 @@ def test_export_rev(script, tmpdir):
with open(export_dir / 'test_file', 'r') as f:
assert f.read() == 'something initial'
@need_bzr
def test_get_remote_url__no_remote(script, tmpdir):
repo_dir = tmpdir / 'temp-repo'
repo_dir.mkdir()
repo_dir = str(repo_dir)
script.run('bzr', 'init', repo_dir)
with pytest.raises(RemoteNotFoundError):
Bazaar().get_remote_url(repo_dir)

View File

@ -0,0 +1,17 @@
import pytest
from pip._internal.vcs.subversion import Subversion
from pip._internal.vcs.versioncontrol import RemoteNotFoundError
from tests.lib import _create_svn_repo, need_svn
@need_svn
def test_get_remote_url__no_remote(script, tmpdir):
repo_dir = tmpdir / 'temp-repo'
repo_dir.mkdir()
repo_dir = str(repo_dir)
_create_svn_repo(script, repo_dir)
with pytest.raises(RemoteNotFoundError):
Subversion().get_remote_url(repo_dir)