Je suis sur Ubuntu 12.10 avec OpenSSL 1.0.1c, python 2.7.3, Requests 1.0.3 et 1.0.4 (essayé les deux), et lors de la tentative de connexion au site Web dans la variable URL avec le code suivant .
def SendInitialRequest(xmlmessage, redirecturl):
url = 'https://centineltest.cardinalcommerce.com/maps/txns.asp'
payload = 'cmpi_msg=' + ET.tostring(xmlmessage)
headers = {
'Content-Type': 'application/x-www-form-urlencoded',
}
r = requests.post(url, data=payload, headers=headers, verify=None)
print r.text
Il lève l'erreur suivante:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "clams/libs/centinel/thinclient.py", line 134, in SendInitialRequest
r = requests.post(url, data=payload, headers=headers, verify=None)
File "/home/jasonamyers/.virtualenv/clams/lib/python2.7/site-packages/requests/api.py", line 87, in post
return request('post', url, data=data, **kwargs)
File "/home/jasonamyers/.virtualenv/clams/lib/python2.7/site-packages/requests/api.py", line 44, in request
return session.request(method=method, url=url, **kwargs)
File "/home/jasonamyers/.virtualenv/clams/lib/python2.7/site-packages/requests/sessions.py", line 269, in request
resp = self.send(prep, stream=stream, timeout=timeout, verify=verify, cert=cert, proxies=proxies)
File "/home/jasonamyers/.virtualenv/clams/lib/python2.7/site-packages/requests/sessions.py", line 364, in send
r = adapter.send(request, **kwargs)
File "/home/jasonamyers/.virtualenv/clams/lib/python2.7/site-packages/requests/adapters.py", line 163, in send
raise SSLError(e)
requests.exceptions.SSLError: [Errno 8] _ssl.c:504: EOF occurred in violation of protocol
La tentative de connexion avec openssl renvoie les éléments suivants:
$ openssl s_client -connect centineltest.cardinalcommerce.com:443
CONNECTED(00000003)
140019346777760:error:140790E5:SSL routines:SSL23_WRITE:ssl handshake failure:s23_lib.c:177:
---
no peer certificate available
---
No client certificate CA names sent
---
SSL handshake has read 0 bytes and written 226 bytes
---
New, (NONE), Cipher is (NONE)
Secure Renegotiation IS NOT supported
Compression: NONE
Expansion: NONE
---
Si je le force à utiliser tls1 cela fonctionne (sortie tronquée):
$ openssl s_client -tls1 -connect centineltest.cardinalcommerce.com:443
CONNECTED(00000003)
depth=2 C = US, O = "thawte, Inc.", OU = Certification Services Division, OU
verify error:num=20:unable to get local issuer certificate
verify return:0
---
J'ai vu de nombreux rapports de bugs pour cela; Cependant, je n'ai pas trouvé le moyen de le contourner à l'aide de la bibliothèque de requêtes Python. Toute assistance sera grandement appréciée.
Republiez ceci ici pour les autres depuis la page des demandes :
Requests 'ne prend pas en charge cette opération avant la version 1. Après la version 1, vous devez sous-classer HTTPAdapter, comme suit:
from requests.adapters import HTTPAdapter
from requests.packages.urllib3.poolmanager import PoolManager
import ssl
class MyAdapter(HTTPAdapter):
def init_poolmanager(self, connections, maxsize, block=False):
self.poolmanager = PoolManager(num_pools=connections,
maxsize=maxsize,
block=block,
ssl_version=ssl.PROTOCOL_TLSv1)
Lorsque vous avez fait cela, vous pouvez faire ceci:
import requests
s = requests.Session()
s.mount('https://', MyAdapter())
Toute demande via cet objet de session utilisera alors TLSv1.
La définition de verify = False ignore uniquement la vérification du certificat de serveur, mais ne permet pas de résoudre les erreurs de protocole SSL.
Ce problème est probablement dû à la désactivation de SSLv2 sur le serveur Web, mais Python 2.x tente d'établir une connexion avec PROTOCOL_SSLv23 par défaut. Cela se produit sur https://github.com/python/cpython/blob/360aa60b2a36f5f6e9e20325efd8d472f7559b1e/Lib/ssl.py#L1057
Vous pouvez corriger ssl.wrap_socket () dans le module ssl en remplaçant le paramètre mot-clé ssl_version. Le code suivant peut être utilisé tel quel. Mettez ceci au début de votre programme avant de faire des demandes.
import ssl
from functools import wraps
def sslwrap(func):
@wraps(func)
def bar(*args, **kw):
kw['ssl_version'] = ssl.PROTOCOL_TLSv1
return func(*args, **kw)
return bar
ssl.wrap_socket = sslwrap(ssl.wrap_socket)
L'installation des extras de paquets "sécurité" pour requests
résolus pour moi:
Sudo apt-get installez libffi-dev
Sudo pip install -U demandes [sécurité]
C'est un bug connu, vous pouvez le contourner avec un hack:
Ouvrez site-packages/requests/packages/urllib3/connectionpool.py
(ou faites simplement une copie locale des demandes dans votre propre projet) et modifiez le bloc qui dit:
def connect(self):
# Add certificate verification
sock = socket.create_connection((self.Host, self.port), self.timeout)
# Wrap socket using verification with the root certs in
# trusted_root_certs
self.sock = ssl_wrap_socket(sock, self.key_file, self.cert_file,
cert_reqs=self.cert_reqs,
ca_certs=self.ca_certs,
server_hostname=self.Host,
ssl_version=self.ssl_version)
à:
def connect(self):
# Add certificate verification
sock = socket.create_connection((self.Host, self.port), self.timeout)
# Wrap socket using verification with the root certs in
# trusted_root_certs
self.sock = ssl_wrap_socket(sock, self.key_file, self.cert_file,
cert_reqs=self.cert_reqs,
ca_certs=self.ca_certs,
server_hostname=self.Host,
ssl_version=ssl.PROTOCOL_TLSv1)
Sinon, je suppose qu’il existe une dérogation moins efficace, mais je n’en trouve pas une en quelques regards.
NOTE: Sur une note, requests
à partir de PIP (1.0.4) sur un MacOS fonctionne uniquement avec l'URL fournie.
Pour les personnes qui ne peuvent pas obtenir les correctifs ci-dessus fonctionnent.
Il a fallu changer le fichier ssl.py pour le réparer . Recherchez la fonction create_default_context et changez la ligne:
context = SSLContext(PROTOCOL_SSLv23)
à
context = SSLContext(PROTOCOL_TLSv1)
Peut-être que quelqu'un peut créer une solution plus facile sans modifier ssl.py?
J'ai rencontré cette erreur et le correctif semble désactiver SNI, ce que Python 2.7 ne supporte pas:
J'ai eu le même problème:
soulève SSLError (e)
requests.exceptions.SSLError: [Errno 8] _ssl.c: 504: EOF s'est produit en violation du protocole.
J'avais un violon en cours d'exécution, j'ai arrêté la capture du violoneux et je n'ai pas vu cette erreur. Peut-être à cause de violoneux.
J'ai eu cette erreur lors de la connexion à un serveur RabbitMQ MQTT via TLS. Je suis presque sûr que le serveur est en panne, mais de toute façon cela a fonctionné avec OpenSSL 1.0.1, mais pas OpenSSL 1.0.2.
Vous pouvez vérifier votre version en Python en utilisant ceci:
import ssl
ssl.OPENSSL_VERSION
Je ne suis pas sûr de savoir comment rétrograder OpenSSL dans Python (il semble être lié statiquement au moins sous Windows), à l'exception d'une version plus ancienne de Python.
Malheureusement, la réponse acceptée n'a pas fonctionné pour moi. Comme solution temporaire, vous pouvez également utiliser verify=False
lors de la connexion au site Web sécurisé.
De Requêtes Python émettant SSLError
requests.get('https://example.com', verify=True)
J'avais un problème similaire et je pense que si nous ignorons simplement la vérification ssl
fonctionnera comme un charme, comme cela a fonctionné pour moi. Donc, vous connecter au serveur avec https
, mais en leur demandant de ne pas vérifier le certificat.
Utilisation de requests
. Il suffit de mentionner verify=False
au lieu de None
requests.post(url, data=payload, headers=headers, verify=False)
En espérant que cela fonctionnera pour ceux qui en ont besoin :).