Skip to content

Commit

Permalink
Unwrap ProxyError when evaluating retries (#1830)
Browse files Browse the repository at this point in the history
  • Loading branch information
hodbn authored and sethmlarson committed Apr 11, 2020
1 parent 240aa20 commit 308a08f
Show file tree
Hide file tree
Showing 3 changed files with 29 additions and 1 deletion.
5 changes: 4 additions & 1 deletion src/urllib3/exceptions.py
Expand Up @@ -45,7 +45,10 @@ class SSLError(HTTPError):

class ProxyError(HTTPError):
"Raised when the connection to a proxy fails."
pass

def __init__(self, message, error, *args):
super(ProxyError, self).__init__(message, error, *args)
self.original_error = error


class DecodeError(HTTPError):
Expand Down
3 changes: 3 additions & 0 deletions src/urllib3/util/retry.py
Expand Up @@ -13,6 +13,7 @@
ReadTimeoutError,
ResponseError,
InvalidHeader,
ProxyError,
)
from ..packages import six

Expand Down Expand Up @@ -306,6 +307,8 @@ def _is_connection_error(self, err):
""" Errors when we're fairly sure that the server did not receive the
request, so it should be safe to retry.
"""
if isinstance(err, ProxyError):
err = err.original_error
return isinstance(err, ConnectTimeoutError)

def _is_read_error(self, err):
Expand Down
22 changes: 22 additions & 0 deletions test/test_proxymanager.py
@@ -1,6 +1,14 @@
import pytest

from .port_helpers import find_unused_port
from urllib3.poolmanager import ProxyManager
from urllib3.util.url import parse_url
from urllib3.util.retry import Retry
from urllib3.exceptions import (
MaxRetryError,
ProxyError,
NewConnectionError,
)


class TestProxyManager(object):
Expand Down Expand Up @@ -43,3 +51,17 @@ def test_invalid_scheme(self):
ProxyManager("invalid://host/p")
with pytest.raises(ValueError):
ProxyManager("invalid://host/p")

def test_proxy_connect_retry(self):
retry = Retry(total=None, connect=False)
with find_unused_port() as port:
with ProxyManager("http://localhost:{}".format(port)) as p:
with pytest.raises(ProxyError) as ei:
p.urlopen("HEAD", url="http://localhost/", retries=retry)
assert isinstance(ei.value.original_error, NewConnectionError)

retry = Retry(total=None, connect=2)
with ProxyManager("http://localhost:{}".format(port)) as p:
with pytest.raises(MaxRetryError) as ei:
p.urlopen("HEAD", url="http://localhost/", retries=retry)
assert isinstance(ei.value.reason.original_error, NewConnectionError)

0 comments on commit 308a08f

Please sign in to comment.