define("print_headers", type=bool, default=False)
define("print_body", type=bool, default=True)
define("follow_redirects", type=bool, default=True)
+ define("validate_cert", type=bool, default=True)
args = parse_command_line()
client = HTTPClient()
for arg in args:
try:
response = client.fetch(arg,
- follow_redirects=options.follow_redirects
+ follow_redirects=options.follow_redirects,
+ validate_cert=options.validate_cert,
)
except HTTPError, e:
if e.response is not None:
def post(self):
self.finish("Got %d bytes in POST" % len(self.request.body))
-class SSLTest(AsyncHTTPTestCase, LogTrapTestCase):
+class BaseSSLTest(AsyncHTTPTestCase, LogTrapTestCase):
+ def get_ssl_version(self):
+ raise NotImplementedError()
+
def setUp(self):
- super(SSLTest, self).setUp()
+ super(BaseSSLTest, self).setUp()
# Replace the client defined in the parent class.
# Some versions of libcurl have deadlock bugs with ssl,
# so always run these tests with SimpleAsyncHTTPClient.
test_dir = os.path.dirname(__file__)
return dict(ssl_options=dict(
certfile=os.path.join(test_dir, 'test.crt'),
- keyfile=os.path.join(test_dir, 'test.key')))
+ keyfile=os.path.join(test_dir, 'test.key'),
+ ssl_version=self.get_ssl_version()))
def fetch(self, path, **kwargs):
self.http_client.fetch(self.get_url(path).replace('http', 'https'),
**kwargs)
return self.wait()
+class SSLTestMixin(object):
def test_ssl(self):
response = self.fetch('/')
self.assertEqual(response.body, b("Hello world"))
response = self.wait()
self.assertEqual(response.code, 599)
+# Python's SSL implementation differs significantly between versions.
+# For example, SSLv3 and TLSv1 throw an exception if you try to read
+# from the socket before the handshake is complete, but the default
+# of SSLv23 allows it.
+class SSLv23Test(BaseSSLTest, SSLTestMixin):
+ def get_ssl_version(self): return ssl.PROTOCOL_SSLv23
+class SSLv3Test(BaseSSLTest, SSLTestMixin):
+ def get_ssl_version(self): return ssl.PROTOCOL_SSLv3
+class TLSv1Test(BaseSSLTest, SSLTestMixin):
+ def get_ssl_version(self): return ssl.PROTOCOL_TLSv1
+
if ssl is None:
- del SSLTest
+ del BaseSSLTest
+ del SSLv23Test
+ del SSLv3Test
+ del TLSv1Test
+elif getattr(ssl, 'OPENSSL_VERSION_INFO', (0,0)) < (1,0):
+ # In pre-1.0 versions of openssl, SSLv23 clients always send SSLv2
+ # ClientHello messages, which are rejected by SSLv3 and TLSv1
+ # servers. Note that while the OPENSSL_VERSION_INFO was formally
+ # introduced in python3.2, it was present but undocumented in
+ # python 2.7
+ del SSLv3Test
+ del TLSv1Test
class MultipartTestHandler(RequestHandler):
def post(self):