seddouguim
seddouguim

Reputation: 548

Web3.py AsyncWeb3 WebSocket Connection Fails for Infura Sepolia

I’m working on an Ethereum project that connects to the Sepolia network using Infura's WebSocket endpoint (wss://sepolia.infura.io/ws/v3/<PROJECT_ID>). While the connection works fine in Postman, my Python implementation using Web3.py fails with the following error:

ERROR:BlockchainLayer:Error connecting to WebSocket: Could not connect to: wss://sepolia.infura.io/ws/v3/<PROJECT_ID>. Retries exceeded max of 5.

I tried applying ExtraDataToPOAMiddleware as I did with the HTTP connection, since Sepolia uses a Proof-of-Authority (PoA) consensus, but no luck. The same setup works perfectly for the HTTP endpoint, but WebSocket connections keep failing.

Here is the relevant code for the WebSocket connection:

async def connect_websocket(self):
    """
    Connects to the WebSocket endpoint using AsyncWeb3 and manages its context.
    """
    try:
        async with AsyncWeb3(WebSocketProvider(self.websocket_url)) as w3:
            # w3.middleware_onion.inject(ExtraDataToPOAMiddleware, layer=0)
            self.web3_ws = w3  
            if not await self.web3_ws.is_connected():
                raise ConnectionError(f"Failed to connect to WebSocket endpoint: {self.websocket_url}")
            self.logger.info(f"Connected to {self.network_name} network via WebSocket.")
    except ConnectionClosedError as e:
        self.logger.error(f"WebSocket connection closed: {e}")
    except Exception as e:
        self.logger.error(f"Error connecting to WebSocket: {e}")

What I’ve Tried

Any insights or examples of working implementations would be greatly appreciated!

Upvotes: 0

Views: 83

Answers (1)

seddouguim
seddouguim

Reputation: 548

It turned out the issue was an [SSL: CERTIFICATE_VERIFY_FAILED] error, but I didn’t realize it at first because my logger wasn’t set up early enough in the code. The error wasn’t showing up in the logs, so I had no idea what was going wrong. Once I moved the logger initialization to the very start of my __init__ method, the issue became clear.

On macOS, the fix was to install the proper SSL certificates. Here’s what worked for me:

  1. Installed certifi with Homebrew to get a fresh set of certificates:

    brew install certifi
    
  2. Set up the environment variables to point to the certificates:

    export SSL_CERT_FILE=/opt/homebrew/etc/[email protected]/cert.pem
    export SSL_CERT_DIR=/opt/homebrew/etc/[email protected]/
    
  3. Made the changes permanent by adding them to ~/.zshrc:

    echo "export SSL_CERT_FILE=/opt/homebrew/etc/[email protected]/cert.pem" >> ~/.zshrc
    echo "export SSL_CERT_DIR=/opt/homebrew/etc/[email protected]/" >> ~/.zshrc
    source ~/.zshrc
    

After that, everything worked smoothly.

If you’re on Windows or Linux, the solution might be a little different. On Windows, you might need to run the Install Certificates.command file that comes with Python. On Linux, you might need to install certificates with your package manager, like:

sudo apt install ca-certificates

or

sudo yum install ca-certificates

Upvotes: 0

Related Questions