Перейти к содержимому
ecdsa.com
Python ssl module (OpenSSL)Python: пакет cryptography

Сообщение об ошибке

[SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: certificate has expired

Формулировка одинакова в Python с OpenSSL 1.1.1, 3.0 и 3.5; за ней следует место в исходном коде, например «(_ssl.c:1082)». Для сертификата, срок действия которого ещё не начался, выводится «certificate is not yet valid».

Python ssl module (OpenSSL) — ssl.SSLCertVerificationError, X509_V_ERR_CERT_HAS_EXPIRED (10)

Что это означает

OpenSSL нашёл в цепочке сертификат, срок действия которого закончился раньше текущего времени на этой машине. Обычно сертификат сервера не продлили или продлённый сертификат не отдаётся; иногда клиент строит путь через просроченный корневой сертификат из устаревшего пакета сертификатов CA или у клиента неправильно идут часы.

Почему это происходит

Как исправить

  1. 1.

    Посмотрите на сертификат, который отдаёт сервер

    Один раз получите сертификат с отключённой проверкой, только чтобы его прочитать, и посмотрите notAfter (вставьте сертификат в декодер). Не используйте это непроверенное соединение ни для чего другого.

    python
    import socket, ssl
    
    # Read the served certificate without verifying it, to see its dates
    ctx = ssl.create_default_context()
    ctx.check_hostname = False
    ctx.verify_mode = ssl.CERT_NONE
    with socket.create_connection(("api.example.com", 443)) as raw:
        with ctx.wrap_socket(raw, server_hostname="api.example.com") as tls:
            der = tls.getpeercert(binary_form=True)
    print(ssl.DER_cert_to_PEM_cert(der))   # paste into a certificate decoder
  2. 2.

    Обновите certifi или пакет сертификатов ОС

    Если с собственным сертификатом сервера всё в порядке, обновите корневые сертификаты на клиенте: pip install --upgrade certifi для библиотек, которые используют certifi, а для системного пакета сертификатов — пакет ca-certificates.

    bash
    python3 -m pip install --upgrade certifi
    python3 -c "import certifi; print(certifi.__version__, certifi.where())"
  3. 3.

    Исправьте системные часы

    Включите NTP на клиенте (для контейнеров — на хосте).

    bash
    date -u
    sudo timedatectl set-ntp true

Связанные ошибки

Открыть всю базу ошибок подписей