Четене на сертификат на TLS партньор през HTTP прокси в Python
Използвайте поддръжката на тунел в HTTPConnection на Python, преди да обвиете сокета в SSL контекст с проверка.
ssl.get_server_certificate не договаря HTTP прокси. Първо установете тунела, след това извършете TLS с името на хоста на дестинацията и получете сертификата на партньора.
За HTTP прокси без удостоверяване, използвайки хоста и порта на кандидат от списъка с HTTP прокси:
from contextlib import closing
import http.client
import ssl
hostname = "example.com"
context = ssl.create_default_context()
with closing(http.client.HTTPConnection(
"proxy.example.net", 8080, timeout=10
)) as connection:
connection.set_tunnel(hostname, 443)
connection.connect()
with context.wrap_socket(
connection.sock, server_hostname=hostname
) as tls:
certificate_der = tls.getpeercert(binary_form=True)
certificate_pem = ssl.DER_cert_to_PEM_cert(certificate_der)
HTTPConnection обработва заявката CONNECT и отговора към нея. След това SSL контекстът проверява веригата и идентичността на дестинацията, преди сертификатът да бъде върнат. За това ръкостискане не е нужна HTTP GET заявка към дестинацията.
Ако средата използва одобрен частен CA, заредете този CA в контекста, вместо да изключвате проверката. Отхвърлена верига прави показаното ръкостискане неуспешно.
getpeercert връща листовия сертификат на партньора, а не автоматично експортирана пълна верига. При доверено TLS прихващане сертификатът на партньора може да е сертификатът, генериран от посредника за това име на хост. Запазете тази разлика, когато го сравнявате със сертификат, наблюдаван по друг път.