mirror of https://github.com/python/cpython
merge 3.5
Issue #26804: urllib.request will prefer lower_case proxy environment variables over UPPER_CASE or Mixed_Case ones. Patch contributed by Hans-Peter Jansen. Reviewed by Martin Panter and Senthil Kumaran.
This commit is contained in:
commit
0996fa3bd8
|
@ -166,6 +166,8 @@ The :mod:`urllib.request` module defines the following functions:
|
||||||
in a case insensitive approach, for all operating systems first, and when it
|
in a case insensitive approach, for all operating systems first, and when it
|
||||||
cannot find it, looks for proxy information from Mac OSX System
|
cannot find it, looks for proxy information from Mac OSX System
|
||||||
Configuration for Mac OS X and Windows Systems Registry for Windows.
|
Configuration for Mac OS X and Windows Systems Registry for Windows.
|
||||||
|
If both lowercase and uppercase environment variables exist (and disagree),
|
||||||
|
lowercase is preferred.
|
||||||
|
|
||||||
|
|
||||||
The following classes are provided:
|
The following classes are provided:
|
||||||
|
|
|
@ -226,8 +226,46 @@ class ProxyTests(unittest.TestCase):
|
||||||
# getproxies_environment use lowered case truncated (no '_proxy') keys
|
# getproxies_environment use lowered case truncated (no '_proxy') keys
|
||||||
self.assertEqual('localhost', proxies['no'])
|
self.assertEqual('localhost', proxies['no'])
|
||||||
# List of no_proxies with space.
|
# List of no_proxies with space.
|
||||||
self.env.set('NO_PROXY', 'localhost, anotherdomain.com, newdomain.com')
|
self.env.set('NO_PROXY', 'localhost, anotherdomain.com, newdomain.com:1234')
|
||||||
self.assertTrue(urllib.request.proxy_bypass_environment('anotherdomain.com'))
|
self.assertTrue(urllib.request.proxy_bypass_environment('anotherdomain.com'))
|
||||||
|
self.assertTrue(urllib.request.proxy_bypass_environment('anotherdomain.com:8888'))
|
||||||
|
self.assertTrue(urllib.request.proxy_bypass_environment('newdomain.com:1234'))
|
||||||
|
|
||||||
|
|
||||||
|
class ProxyTests_withOrderedEnv(unittest.TestCase):
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
# We need to test conditions, where variable order _is_ significant
|
||||||
|
self._saved_env = os.environ
|
||||||
|
# Monkey patch os.environ, start with empty fake environment
|
||||||
|
os.environ = collections.OrderedDict()
|
||||||
|
|
||||||
|
def tearDown(self):
|
||||||
|
os.environ = self._saved_env
|
||||||
|
|
||||||
|
def test_getproxies_environment_prefer_lowercase(self):
|
||||||
|
# Test lowercase preference with removal
|
||||||
|
os.environ['no_proxy'] = ''
|
||||||
|
os.environ['No_Proxy'] = 'localhost'
|
||||||
|
self.assertFalse(urllib.request.proxy_bypass_environment('localhost'))
|
||||||
|
self.assertFalse(urllib.request.proxy_bypass_environment('arbitrary'))
|
||||||
|
os.environ['http_proxy'] = ''
|
||||||
|
os.environ['HTTP_PROXY'] = 'http://somewhere:3128'
|
||||||
|
proxies = urllib.request.getproxies_environment()
|
||||||
|
self.assertEqual({}, proxies)
|
||||||
|
# Test lowercase preference of proxy bypass and correct matching including ports
|
||||||
|
os.environ['no_proxy'] = 'localhost, noproxy.com, my.proxy:1234'
|
||||||
|
os.environ['No_Proxy'] = 'xyz.com'
|
||||||
|
self.assertTrue(urllib.request.proxy_bypass_environment('localhost'))
|
||||||
|
self.assertTrue(urllib.request.proxy_bypass_environment('noproxy.com:5678'))
|
||||||
|
self.assertTrue(urllib.request.proxy_bypass_environment('my.proxy:1234'))
|
||||||
|
self.assertFalse(urllib.request.proxy_bypass_environment('my.proxy'))
|
||||||
|
self.assertFalse(urllib.request.proxy_bypass_environment('arbitrary'))
|
||||||
|
# Test lowercase preference with replacement
|
||||||
|
os.environ['http_proxy'] = 'http://somewhere:3128'
|
||||||
|
os.environ['Http_Proxy'] = 'http://somewhereelse:3128'
|
||||||
|
proxies = urllib.request.getproxies_environment()
|
||||||
|
self.assertEqual('http://somewhere:3128', proxies['http'])
|
||||||
|
|
||||||
class urlopen_HttpTests(unittest.TestCase, FakeHTTPMixin, FakeFTPMixin):
|
class urlopen_HttpTests(unittest.TestCase, FakeHTTPMixin, FakeFTPMixin):
|
||||||
"""Test urlopen() opening a fake http connection."""
|
"""Test urlopen() opening a fake http connection."""
|
||||||
|
|
|
@ -2455,19 +2455,35 @@ def getproxies_environment():
|
||||||
|
|
||||||
"""
|
"""
|
||||||
proxies = {}
|
proxies = {}
|
||||||
|
# in order to prefer lowercase variables, process environment in
|
||||||
|
# two passes: first matches any, second pass matches lowercase only
|
||||||
for name, value in os.environ.items():
|
for name, value in os.environ.items():
|
||||||
name = name.lower()
|
name = name.lower()
|
||||||
if value and name[-6:] == '_proxy':
|
if value and name[-6:] == '_proxy':
|
||||||
proxies[name[:-6]] = value
|
proxies[name[:-6]] = value
|
||||||
|
for name, value in os.environ.items():
|
||||||
|
if name[-6:] == '_proxy':
|
||||||
|
name = name.lower()
|
||||||
|
if value:
|
||||||
|
proxies[name[:-6]] = value
|
||||||
|
else:
|
||||||
|
proxies.pop(name[:-6], None)
|
||||||
return proxies
|
return proxies
|
||||||
|
|
||||||
def proxy_bypass_environment(host):
|
def proxy_bypass_environment(host, proxies=None):
|
||||||
"""Test if proxies should not be used for a particular host.
|
"""Test if proxies should not be used for a particular host.
|
||||||
|
|
||||||
Checks the environment for a variable named no_proxy, which should
|
Checks the proxy dict for the value of no_proxy, which should
|
||||||
be a list of DNS suffixes separated by commas, or '*' for all hosts.
|
be a list of comma separated DNS suffixes, or '*' for all hosts.
|
||||||
|
|
||||||
"""
|
"""
|
||||||
no_proxy = os.environ.get('no_proxy', '') or os.environ.get('NO_PROXY', '')
|
if proxies is None:
|
||||||
|
proxies = getproxies_environment()
|
||||||
|
# don't bypass, if no_proxy isn't specified
|
||||||
|
try:
|
||||||
|
no_proxy = proxies['no']
|
||||||
|
except KeyError:
|
||||||
|
return 0
|
||||||
# '*' is special case for always bypass
|
# '*' is special case for always bypass
|
||||||
if no_proxy == '*':
|
if no_proxy == '*':
|
||||||
return 1
|
return 1
|
||||||
|
@ -2562,8 +2578,15 @@ if sys.platform == 'darwin':
|
||||||
|
|
||||||
|
|
||||||
def proxy_bypass(host):
|
def proxy_bypass(host):
|
||||||
if getproxies_environment():
|
"""Return True, if host should be bypassed.
|
||||||
return proxy_bypass_environment(host)
|
|
||||||
|
Checks proxy settings gathered from the environment, if specified,
|
||||||
|
or from the MacOSX framework SystemConfiguration.
|
||||||
|
|
||||||
|
"""
|
||||||
|
proxies = getproxies_environment()
|
||||||
|
if proxies:
|
||||||
|
return proxy_bypass_environment(host, proxies)
|
||||||
else:
|
else:
|
||||||
return proxy_bypass_macosx_sysconf(host)
|
return proxy_bypass_macosx_sysconf(host)
|
||||||
|
|
||||||
|
@ -2677,14 +2700,15 @@ elif os.name == 'nt':
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
def proxy_bypass(host):
|
def proxy_bypass(host):
|
||||||
"""Return a dictionary of scheme -> proxy server URL mappings.
|
"""Return True, if host should be bypassed.
|
||||||
|
|
||||||
Returns settings gathered from the environment, if specified,
|
Checks proxy settings gathered from the environment, if specified,
|
||||||
or the registry.
|
or the registry.
|
||||||
|
|
||||||
"""
|
"""
|
||||||
if getproxies_environment():
|
proxies = getproxies_environment()
|
||||||
return proxy_bypass_environment(host)
|
if proxies:
|
||||||
|
return proxy_bypass_environment(host, proxies)
|
||||||
else:
|
else:
|
||||||
return proxy_bypass_registry(host)
|
return proxy_bypass_registry(host)
|
||||||
|
|
||||||
|
|
|
@ -673,6 +673,7 @@ Kjetil Jacobsen
|
||||||
Bertrand Janin
|
Bertrand Janin
|
||||||
Geert Jansen
|
Geert Jansen
|
||||||
Jack Jansen
|
Jack Jansen
|
||||||
|
Hans-Peter Jansen
|
||||||
Bill Janssen
|
Bill Janssen
|
||||||
Thomas Jarosch
|
Thomas Jarosch
|
||||||
Juhana Jauhiainen
|
Juhana Jauhiainen
|
||||||
|
|
|
@ -256,6 +256,10 @@ Core and Builtins
|
||||||
Library
|
Library
|
||||||
-------
|
-------
|
||||||
|
|
||||||
|
- Issue #26804: urllib.request will prefer lower_case proxy environment
|
||||||
|
variables over UPPER_CASE or Mixed_Case ones. Patch contributed by Hans-Peter
|
||||||
|
Jansen.
|
||||||
|
|
||||||
- Issue #26837: assertSequenceEqual() now correctly outputs non-stringified
|
- Issue #26837: assertSequenceEqual() now correctly outputs non-stringified
|
||||||
differing items (like bytes in the -b mode). This affects assertListEqual()
|
differing items (like bytes in the -b mode). This affects assertListEqual()
|
||||||
and assertTupleEqual().
|
and assertTupleEqual().
|
||||||
|
|
Loading…
Reference in New Issue