Перейти к содержимому
ecdsa.com
git over HTTPS with libcurl + OpenSSL (Git for Windows default, macOS Homebrew, Alpine, RHEL)Git

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

fatal: unable to access 'https://git.example.com/team/app.git/': SSL certificate problem: unable to get local issuer certificate

Также выводится как

  • fatal: unable to access 'https://git.example.com/team/app.git/': SSL certificate OpenSSL verify result: unable to get local issuer certificate (20)

URL в сообщении — адрес вашего удалённого репозитория. В libcurl 8.22 (и, возможно, в других недавних версиях) причина звучит так: «SSL certificate OpenSSL verify result: unable to get local issuer certificate (20)». Сборки git в Debian и Ubuntu используют GnuTLS и вместо этого выводят «server verification failed: certificate signer not trusted».

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

HTTPS-транспорт git использует libcurl, а libcurl с OpenSSL не нашла CA, который выпустил последний сертификат, отправленный Git-сервером. Либо сервер не отправляет промежуточный сертификат, либо цепочка заканчивается корневым сертификатом (CA компании, CA прокси), которого нет в пакете сертификатов, используемом git. В Windows это классический симптом того, что Git for Windows проверяет сертификаты по собственному встроенному файлу CA, а не по хранилищу сертификатов Windows.

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

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

  1. 1.

    Windows: переключите git на хранилище сертификатов Windows

    С http.sslBackend schannel Git for Windows проверяет сертификаты средствами самой Windows и принимает все корневые сертификаты, которым доверяет Windows, включая развёрнутые через групповую политику. Для корпоративных сетей это правильное решение.

    bash
    # Git for Windows: verify with the Windows certificate store, where IT deploys company roots
    git config --global http.sslBackend schannel
    git config --global --get http.sslBackend
  2. 2.

    Добавьте доверие к CA только для одного Git-хоста

    Параметр http.<url>.sslCAInfo с привязкой к URL добавляет частный CA только для этого хоста; GIT_SSL_CAINFO действует на одну команду или одно задание.

    bash
    git config --global http."https://git.example.com/".sslCAInfo /etc/ssl/private-ca/corp-root-ca.pem
    # one command or CI job only
    GIT_SSL_CAINFO=/etc/ssl/private-ca/corp-root-ca.pem git clone https://git.example.com/team/app.git
  3. 3.

    Установите корневой сертификат в системный пакет сертификатов

    В Linux libcurl по умолчанию читает именно системный пакет сертификатов, поэтому корневой сертификат, добавленный туда, исправляет git вместе с curl и менеджерами пакетов.

    bash
    # Alpine / Debian / Ubuntu
    cp corp-root-ca.pem /usr/local/share/ca-certificates/corp-root-ca.crt && update-ca-certificates
    # RHEL / Fedora
    cp corp-root-ca.pem /etc/pki/ca-trust/source/anchors/ && update-ca-trust
  4. 4.

    Найдите переопределение, которое заменяет пакет сертификатов

    --show-origin показывает, в каком файле конфигурации задан путь к CA. Удалите глобальные переопределения, которые следовало ограничить одним хостом.

    bash
    git config --show-origin --get-all http.sslCAInfo
    git config --show-origin --get-regexp 'http\..*\.sslcainfo'
    env | grep -E 'GIT_SSL_CAINFO|CURL_CA_BUNDLE|SSL_CERT_FILE'
  5. 5.

    Временная диагностика: отключите проверку для одной команды

    Используйте -c http.sslVerify=false только для подтверждения диагноза и никогда не прописывайте его в глобальной конфигурации: так раскрываются учётные данные, а любой на пути трафика может изменить получаемый вами код.

    bash
    # Diagnostic only, for one command
    git -c http.sslVerify=false ls-remote https://git.example.com/team/app.git

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

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