2012-03-19 14 views
9

Mam problemy na moim serwerze programistycznym, gdzie cURL, działając doskonale z dowolnym HTTP, nie działa poprawnie z niczym HTTPS - nawet ten sam zasób z różnymi protokołami (do testowania I ' ve been requesting google.com przy użyciu zarówno http i https).PHP cURL nie działa z HTTPS

Zwrócony błąd cURL to 35: "Wystąpił problem podczas uzgadniania SSL/TLS."

Połączyłem sieć i SO w poszukiwaniu rozwiązań, a wszystkie z nich ustawiły CURLOPT_SSL_VERIFYPEER na false, co niczego nie zmieniało, lub aby pobrać plik certyfikatu i ustawić CURLOPT_CAINFO na ścieżce, która również niczego nie zmienia.

Podczas ustawiania certyfikatu postępowałem zgodnie z instrukcjami this tutorial i this tutorial, próbując zarówno pobrać certyfikat dla żądanego zasobu, jak i pobrać pakiet certyfikatu.

Próbowałem zostały również wyraźnie ustalone CURLOP_PORT do 443. Dla dokładności moje pytanie, mam inne opcje są ustawione CURLOPT_VERBOSE = true, CURLOPT_RETURNTRANSFER = true, a CURLOPT_SSL_VERIFYHOST = 2 (Próbowałem wszystkich kombinacji 1 i 2 z VERIFYPEER zarówno true, jak i false). Upewniłem się również w phpinfo(), że mam OpenSSL i jest on włączony.

Używam wielu starych kodów, które działały idealnie na moim ostatnim serwerze produkcyjnym, więc ten kod działał wcześniej. Ale ten hosting był hostem dzielonym i nie znam tam większości konfiguracji.

+0

Czy uzyskujesz dostęp do tego samego adresu URL? Udało Ci się dotrzeć do większości tych samych badań, które zrobiłem, gdy wpadłem na ten problem. – Jason

+0

Użyłem zarówno http: // www.google.com, który działał; i https: // www.google.com, ale nie. – spezied

+0

@Spezied, jeśli dostarczona odpowiedź odpowiada na twoje pytanie, czy mógłbyś wybrać ją jako odpowiedź, aby pytanie zostało zamknięte? Dzięki. –

Odpowiedz

8

Co powiesz na to. To pobiera dla mnie stronę domową Google HTTPS. To powinno załatwić sprawę.

<?PHP 

// connect via SSL, but don't check cert 
$handle=curl_init('https://www.google.com'); 
curl_setopt($handle, CURLOPT_VERBOSE, true); 
curl_setopt($handle, CURLOPT_RETURNTRANSFER, true); 
curl_setopt($handle, CURLOPT_SSL_VERIFYPEER, false); 
$content = curl_exec($handle); 

echo $content; // show target page 
?> 
+1

Zobacz moją odpowiedź powyżej, ignorowanie cedru nie jest najlepszą opcją. – Ray

+3

TO JEST NIECH WAŻNE. Nie rób tego. Zawsze weryfikuj peer i hosta. Zobacz inną odpowiedź. –

+5

@Matt. Zależy od tego, co robisz. Przenoszenie ważnych rzeczy dla finansów, na pewno sprawdź poprawność HTTPS. Skrobanie marek obuwia ze sklepu detalicznego ... MITM nie powinien stanowić problemu. Oczywiście rozważ kontekst problemu. –

16

Curl nie ma wbudowanych certyfikatów głównych (jak większość współczesnych przeglądarek). Trzeba wyraźnie podkreślić je do pliku cacert.pem:

curl_setopt($ch, CURLOPT_CAINFO, '/path/to/cert/file/cacert.pem'); 

Bez tego, curl nie może zweryfikować certyfikatu odsyłany przez SSL. Ten sam plik certyfikatu głównego może być używany za każdym razem, gdy używasz SSL w curl.

Możesz pobrać plik cacert.pem tutaj: http://curl.haxx.se/docs/caextract.html

+0

Dlaczego po prostu nie użyć odpowiednika flagi '--insecure'? Czy jest jeden? – Pacerier

+1

@ Ustawień programiście 'CURLOPT_SSL_VERIFYPEER' na false to dokładnie' --insecure' flaga w wierszu poleceń. Nie chcesz tego robić, jeśli zależy Ci na autentyczności serwera docelowego – Ray

+0

, to nie zadziałało. Podczas gdy 'CURLOPT_SSL_VERIFYPEER' na' false' ma. – n8bar

2

Znajdź jeśli OS zawiera katalog certyfikatów. Jeśli tak, to wymagane certyfikaty CA często będą już uwzględnione. Na przykład na Ubuntu zwykle jest to /etc/ssl/certs. Jeśli ten katalog istnieje, ustaw parametr ścieżki CA:

curl_setopt($ch, CURLOPT_CAPATH, '/etc/ssl/certs'); 

Alternatywnie można odwołać się do pojedynczego pliku certyfikatu urzędu certyfikacji. Dodaj plik cacert.pem do swojego projektu lub zainstaluj go na swoim serwerze. Pobierz z zaufanego źródła, np. cacert.org. W przypadku pojedynczego pliku nie ustawia CApath i zamiast tylko ustawić CAINFO:

curl_setopt($ch, CURLOPT_CAINFO, '/path/to/cacert.pem'); 

Wyłączanie wzajemnej weryfikacji i gospodarz jest szybkie ale niepewny obejście rzeczywistego problemu. Te funkcje istnieją z dobrego powodu: możesz więc zaufać, za pośrednictwem innej firmy, że system, z którym się łączysz, jest tym, którego oczekujesz.

curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 1); 
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 2);