Skip to content

Commit

Permalink
Merge pull request #8584 from McSinyx/range-unsupported-exc
Browse files Browse the repository at this point in the history
  • Loading branch information
pradyunsg authored Jul 21, 2020
2 parents d504fc4 + 892018e commit 982aac5
Show file tree
Hide file tree
Showing 3 changed files with 28 additions and 11 deletions.
14 changes: 10 additions & 4 deletions src/pip/_internal/network/lazy_wheel.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
"""Lazy ZIP over HTTP"""

__all__ = ['dist_from_wheel_url']
__all__ = ['HTTPRangeRequestUnsupported', 'dist_from_wheel_url']

from bisect import bisect_left, bisect_right
from contextlib import contextmanager
Expand All @@ -27,13 +27,18 @@
from pip._internal.network.session import PipSession


class HTTPRangeRequestUnsupported(Exception):
pass


def dist_from_wheel_url(name, url, session):
# type: (str, str, PipSession) -> Distribution
"""Return a pkg_resources.Distribution from the given wheel URL.
This uses HTTP range requests to only fetch the potion of the wheel
containing metadata, just enough for the object to be constructed.
If such requests are not supported, RuntimeError is raised.
If such requests are not supported, HTTPRangeRequestUnsupported
is raised.
"""
with LazyZipOverHTTP(url, session) as wheel:
# For read-only ZIP files, ZipFile only needs methods read,
Expand All @@ -49,7 +54,8 @@ class LazyZipOverHTTP(object):
This uses HTTP range requests to lazily fetch the file's content,
which is supposed to be fed to ZipFile. If such requests are not
supported by the server, raise RuntimeError during initialization.
supported by the server, raise HTTPRangeRequestUnsupported
during initialization.
"""

def __init__(self, url, session, chunk_size=CONTENT_CHUNK_SIZE):
Expand All @@ -64,7 +70,7 @@ def __init__(self, url, session, chunk_size=CONTENT_CHUNK_SIZE):
self._left = [] # type: List[int]
self._right = [] # type: List[int]
if 'bytes' not in head.headers.get('Accept-Ranges', 'none'):
raise RuntimeError('range request is not supported')
raise HTTPRangeRequestUnsupported('range request is not supported')
self._check_zip()

@property
Expand Down
Binary file added tests/data/packages/mypy-0.782-py3-none-any.whl
Binary file not shown.
25 changes: 18 additions & 7 deletions tests/unit/test_network_lazy_wheel.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,12 @@
from pip._vendor.pkg_resources import Requirement
from pytest import fixture, mark, raises

from pip._internal.network.lazy_wheel import dist_from_wheel_url
from pip._internal.network.lazy_wheel import (
HTTPRangeRequestUnsupported,
dist_from_wheel_url,
)
from pip._internal.network.session import PipSession
from tests.lib.requests_mocks import MockResponse
from tests.lib.server import file_response

MYPY_0_782_WHL = (
'https://files.pythonhosted.org/packages/9d/65/'
Expand All @@ -25,6 +28,16 @@ def session():
return PipSession()


@fixture
def mypy_whl_no_range(mock_server, shared_data):
mypy_whl = shared_data.packages / 'mypy-0.782-py3-none-any.whl'
mock_server.set_responses([file_response(mypy_whl)])
mock_server.start()
base_address = 'http://{}:{}'.format(mock_server.host, mock_server.port)
yield "{}/{}".format(base_address, 'mypy-0.782-py3-none-any.whl')
mock_server.stop()


@mark.network
def test_dist_from_wheel_url(session):
"""Test if the acquired distribution contain correct information."""
Expand All @@ -35,12 +48,10 @@ def test_dist_from_wheel_url(session):
assert set(dist.requires(dist.extras)) == MYPY_0_782_REQS


@mark.network
def test_dist_from_wheel_url_no_range(session, monkeypatch):
def test_dist_from_wheel_url_no_range(session, mypy_whl_no_range):
"""Test handling when HTTP range requests are not supported."""
monkeypatch.setattr(session, 'head', lambda *a, **kw: MockResponse(b''))
with raises(RuntimeError):
dist_from_wheel_url('mypy', MYPY_0_782_WHL, session)
with raises(HTTPRangeRequestUnsupported):
dist_from_wheel_url('mypy', mypy_whl_no_range, session)


@mark.network
Expand Down

0 comments on commit 982aac5

Please sign in to comment.