Я пытаюсь отправить HTTP-запросы на сервер (доступный только из указанной c сети, поэтому все имена составлены) через запросы lib, но я получаю ошибку SSL.
Мой код:
site_auth = HTTPBasicAuth("user", "password")
response = requests.get("https://my.hidden.site.com", auth=site_auth , verify="location/src/mycertfile.pem")
Я тоже пробовал это:
site_auth = HTTPBasicAuth("user", "password")
response = requests.get("https://my.hidden.site.com", auth=site_auth , verify=True, cert="location/src/mycertfile.pem")
Но результат был тот же stacktrace.
Stacktrace:
Traceback (most recent call last):
File "location\.venv\lib\site-packages\urllib3\connectionpool.py", line 670, in urlopen
httplib_response = self._make_request(
File "location\.venv\lib\site-packages\urllib3\connectionpool.py", line 381, in _make_request
self._validate_conn(conn)
File "location\.venv\lib\site-packages\urllib3\connectionpool.py", line 976, in _validate_conn
conn.connect()
File "location\.venv\lib\site-packages\urllib3\connection.py", line 361, in connect
self.sock = ssl_wrap_socket(
File "location\.venv\lib\site-packages\urllib3\util\ssl_.py", line 377, in ssl_wrap_socket
return context.wrap_socket(sock, server_hostname=server_hostname)
File "C:\Users\Adam\AppData\Local\Programs\Python\Python38-32\lib\ssl.py", line 500, in wrap_socket
return self.sslsocket_class._create(
File "C:\Users\Adam\AppData\Local\Programs\Python\Python38-32\lib\ssl.py", line 1040, in _create
self.do_handshake()
File "C:\Users\Adam\AppData\Local\Programs\Python\Python38-32\lib\ssl.py", line 1309, in do_handshake
self._sslobj.do_handshake()
ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1108)
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "location\.venv\lib\site-packages\requests\adapters.py", line 439, in send
resp = conn.urlopen(
File "location\.venv\lib\site-packages\urllib3\connectionpool.py", line 724, in urlopen
retries = retries.increment(
File "location\.venv\lib\site-packages\urllib3\util\retry.py", line 439, in increment
raise MaxRetryError(_pool, url, error or ResponseError(cause))
urllib3.exceptions.MaxRetryError: HTTPSConnectionPool(host='my.hidden.site.com', port=443): Max retries exceeded with url: / (Caused by SSLError(SSLCertVerificationError(1, '[SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1108)')))
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "location/main_playground.py", line 15, in <module>
response = requests.get("https://my.hidden.site.com", auth=rt_auth, verify="location/mycertfile.pem")
File "location\.venv\lib\site-packages\requests\api.py", line 76, in get
return request('get', url, params=params, **kwargs)
File "location\.venv\lib\site-packages\requests\api.py", line 61, in request
return session.request(method=method, url=url, **kwargs)
File "location\.venv\lib\site-packages\requests\sessions.py", line 530, in request
resp = self.send(prep, **send_kwargs)
File "location\.venv\lib\site-packages\requests\sessions.py", line 643, in send
r = adapter.send(request, **kwargs)
File "location\.venv\lib\site-packages\requests\adapters.py", line 514, in send
raise SSLError(e, request=request)
requests.exceptions.SSLError: HTTPSConnectionPool(host='my.hidden.site.com', port=443): Max retries exceeded with url: / (Caused by SSLError(SSLCertVerificationError(1, '[SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1108)')))
Я использую следующие версии библиотек:
requests==2.23.0
urllib3==1.25.9
Я много гуглил, но у меня ничего не работает. Я вручную загрузил цепочку сертификации и создал свой файл .pem, который я проверил с помощью openssl verify. У меня есть 3 сертификата, и я заказал их из root на мой целевой сайт сверху вниз следующим образом:
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
Странно то, что urrlib3 отлично работает даже без файла .pem и явно включенные сертификаты, код:
http = urllib3.PoolManager(cert_reqs='CERT_REQUIRED')
r = http.request('GET', "https://my.hidden.site.com", fields={'user': "user", 'pass': "password"})
print(r)
print(r.data.decode('utf-8'))
Еще одна странность заключается в том, что curl не работает по умолчанию, но работает так, как должен, когда я предоставляю файл .pem, поэтому запросы тоже должны, верно?
curl https://my.hidden.site.com --cacert mycertfile.pem
Я пробовал также Postman, но он не работает даже с выбранным файлом .pem в настройках.
Could not get any response
There was an error connecting to https://my.hidden.site.com.
Я также пробовал установить root и промежуточные сертификаты на моем компьютере (Windows 10), но это не действует. Кто-нибудь знает, что может быть не так или что мне следует проверить дальше?
Спасибо за любую помощь
// РЕДАКТИРОВАТЬ 1
Я создал цепочку сертификатов, используя эту команду и извлекая из нее 3 ключа. Я изменил порядок в файле .pem, как я уже упоминал, поэтому ключ CA root будет первым в файле .pem, а также промежуточным является вторым, а ключ для my.hidden.site.com - третий.
Я вижу, что есть строки невозможно получить сертификат местного эмитента и проверить ошибку: num = 21: невозможно проверить первый сертификат , но я не знаю, проблема это или нет, а может, чего-то не хватает.
$ openssl s_client -showcerts -connect my.hidden.site.com:443
CONNECTED(0000017C)
---
Certificate chain
0 s:SECRET LINE my.hidden.site.com
i:SECRET LINE intermediate
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
1 s:SECRET LINE intermediate
i:SECRET LINE root ca
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
2 s:SECRET LINE root ca
i:SECRET LINE root ca
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
---
Server certificate
subject=SECRET LINE my.hidden.site.com
issuer=SECRET LINE intermediate
---
No client certificate CA names sent
Peer signing digest: SHA256
Peer signature type: RSA
Server Temp Key: ECDH, P-256, 256 bits
---
SSL handshake has read 4618 bytes and written 444 bytes
Verification error: unable to verify the first certificate
---
New, TLSv1.2, Cipher is ECDHE-RSA-AES256-GCM-SHA384
Server public key is 2048 bit
Secure Renegotiation IS supported
Compression: NONE
Expansion: NONE
No ALPN negotiated
SSL-Session:
Protocol : TLSv1.2
Cipher : ECDHE-RSA-AES256-GCM-SHA384
Session-ID: <HIDDEN_SESSION_ID>
Session-ID-ctx:
Master-Key: <HIDDEN_MASTER_KEY>
PSK identity: None
PSK identity hint: None
SRP username: None
TLS session ticket lifetime hint: 300 (seconds)
TLS session ticket:
<HIDDEN_SESSION_TICKET>
Start Time: 1588693969
Timeout : 7200 (sec)
Verify return code: 21 (unable to verify the first certificate)
Extended master secret: no
---
closed
depth=0 HIDDEN DETAILS, CN = my.hidden.site.com
verify error:num=20:unable to get local issuer certificate
verify return:1
depth=0 HIDDEN DETAILS CN = my.hidden.site.com
verify error:num=21:unable to verify the first certificate
verify return:1