PHP - błąd certyfikatu SSL: nie można uzyskać certyfikatu lokalnego wystawcy

189

Używam PHP w wersji 5.6.3 jako część XAMPP na Windows 7.

Kiedy próbuję użyć Mandrill API, pojawia się następujący błąd:

Nieprzechwycony wyjątek „Mandrill_HttpError” z komunikatem „Niepowodzenie wywołania interfejsu API do wiadomości / szablonu wysyłania: problem z certyfikatem SSL: nie można uzyskać certyfikatu lokalnego wystawcy”

Próbowałem już wszystkiego, co przeczytałem na StackOverflow, w tym dodając następujące informacje do pliku php.ini:

curl.cainfo = "C:\xampp\php\cacert.pem"

I oczywiście pobrany do tej lokalizacji plik cacert.pem z http://curl.haxx.se/docs/caextract.html

ale po tym wszystkim zrestartowałem XAMPP i serwer Apache, ale nadal pojawia się ten sam błąd.

Naprawdę nie wiem, co jeszcze spróbować.

Czy ktoś może doradzić, co jeszcze mogę spróbować?

Dor Dadush
źródło
Zobacz moją odpowiedź: stackoverflow.com/a/29649024/660410
Michal-sk
3
Upewnij się także, że odkomentowałeś tę linię, usuwając początkowe „;”. powinno to być curl.cainfo = "C: \ xampp \ php \ cacert.pem" zamiast; curl.cainfo = "C: \ xampp \ php \ cacert.pem"
Jon Tan
Czy używanie HTTPS przez HTTP również spowoduje ten błąd?
javiniar.leonard

Odpowiedzi:

366

Nareszcie mam to do pracy!

  1. Pobierz pakiet certyfikatów .

  2. Połóż to gdzieś. W moim przypadku był to c:\wamp\katalog (jeśli używasz Wampa 64-bitowego, to jest c:\wamp64\).

  3. Włącz mod_sslw Apache i php_openssl.dllw php.ini(odkomentuj je, usuwając ;na początku). Ale bądź ostrożny, moim problemem było to, że miałem dwa php.inipliki i muszę to zrobić w obu z nich. Jedna to ta, którą otrzymujesz z ikony paska zadań WAMP, a druga, w moim przypadku, toC:\wamp\bin\php\php5.5.12\

  4. Dodaj te wiersze do certyfikatu w obu php.iniplikach:

    curl.cainfo="C:/wamp/cacert.pem"
    openssl.cafile="C:/wamp/cacert.pem"
  5. Uruchom ponownie usługi Wamp.

Mladen Janjetovic
źródło
3
W moim przypadku był to katalog c: \ xamp \ i jego Windows 7, a to rozwiązanie działa idealnie .. bardzo dużo ...
Manu RS
1
Najnowszy pakiet certyfikatów można pobrać z oryginalnej strony curl.haxx.se/docs/caextract.html
Paul
1
W moim przypadku linia miała ;na początku i zajęło mi godziny, zanim zrozumiałem, że to oznacza komentarz. tak dla noobs jak ja, trzeba usunąć ;, a także
abhyudayasrinet
1
@SurajNeupane nie jestem pewien, spędziłem wtedy dużo czasu, aby go zdobyć, używam maszyn wirtualnych, takich jak Homestead i nie muszę sobie z tym poradzić. To był konkretny przypadek
Mladen Janjetovic,
2
To jest kluczBut be careful, my problem was that I had two php.ini files and I need to do this in both of them. One is the one you get from your WAMP taskbar icon, and another one is, in my case, in C:\wamp\bin\php\php5.5.12\
AA
127

Oświadczenie: Ten kod powoduje, że Twój serwer jest niepewny.

Miałem ten sam problem w pliku Mandrill.php po linii nr 65, gdzie napisano $ this-> ch = curl_init ();

Dodaj następujące dwie linie:

