Почему cURL не может правильно проверить сертификат в Windows?

30

Когда я пытаюсь использовать Curl в Windows, чтобы получить httpsURL-адрес, я получаю страшную «ошибку соединения (60)».

введите описание изображения здесь

Точное сообщение об ошибке:

curl: (60) Проблема с сертификатом SSL, убедитесь, что сертификат CA в порядке. Подробности:
ошибка: 14090086: подпрограммы SSL: SSL3_GET_SERVER_CERTIFICATE: сбой проверки сертификата.
Подробнее здесь: http://curl.haxx.se/docs/sslcerts.html

Как решить это?

Cheeso
источник
SU не нравится слово «проблема» в названии, потому что оно не носит описательный характер. Если вы не можете придумать способ перефразировать ваш заголовок без слова «проблема», значит, вы недостаточно стараетесь. :)
Гарретт
1
это точная цитата из сообщения, о котором я спрашиваю. Я не хочу пытаться удалить это слово, оно очень важно для индексации поиска.
Cheeso
@Cheeso: Содержание публикации также индексируется, кто-то ищет ваш вопрос, увидит его в описании под заголовком.
Тамара Вийсман

Ответы:

36

Я не знаю почему, но я не нашел эту информацию в одном месте.

  1. Загрузите версию Curl с поддержкой SSL или создайте версию с поддержкой SSL самостоятельно.

  2. Из http://curl.haxx.se/docs/caextract.html , Скачать файл cacert.pem.

  3. Поместите curl.exe и файл .pem в один каталог.

  4. Переименуйте cacert.pemфайл вcurl-ca-bundle.crt

  5. Перезапустите curl.exe!


РЕДАКТИРОВАТЬ:

Есть и другие способы решения проблемы. этот конкретный способ опирается на cacert, созданный создателем Curl. Это может быть не то, что вам нужно, и, в частности, это может не сработать в тех случаях, когда у вас есть менее известный центр сертификации (например, центр, известный только вашей корпорации) для сертификата, используемого сайтом SSL , В этом случае вы захотите создать свой собственный curl-ca-bundle.crtфайл. Вы можете использовать certreq.exe и openssl.exe для экспорта такого сертификата из хранилища IE / Windows, а затем преобразовать в формат pem, соответственно.

Cheeso
источник
1
Спасибо!!! Недавно я попытался взломать HTTPS и потратил немало времени, пытаясь понять, как заставить его работать. Как и вы, мне тоже пришлось проверять различные источники информации, но, к сожалению, я не нашел части о необходимости загрузки файла сертификата с сайта cURL (я видел много материала о загрузке сертификата с целевого сайта, но не это).
Synetech
Рад, что это помогло.
Cheeso
Какой смысл переименовывать его в curl-ca-bundle.crt? Это конкретные окна?
Nawfal
Благодарность! Я использовал curlотмеченный WinSSLв Windows 7. Согласно ссылке на документацию, отмеченные версии должны работать только с использованием системных сертификатов. Однако я получал ошибку, пока не последовал вашему решению.
Джордж,
Однако, если конечный пользователь не имеет прав администратора, он не сможет поместить новый сертификат в папки, принадлежащие системе. В качестве альтернативы пользователь может использовать переменную окружения set CURL_CA_BUNDLE=<path to crt>. Убедитесь, что формат файла правильный. Этот метод будет работать, даже если у вас есть несколько curlустановок, например, git, vagrant ...
Aaron C
6

Я создал сценарий PowerShell, который способен записывать ca-cert.crtфайл на основе сертификатов CA, установленных в вашем хранилище сертификатов Windows (CurrentUser или LocalMachine). Запустите скрипт так:

CreateCaCert.ps1 -StoreLocation CurrentUser | Out-File -Encoding utf8 curl-ca-cert.crt

Это создаст curl-ca-cert.crtфайл, который должен храниться в том же каталоге, что curl.exeи вы сможете проверять те же сайты, что и в своих приложениях Windows (обратите внимание, что этот файл также может использоваться git).

«Официальный» скрипт можно найти на GitHub , но его начальная версия приведена здесь для справки:

[CmdletBinding()]
Param(
    [ValidateSet(
        [System.Security.Cryptography.X509Certificates.StoreLocation]::CurrentUser,
        [System.Security.Cryptography.X509Certificates.StoreLocation]::LocalMachine)]
    [string]
    $StoreLocation = [System.Security.Cryptography.X509Certificates.StoreLocation]::CurrentUser
)

$maxLineLength = 77

# Open the store
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store ([System.Security.Cryptography.X509Certificates.StoreName]::AuthRoot, $StoreLocation)
$store.Open([System.Security.Cryptography.X509Certificates.OpenFlags]::ReadOnly);

# Write header
Write-Output "# Root certificates ($StoreLocation) generated at $(Get-Date)"

# Write all certificates
Foreach ($certificate in $store.Certificates)
{
    # Start with an empty line
    Write-Output ""

    # Convert the certificate to a BASE64 encoded string
    $certString = [Convert]::ToBase64String($certificate.Export([System.Security.Cryptography.X509Certificates.X509ContentType]::Cert));

    # Write the actual certificate
    Write-Output "# Friendly name: $($certificate.FriendlyName)"
    Write-Output "# Issuer:        $($certificate.Issuer)"
    Write-Output "# Expiration:    $($certificate.GetExpirationDateString())"
    Write-Output "# Serial:        $($certificate.SerialNumber)"
    Write-Output "# Thumbprint:    $($certificate.Thumbprint)"
    Write-Output "-----BEGIN CERTIFICATE-----"
    For ($i = 0; $i -lt $certString.Length; $i += $maxLineLength)
    {
        Write-Output $certString.Substring($i, [Math]::Min($maxLineLength, $certString.Length - $i))
    }
    Write-Output "-----END CERTIFICATE-----"
}
Рамон де Кляйн
источник
2

На самом деле у нас была та же проблема с Typheous / Ruby. Решение загружало файл cacert.pem и сохранял его в C: \ Windows \ System32 (или там, где у вас Windows). После этого мы устанавливаем глобальную переменную среды, подобную описанной здесь, где должно быть «Имя переменной» CURL_CA_BUNDLEи «Значение переменной» путь к файлу %SystemRoot%\System32\cacert.pem.

При запуске нового сеанса CMD вы теперь можете просто использовать функцию Typheous / Libcurl для аутентификации соединений SSL. Я успешно попробовал это с Windows 8.1.

Мартин
источник