Does urllib3 support IPv6?

Yes, urllib3 fully supports IPv6 connectivity. As a modern Python HTTP client library, urllib3 leverages Python's built-in http.client module, which provides native IPv6 support for both HTTP and HTTPS connections.

Basic IPv6 Usage

Using Literal IPv6 Addresses

When connecting to a specific IPv6 address, wrap it in square brackets to distinguish it from port numbers:

import urllib3

# Create a PoolManager instance
http = urllib3.PoolManager()

# IPv6 address wrapped in square brackets
url = 'http://[2001:db8::1]/'

try:
    response = http.request('GET', url)
    print(f"Status: {response.status}")
    print(f"Content: {response.data.decode('utf-8')[:100]}...")
except urllib3.exceptions.ConnectTimeoutError:
    print("Connection timed out - IPv6 may not be available")
except Exception as e:
    print(f"Error: {e}")

IPv6 with Custom Ports

Specify ports after the closing bracket:

import urllib3

http = urllib3.PoolManager()

# IPv6 address with custom port
url = 'http://[2001:db8::1]:8080/api/data'

response = http.request('GET', url)
print(f"Response: {response.status}")

HTTPS over IPv6

IPv6 works seamlessly with HTTPS connections:

import urllib3

# Disable SSL warnings for demo (not recommended in production)
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)

http = urllib3.PoolManager()

# HTTPS with IPv6
url = 'https://[2606:2800:220:1:248:1893:25c8:1946]/'

try:
    response = http.request('GET', url, timeout=10)
    print(f"HTTPS IPv6 Status: {response.status}")
except Exception as e:
    print(f"HTTPS IPv6 Error: {e}")

Hostname Resolution

When using hostnames, DNS resolution automatically handles IPv4/IPv6 selection:

import urllib3
import socket

http = urllib3.PoolManager()

# Test IPv6-enabled hostname
hostname = 'ipv6.google.com'

# Check what IP addresses the hostname resolves to
try:
    addr_info = socket.getaddrinfo(hostname, 80, socket.AF_UNSPEC)
    print("Available addresses:")
    for info in addr_info:
        print(f"  {info[4][0]} ({info[0].name})")
except socket.gaierror as e:
    print(f"DNS resolution failed: {e}")

# Make request (urllib3 will choose appropriate IP version)
try:
    response = http.request('GET', f'https://{hostname}/')
    print(f"Response status: {response.status}")
except Exception as e:
    print(f"Request failed: {e}")

Forcing IPv6 Connections

To ensure only IPv6 connections are used, you can customize the socket creation:

import urllib3
import socket
from urllib3.util.connection import create_connection

def create_ipv6_connection(address, timeout=None, source_address=None, socket_options=None):
    """Force IPv6 connection"""
    host, port = address

    # Resolve to IPv6 addresses only
    addr_info = socket.getaddrinfo(host, port, socket.AF_INET6, socket.SOCK_STREAM)
    if not addr_info:
        raise socket.error("No IPv6 addresses found")

    # Use the first IPv6 address
    family, type_, proto, canonname, sockaddr = addr_info[0]
    sock = socket.socket(family, type_, proto)

    if timeout is not None:
        sock.settimeout(timeout)

    sock.connect(sockaddr)
    return sock

# Monkey patch urllib3 to use IPv6-only connections
urllib3.util.connection.create_connection = create_ipv6_connection

http = urllib3.PoolManager()
response = http.request('GET', 'https://ipv6.google.com/')
print(f"IPv6-only connection status: {response.status}")

Testing IPv6 Connectivity

Check if your system supports IPv6:

import urllib3
import socket

def test_ipv6_support():
    """Test if IPv6 is available on the system"""
    try:
        # Try to create an IPv6 socket
        sock = socket.socket(socket.AF_INET6, socket.SOCK_STREAM)
        sock.close()
        print("✓ IPv6 socket creation successful")

        # Test IPv6 connectivity
        http = urllib3.PoolManager()
        response = http.request('GET', 'https://ipv6.google.com/', timeout=5)
        print(f"✓ IPv6 connectivity test: {response.status}")

        return True
    except Exception as e:
        print(f"✗ IPv6 not available: {e}")
        return False

# Run the test
if test_ipv6_support():
    print("Your system supports IPv6 with urllib3")
else:
    print("IPv6 support is limited or unavailable")

Common Issues and Troubleshooting

Network Configuration Issues

import urllib3
from urllib3.exceptions import ConnectTimeoutError, NewConnectionError

http = urllib3.PoolManager()

def test_ipv6_connection(url):
    """Test IPv6 connection with proper error handling"""
    try:
        response = http.request('GET', url, timeout=10)
        return f"Success: {response.status}"
    except ConnectTimeoutError:
        return "Error: Connection timeout - check IPv6 connectivity"
    except NewConnectionError as e:
        if "Name or service not known" in str(e):
            return "Error: DNS resolution failed"
        elif "Network is unreachable" in str(e):
            return "Error: IPv6 network unreachable - check network config"
        return f"Error: Connection failed - {e}"
    except Exception as e:
        return f"Error: {e}"

# Test various IPv6 endpoints
test_urls = [
    'https://[2606:2800:220:1:248:1893:25c8:1946]/',  # Example.com IPv6
    'https://ipv6.google.com/',
    'https://test-ipv6.com/'
]

for url in test_urls:
    result = test_ipv6_connection(url)
    print(f"{url}: {result}")

Best Practices

  1. Always handle exceptions when working with IPv6, as not all networks support it
  2. Use brackets around literal IPv6 addresses in URLs
  3. Test connectivity before deploying IPv6-dependent applications
  4. Provide fallback to IPv4 when IPv6 is unavailable
  5. Consider dual-stack implementations for maximum compatibility

Requirements

  • Python 3.x with urllib3 installed
  • IPv6-enabled network stack
  • Proper network configuration with IPv6 connectivity
  • DNS servers that support AAAA records for hostname resolution

urllib3 handles IPv6 transparently, making it easy to build applications that work with both IPv4 and IPv6 addresses without additional complexity.

Related Questions

Get Started Now

WebScraping.AI provides rotating proxies, Chromium rendering and built-in HTML parser for web scraping
Icon