curl_setopt($this->ch, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($this->ch, CURLOPT_SSL_VERIFYPEER, 0);

To rozwiązało mój problem i wysłało e-mail za pomocą localhost, ale sugeruję NIE używać go w wersji na żywo na żywo. Na serwerze na żywo kod powinien działać bez tego kodu.

Shehzad Nizamani
źródło
1
jakieś rzeczy, które mogę spróbować sprawić, aby moje środowisko programistyczne działało bez tego obejścia?
Dor Dadush
4
dla mnie tylko z ustawieniem CURLOPT_SSL_VERIFYPEERdo falsepracy.
Francisco Corrales Morales,
29
Chociaż technicznie masz rację, wyłączenie protokołu SSL jest złym pomysłem. Nawet na localhost lepiej poprawnie załadować certyfikaty, jak wspomniano w drugiej odpowiedzi.
kręgosłup
Chociaż technicznie masz rację, wyłączenie protokołu SSL jest złym pomysłem. Nawet jeśli jest to bardzo odporne na pracę w jakikolwiek inny sposób, lepiej stracić pracę, niż robić rzeczy w niewłaściwy sposób. @Spinal
45

Dzięki @Mladen Janjetovic,

Twoja sugestia zadziałała dla mnie w systemie Mac z zainstalowanymi wzmacniaczami.

Skopiowano: http://curl.haxx.se/ca/cacert.pem

Do: /Applications/AMPPS/extra/etc/openssl/certs/cacert.pem

Zaktualizowałem php.initę ścieżkę i zrestartowałem Apache:

[curl]
; A default value for the CURLOPT_CAINFO option. This is required to be an
; absolute path.
curl.cainfo="/Applications/AMPPS/extra/etc/openssl/certs/cacert.pem"
openssl.cafile="/Applications/AMPPS/extra/etc/openssl/certs/cacert.pem"

Zastosowałem to samo ustawienie w instalacji systemu Windows AMPPS i działało w nim również doskonale.

[curl]
; A default value for the CURLOPT_CAINFO option. This is required to be an
; absolute path.
curl.cainfo="C:/Ampps/php/extras/ssl/cacert.pem"
openssl.cafile="C:/Ampps/php/extras/ssl/cacert.pem"

: To samo dla wampa.

[curl]
; A default value for the CURLOPT_CAINFO option. This is required to be an
; absolute path.
curl.cainfo="C:/wamp/bin/php/php5.6.16/extras/ssl/cacert.pem"
openssl.cafile="C:/wamp/bin/php/php5.6.16/extras/ssl/cacert.pem"

Jeśli szukasz sposobu na wygenerowanie nowego certyfikatu SSL przy użyciu SAN dla localhost, kroki w tym poście działały dla mnie Centos 7 / Vagrant / Chrome Browser.

Damodar Bashyal
źródło
18

Podczas przeglądania strony http://curl.haxx.se/docs/caextract.html zauważysz dużymi literami sekcję o nazwie:

Usunięto RSA-1024

Przeczytaj, a następnie pobierz wersję certyfikatów, która zawiera certyfikaty „RSA-1024”. https://github.com/bagder/ca-bundle/blob/e9175fec5d0c4d42de24ed6d84a06d504d5e5a09/ca-bundle.crt

Będą współpracować z Mandrillem.

Wyłączenie SSL to zły pomysł.

Arturo Alvarado
źródło
1
To naprawiło problem z AWS / Guzzle / cURL, z którym walczyłem cały dzień. Dziękuję Ci!
voidstate
@ unikaj stanu Wiem, że to jest stare, ale możesz też ominąć go w guzzle, używając tego ['Verify' => false], aby uzyskać pełny dokument na ssl / curl / guzzle, przejdź tutaj guzzle.readthedocs.org/en/latest/…
John
@John, ale uniemożliwiłoby to weryfikację SSL, co nie jest tym, co chcesz zrobić, więc nie sugeruję tego.
Arturo Alvarado,
1
W systemie Windows musisz zapisać pliki na serwerze (np. Do C: \ curl \ curl-ca-bundle.crt), a następnie dodać następujące informacje do pliku php.ini: [curl] curl.cainfo = " C: /curl/curl-ca-bundle.crt "[openssl] openssl.cafile =" C: /curl/curl-ca-bundle.crt "
voidstate
Właśnie to miałem po tym, jak działało doskonale przez wieki (nawet przetrwałem zmianę serwera), ale mam problem ze zrozumieniem, co się tutaj dzieje. Czy to curl lub openssl został zaktualizowany i zmieniono pakiet ca na pakiet niezgodny z mailchimp?
Sammaye
11

Powyższe kroki, chociaż pomocne, nie działały dla mnie w systemie Windows 8. Nie znam powiązania, ale poniższe kroki zadziałały. Zasadniczo zmiana w pliku cacert.pem. Mam nadzieję, że to komuś pomoże.

  • Pobierz plik cacert.pem stąd: http://curl.haxx.se/docs/caextract.html
  • Zapisz plik w folderze instalacyjnym PHP. (np .: Jeśli używasz xampp - zapisz go w katalogu c: \ katalog_instalacyjny \ xampp \ php \ cacert.pem).
  • Otwórz plik php.ini i dodaj następujące linie:
  • curl.cainfo = ”C: \ katalog_instalacyjny \ xampp \ php \ cacert.pem” openssl.cafile = ”C: \ katalog_instalacyjny \ xampp \ php \ cacert.pem”
  • Uruchom ponownie serwer Apache, co powinno go naprawić (po prostu zatrzymaj i uruchom usługi w razie potrzeby).
HopeKing
źródło
11

Znalazłem nowe rozwiązanie bez wymaganej certyfikacji, aby zawijać curl tylko dodać kod dwóch linii.

curl_setopt($ch, CURLOPT_FOLLOWLOCATION, TRUE);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
Manish Sharma
źródło
9
Chociaż może to działać, nie jest to wcale zalecane. Mówisz w zasadzie, zaufaj wszystkim certyfikatom ... a także otworzy twoją aplikację na ewentualny atak, jeśli zapomnisz, a twój kod przejdzie do produkcji dzięki tej zmianie ... naprawdę nie jest dużo pracy, aby pobrać pakiet CA i dodaj do niego punkt PHP.
user919426,
to jest koncepcja curl, więc za każdym razem, gdy używasz curl, dodaj powyższy kod
Manish sharma
8

Jeśli nie masz dostępu do php.ini , dodanie tego kodu (po $ch = curl_init();linii) działa dla mnie:

$certificate_location = "C:\Program Files (x86)\EasyPHP-Devserver-16.1\ca-bundle.crt"; // modify this line accordingly (may need to be absolute)
curl_setopt($ch, CURLOPT_CAINFO, $certificate_location);
curl_setopt($ch, CURLOPT_CAPATH, $certificate_location);

Następnie wystarczy pobrać plik ca-bundle.crt i zapisać go w lokalizacji określonej w $certificate_location.

zakaz geoinżynierii
źródło
3

Mam bardzo proste rozwiązanie tego problemu. Możesz to zrobić bez pliku certyfikatu.

Idź na Laravel Root Folder -> Vender -> guzzlehttp -> guzzle -> src

otwórz Client.php

znajdź $ defaults Array. tak to wygląda…

$defaults = [
    'allow_redirects' => RedirectMiddleware::$defaultSettings,
    'http_errors'     => true,
    'decode_content'  => true,
    'verify'          => true,
    'cookies'         => false
];

Teraz głównym zadaniem jest zmiana wartości klucza weryfikacyjnego .

'verify'          => false,

Więc po tym nie sprawdzi certyfikatu SSL dla żądania CURL ... To rozwiązanie działa dla mnie. Znalazłem to rozwiązanie po wielu badaniach ...

pankaj
źródło
2

opracowanie powyższych odpowiedzi na wdrożenie serwera.

$hostname = gethostname();
if($hostname=="mydevpc")
{
    curl_setopt($ch, CURLOPT_FOLLOWLOCATION, TRUE);
    curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
}

powinien wykonać sztuczkę w środowisku programistycznym bez narażania serwera na wdrożenie.

kolęda
źródło
Uruchamianie różnych części kodu w różnych środowiskach nie wydaje się dobrym pomysłem - utrudnia debugowanie
Nico Haase,
2

Próbowałem, to działa

otwarty

vendor\guzzlehttp\guzzle\src\Handler\CurlFactory.php

i zmień to

 $conf[CURLOPT_SSL_VERIFYHOST] = 2;
 `enter code here`$conf[CURLOPT_SSL_VERIFYPEER] = true;

do tego

$conf[CURLOPT_SSL_VERIFYHOST] = 0;
$conf[CURLOPT_SSL_VERIFYPEER] = FALSE;
Yuan Libres
źródło
0

Miałem ten sam problem podczas tworzenia mojej aplikacji w AppVeyor.

  • Pobierz https://curl.haxx.se/ca/cacert.pem nac:\php
  • Włącz openssl echo extension=php_openssl.dll >> c:\php\php.ini
  • Znajdź certyfikatecho curl.cainfo=c:\php\cacert.pem >> c:\php\php.ini
Głową w dół
źródło
0

Jeśli żadne z powyższych rozwiązań nie działa, spróbuj zaktualizować instalację XAMPP do nowszej wersji.

Korzystałem z XAMPP z php 5.5.11, ten sam dokładny kod nie działał, zaktualizowałem do XAMPP z php 5.6.28 i powyższe rozwiązania działały.

Dodatkowo tylko aktualizacja PHP nie działała albo wydaje się kombinacją ustawień apache i php w tej wersji XAMPP.

Mam nadzieję, że to komuś pomoże.

ccrez
źródło
0

Wystąpił błąd:

failed loading cafile stream: `C:\xamppPhp\apache\bin\curl-ca-bundle.crt`

Używam komputera z systemem Windows. Więc wykonałem poniższe kroki.

1. I have downloaded .pem file from " https://curl.haxx.se/docs/caextract.html "

2. Then I kept the downloaded file inside  "C:/xamppPhp/apache/bin/" folder and renamed the same downloaded file to "curl-ca-bundle.crt".

3. I restarted XAMPP and cleared the cache.
4. It's done.

Mam nadzieję, że to może komuś pomóc

S Debasish Nayak
źródło
0

Miałem taki problem w moim systemie lokalnym, ale nie na serwerze na żywo. Wspomniałem też o innym rozwiązaniu na tej stronie, ale nie działało to w localhost. Znajdź więc nowe rozwiązanie, które działa w localhost-WAMP Server .

cURL Error #: Problem z certyfikatem SSL: nie można uzyskać certyfikatu lokalnego wystawcy

czasami system nie może znaleźć pliku cacert.pem na dysku. więc możesz zdefiniować to w swoim kodzie, w którym będziesz używać CURL

Pamiętaj, że spełniam wszystkie warunki, takie jak aktywna biblioteka OPEN-SSL i inne rzeczy.

sprawdź ten kod CURL .

 $curl = curl_init();
 curl_setopt_array($curl, array(
            CURLOPT_URL =>$url,
            CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
            CURLOPT_CUSTOMREQUEST => "GET",
            CURLOPT_RETURNTRANSFER=> true,
        ));
curl_setopt($curl, CURLOPT_CAINFO, "f:/wamp/bin/cacert.pem"); // <------ 
curl_setopt($curl, CURLOPT_CAPATH, "f:/wamp/bin/cacert.pem"); // <------
$response = json_decode(curl_exec($curl),true);
$err = curl_error($curl);
curl_close($curl);

ale to rozwiązanie może nie działać na serwerze na żywo. z powodu bezwzględnej ścieżki cacert.pem

pankaj kumar
źródło
0

Mam właściwe rozwiązanie tego problemu, spróbujmy zrozumieć podstawową przyczynę tego problemu. Ten problem występuje, gdy nie można zweryfikować zdalnych serwerów ssl przy użyciu certyfikatów głównych w magazynie certyfikatów systemu lub zdalny ssl nie jest zainstalowany razem z certyfikatami łańcuchowymi. Jeśli masz system Linux z dostępem root ssh, w takim przypadku możesz spróbować zaktualizować bazę certyfikatów za pomocą poniższego polecenia:

update-ca-certificates

Jeśli nadal nie działa, musisz dodać główny i tymczasowy certyfikat zdalnego serwera w swoim magazynie certyfikatów. Możesz pobrać certyfikaty root i pośrednie i dodać je do katalogu / usr / local / share / ca-certyfikaty, a następnie uruchomić polecenie update-ca-certificates. To powinno załatwić sprawę. Podobnie w przypadku systemu Windows możesz wyszukać sposób dodawania certyfikatu root i pośredniego.

Innym sposobem rozwiązania tego problemu jest poproszenie zdalnego zespołu serwerów o dodanie certyfikatu ssl jako pakietu certyfikatu głównego domeny, certyfikatu pośredniego i certyfikatu głównego.

prasoon
źródło
-4

jeśli chcesz, możesz spróbować:

$client = new Client(env('API_HOST'));
$client->setSslVerification(false);

testowany na guzzle / guzzle 3. *

fico7489
źródło
1
czy jest sens odpowiadać na 3-letnie pytanie, na które przyjęto odpowiedź z ponad 200 głosami pozytywnymi?
treyBake
moja odpowiedź jest prostsza niż powyższe, zobaczysz, że dostanę 10 głosów poparcia na kilka miesięcy ...
fico7489,
1
Bardzo w to wątpię, nie widząc żadnej wzmianki o żlebie w OP ... więc jest to niezwiązana odpowiedź. To samo, gdy ktoś udostępnia rozwiązanie jQuery dla problemu JavaScript. To nie ma znaczenia.
treyBake
to nie zmienia faktu, że nie jest tu używany. Czy sugerowałbyś użytkownikowi Linuksa rozwiązanie dla systemu Linux, ponieważ jest to najczęściej używany system operacyjny serwera? Nie wszyscy chcą korzystać z Guzzle, osobiście nigdy nie korzystałem z niego raz w ciągu moich lat używania PHP. Dla mnie żądanie HTTP naprawdę nie jest tak trudne, aby potrzebować do niego pakietu.
treyBake
1
w pełni świadomy - to po prostu nie jest potrzebne ... po prostu przeczytaj dokumenty dotyczące curl i wszystko to samo wyjaśnia. Tu nie chodzi o bycie mądrzejszym ... chodzi o właściwe udzielenie odpowiedzi na pytanie
treyBake