Python Requests SSL Error: EOF occurred in violation of protocol

Updated: January 2, 2024 By: Guest Contributor Post a comment

Understanding the SSL Error in Python Requests

The requests.exceptions.SSLError: EOF occurred in violation of protocol error occurs when the Python Requests library encounters an issue with the SSL/TLS protocol during an HTTPS connection. This can be caused by several factors including outdated libraries, issues with the server’s SSL certificate, or incompatible SSL protocol versions between the client and server. Here are various solutions to address the error:

Solutions

Solution 1: Update Packages

Outdated packages can cause incompatibility issues with SSL protocols.

  • Step 1: Update the requests library using pip: pip install requests --upgrade.
  • Step 2: Ensure that other related packages like PyOpenSSL, cryptography, and ndg-httpsclient are up to date: pip install PyOpenSSL cryptography ndg-httpsclient --upgrade.

Advantages: Simple and can remedy compatibility issues. Limitations: Might not solve server-side problems.

Solution 2: Disable SSL Verification

Disabling SSL verification bypasses SSL certificate checks. Only use this for debugging or with trusted endpoints.

Directly set verify=False in the requests call:

import requests
response = requests.get('https://example.com', verify=False)
print(response.text)

Advantages: Quick fix for testing. Limitations: Security risk, should not be used in production.

Solution 3: Specify Cipher Suite

If the error is due to the client and server not agreeing on a cipher suite, you can specify a cipher suite supported by the server.

  • Use openssl to check supported cipher suites: openssl s_client -connect example.com:443.
  • Configure the Requests session to use the desired cipher suite.

Code example:

import requests
from requests.adapters import HTTPAdapter
from requests.packages.urllib3.poolmanager import PoolManager
import ssl

class SSLAdapter(HTTPAdapter):
    def init_poolmanager(self, connections, maxsize, block=False):
        self.poolmanager = PoolManager(
            num_pools=connections,
            maxsize=maxsize,
            block=block,
            ssl_version=ssl.PROTOCOL_TLS,
            ciphers='ECDHE-RSA-AES128-GCM-SHA256'
        )
session = requests.Session()
session.mount('https://', SSLAdapter())
response = session.get('https://example.com')
print(response.text)

Advantages: Can resolve cipher-specific issues. Limitations: Needs knowledge of the server’s supported cipher suites.

Solution 4: Change the SSL Protocol

Specifying an alternate SSL protocol version can resolve compatibility issues.

Modify the Requests session to use an alternative SSL protocol such as TLS 1.2 or 1.3 (or a higher one) as follows:

import requests
from requests.packages.urllib3.util.ssl_ import create_urllib3_context

# In this context, we force the use of TLS 1.2
ssl_context = create_urllib3_context(ssl_version=ssl.PROTOCOL_TLSv1_2)

response = requests.get('https://example.com', ssl_context=ssl_context)
print(response.text)

Advantages: Resolves protocol version mismatches. Limitations: Server must support the selected protocol; Experimentation to determine compatible protocol.