]> git.ipfire.org Git - thirdparty/tornado.git/commitdiff
test: More robust ipv6 detection
authorBen Darnell <ben@bendarnell.com>
Sun, 5 Nov 2017 15:38:03 +0000 (10:38 -0500)
committerBen Darnell <ben@bendarnell.com>
Fri, 5 Jan 2018 14:04:44 +0000 (09:04 -0500)
There are many ways ipv6 can be disabled or broken (and it just
stopped working on travis-ci), so instead of checking flags like
socket.has_ipv6, attempt to actually bind to an ipv6 address.

Closes #2185

tornado/test/simple_httpclient_test.py
tornado/test/util.py

index 451942d2800846c552a875fb15864fb5f1c88388..0e75e530cd8f576502acc7f46eb07115e95d9f82 100644 (file)
@@ -272,16 +272,9 @@ class SimpleHTTPClientTestMixin(object):
 
     @skipIfNoIPv6
     def test_ipv6(self):
-        try:
-            [sock] = bind_sockets(None, '::1', family=socket.AF_INET6)
-            port = sock.getsockname()[1]
-            self.http_server.add_socket(sock)
-        except socket.gaierror as e:
-            if e.args[0] == socket.EAI_ADDRFAMILY:
-                # python supports ipv6, but it's not configured on the network
-                # interface, so skip this test.
-                return
-            raise
+        [sock] = bind_sockets(None, '::1', family=socket.AF_INET6)
+        port = sock.getsockname()[1]
+        self.http_server.add_socket(sock)
         url = '%s://[::1]:%d/hello' % (self.get_protocol(), port)
 
         # ipv6 is currently enabled by default but can be disabled
index 5f534e84ed144d59ff20c7eddba50d033d35679b..7958d92b26a8b35d06ebc312ac8740890830375e 100644 (file)
@@ -35,15 +35,32 @@ skipOnAppEngine = unittest.skipIf('APPENGINE_RUNTIME' in os.environ,
 skipIfNoNetwork = unittest.skipIf('NO_NETWORK' in os.environ,
                                   'network access disabled')
 
-skipIfNoIPv6 = unittest.skipIf(not socket.has_ipv6, 'ipv6 support not present')
-
-
 skipBefore33 = unittest.skipIf(sys.version_info < (3, 3), 'PEP 380 (yield from) not available')
 skipBefore35 = unittest.skipIf(sys.version_info < (3, 5), 'PEP 492 (async/await) not available')
 skipNotCPython = unittest.skipIf(platform.python_implementation() != 'CPython',
                                  'Not CPython implementation')
 
 
+def _detect_ipv6():
+    if not socket.has_ipv6:
+        # socket.has_ipv6 check reports whether ipv6 was present at compile
+        # time. It's usually true even when ipv6 doesn't work for other reasons.
+        return False
+    sock = None
+    try:
+        sock = socket.socket(socket.AF_INET6)
+        sock.bind(('::1', 0))
+    except socket.error:
+        return False
+    finally:
+        if sock is not None:
+            sock.close()
+    return True
+
+
+skipIfNoIPv6 = unittest.skipIf(not _detect_ipv6(), 'ipv6 support not present')
+
+
 def refusing_port():
     """Returns a local port number that will refuse all connections.