I'm trying to get a file via https using requests 2.11.1 with Python 2.7.12 and OpenSSL 1.0.2h (all installed from Anaconda) on MacOS 10.11.6 from behind a proxy. According to SSLLabs, the server supports TLS 1.0, 1.1, and 1.2. Moreover, I can successfully retrieve the file with wget (linked to OpenSSL 1.0.2h) if I explicitly set the secure-protocol to tlsv1 (but not if I set it to unsupported protocols like sslv2). However, if I try to explicitly set the secure protocol used by requests to TLSv1, TLSv1_1, or TLSv1_2, e.g., as follows,
from requests_toolbelt import SSLAdapter
import requests
import ssl
s = requests.Session()
p = ssl.PROTOCOL_TLSv1
s.mount('https://', SSLAdapter(p))
r = s.get("https://anaconda.org/conda-forge/matplotlib/2.0.0b3/download/osx-64/matplotlib-2.0.0b3-np111py27_5.tar.bz2")
I encounter the following exception:
/Users/lebedov/anaconda2/lib/python2.7/site-packages/requests/adapters.pyc in send(self, request, stream, timeout, verify, cert, proxies)
495 except (_SSLError, _HTTPError) as e:
496 if isinstance(e, _SSLError):
--> 497 raise SSLError(e, request=request)
498 elif isinstance(e, ReadTimeoutError):
499 raise ReadTimeout(e, request=request)
SSLError: ("bad handshake: Error([('SSL routines', 'SSL3_GET_RECORD', 'wrong version number')],)",)
(Less surprisingly, explicitly setting the protocol to SSLv2, SSLv3, or SSLv23 also results in handshake exceptions.) Also, I don't observe any exception when attempting to get other sites via https. Any idea why the connection fails with requests even when I force it to use TLSv1?
This issue proved to be due to the proxy rejecting HTTP headers with unrecognized user-agent strings. Explicitly setting the user-agent in the headers to something like Mozilla/4.0 (compatible; MSIE 5.5; Windows 98)
via a hacked version of cntlm solved the problem.