erreur cURL 60: certificat SSL: impossible d'obtenir le certificat de l'émetteur local
J'utilise WAMP sur un environnement de développement local et j'essaie de charger une carte de crédit mais j'obtiens le message d'erreur:
Erreur CURL 60: problème de certificat SSL: impossible d'obtenir le certificat d'émetteur local
J'ai beaucoup cherché sur Google et beaucoup de gens suggèrent que je télécharge ce fichier: cacert.pem , mettez-le quelque part et référencez-le dans mon php.ini. C'est la partie dans mon php.ini:
curl.cainfo = "C:Windowscacert.pem"
Pourtant, même après avoir redémarré mon serveur plusieurs fois et en changeant le chemin, je reçois le même message d'erreur.
J'utilise WAMP à partir des Modules Apache et j'ai le ssl_module activé. Et à partir des extensions PGP, php_curl est activé.
Toujours le même message d'erreur. Pourquoi est-ce qui se passe?
Maintenant, je suis ce correctif: Comment réparer L'erreur PHP CURL 60 SSL
Ce qui suggère que j'ajoute ces lignes à mes options de boucle:
curl_setopt($process, CURLOPT_CAINFO, dirname(__FILE__) . '/cacert.pem');
curl_setopt($process, CURLOPT_SSL_VERIFYPEER, true);
Où puis-je ajouter des options à ma boucle? Apparemment pas via la ligne de commande, puisque mon CLI ne trouve pas la commande "curl_setopt"
Modifier
C'est le code que je cours:
public function chargeStripe()
{
$stripe = new Stripe;
$stripe = Stripe::make(env('STRIPE_PUBLIC_KEY'));
$charge = $stripe->charges()->create([
'amount' => 2900,
'customer' => Input::get('stripeEmail'),
'currency' => 'EUR',
]);
dd($charge);
// echo $charge[Input::get('stripeToken')];
return Redirect::route('step1');
}
16 réponses
Solution de travail:
- en supposant sur windows
Serveur XAMPP
Similaire pour un autre environnement - télécharger et extraire pour cacert.pem ici (un format de fichier/Données propre)
- Mettez-le ici
C:\xampp\php\extras\ssl\cacert.pem
- dans votre php.ini mettre cette ligne dans cette section ("c:\xampp\php\php.ini"):
;;;;;;;;;;;;;;;;;;;; ; php.ini Options ; ;;;;;;;;;;;;;;;;;;;; curl.cainfo = "C:\xampp\php\extras\ssl\cacert.pem"
- Redémarrez votre serveur web/apache
Problème résolu!
Si vous utilisez PHP 5.6 avec Guzzle, Guzzle est passé à utiliser les bibliothèques PHP autodetect pour les certificats plutôt que son processus (ref). PHP décrit les changements ici .
Trouver où PHP / Guzzle cherche des certificats
Vous pouvez vider où PHP regarde en utilisant:
var_dump(openssl_get_cert_locations());
Obtenir un paquet de certificats
Pour les tests OS X, vous pouvez utiliser homebrew pour installer openssl brew install openssl
et ensuite utiliser openssl.cafile=/usr/local/etc/openssl/cert.pem
dans votre php.ini ou Zend Paramètres du serveur (sous OpenSSL).
Un paquet de certificats est également disponible à partir de curl / Mozilla sur le site Web de curl: https://curl.haxx.se/docs/caextract.html
Indiquer à PHP où se trouvent les certificats
Une fois que vous avez un bundle, placez-le là où PHP est déjà à la recherche (ce que vous avez découvert ci-dessus) ou mettez à jour openssl.cafile
en php.ini. (Généralement, /etc/php.ini
ou /etc/php/7.0/cli/php.ini
ou /etc/php/php.ini
sur Unix.)
Attention aux utilisateurs de WAMP / Wordpress / windows. J'ai eu ce problème pendant des heures et même la bonne réponse ne le faisait pas pour moi, parce que j'éditais le mauvais php.fichier ini parce que la question a été répondu à XAMPP et non pour les utilisateurs WAMP, même si la question était pour WAMP.
Voici ce que j'ai fait
Téléchargez le paquet de certificats .
Mettre à l'intérieur de C:\wamp64\bin\php\your php version\extras\ssl
Assurez-vous que le fichier mod_ssl.so
est à l'intérieur de C:\wamp64\bin\apache\apache(version)\modules
Activer mod_ssl
dans httpd.conf
dans le répertoire Apache C:\wamp64\bin\apache\apache2.4.27\conf
Activer php_openssl.dll
dans php.ini
. Sachez que mon problème était que j'avais deux php.les fichiers ini et je dois le faire dans les deux. Le premier peut être situé à l'intérieur de votre icône de barre des tâches WAMP ici.
, Et l'autre est situé dans C:\wamp64\bin\php\php(Version)
Trouvez l'emplacement pour les deux fichiers php.ini
et trouvez la ligne curl.cainfo =
et donnez - lui un chemin comme ceci
curl.cainfo = "C:\wamp64\bin\php\php(Version)\extras\ssl\cacert.pem"
Maintenant enregistrer les fichiers et redémarrez votre serveur et vous devriez être bon pour aller
Guzzle, qui est utilisé par cartalyst / stripe , fera ce qui suit pour trouver une archive de certificat appropriée pour vérifier un certificat de serveur:
- vérifiez si {[1] } est défini dans votre php.fichier ini.
- vérifiez si
curl.cainfo
est défini dans votre php.fichier ini. - vérifiez si
/etc/pki/tls/certs/ca-bundle.crt
existe (Red Hat, CentOS, Fedora; fourni par le paquet ca-certificates) - vérifiez si
/etc/ssl/certs/ca-certificates.crt
existe (Ubuntu, Debian; fourni par le paquet ca-certificates) - vérifier si
/usr/local/share/certs/ca-root-nss.crt
existe (FreeBSD; fourni par le paquet ca_root_nss) - vérifiez si
/usr/local/etc/openssl/cert.pem
(OS X; fourni par homebrew) - vérifiez si
C:\windows\system32\curl-ca-bundle.crt
existe (Windows) - vérifiez si
C:\windows\curl-ca-bundle.crt
existe (Windows)
Vous Voulez vous assurer que les valeurs des deux premiers paramètres sont correctement définies en faisant un test simple:
echo "openssl.cafile: ", ini_get('openssl.cafile'), "\n";
echo "curl.cainfo: ", ini_get('curl.cainfo'), "\n";
Sinon, essayez d'écrire le fichier dans les emplacements indiqués par #7 ou # 8.
Si vous ne parvenez pas à changer php.ini vous pouvez également pointer vers le cacert.fichier pem du code comme ceci:
$http = new GuzzleHttp\Client(['verify' => '/path/to/cacert.pem']);
$client = new Google_Client();
$client->setHttpClient($http);
J'ai trouvé une solution qui a fonctionné pour moi. J'ai rétrogradé de la dernière guzzle à la version ~ 4.0 et cela a fonctionné.
Dans compositeur.json ajouter "guzzlehttp/bouffer": "~4.0"
J'espère que cela aide quelqu'un
Ce que j'ai fait était d'utiliser var_dump(openssl_get_cert_locations()); die;
dans n'importe quel script php, ce qui m'a donné les informations sur les valeurs par défaut que mon php local utilisait:
array (size=8)
'default_cert_file' => string 'c:/openssl-1.0.1c/ssl/cert.pem' (length=30)
'default_cert_file_env' => string 'SSL_CERT_FILE' (length=13)
'default_cert_dir' => string 'c:/openssl-1.0.1c/ssl/certs' (length=27)
'default_cert_dir_env' => string 'SSL_CERT_DIR' (length=12)
'default_private_dir' => string 'c:/openssl-1.0.1c/ssl/private' (length=29)
'default_default_cert_area' => string 'c:/openssl-1.0.1c/ssl' (length=21)
'ini_cafile' => string 'E:\xampp\php\extras\ssl\cacert.pem' (length=34)
'ini_capath' => string '' (length=0)
Comme vous pouvez le remarquer, j'ai défini l'option ini_cafile ou l'option ini curl.cainfo. Mais dans mon cas, curl essaierait d'utiliser le "default_cert_file" qui n'existait pas.
J'ai copié le fichier depuis https://curl.haxx.se/ca/cacert.pem dans l'emplacement de "default_cert_file" (c:/openssl-1.0.1c/ssl/cert.pem) et j'ai pu le faire fonctionner.
C'était la seule solution pour moi.
J'ai eu ce problème un jour, quand un script Guzzle(5) tentait de se connecter à un hôte via SSL. Bien sûr, je pourrais désactiver L'option VERIFY dans Guzzle / Curl, mais ce n'est clairement pas la bonne façon de procéder.
J'ai essayé tout répertorié ici et dans des threads similaires, puis finalement allé au terminal avec openssl pour tester le domaine avec lequel j'essayais de me connecter:
openssl s_client -connect example.com:443
... et reçu les premières lignes indiquer:
CONNECTED(00000003)
depth=0 CN = example.com
verify error:num=20:unable to get local issuer certificate
verify return:1
depth=0 CN = example.com
verify error:num=21:unable to verify the first certificate
verify return:1
... alors que tout fonctionnait bien en essayant d'autres destinations (ie: google.com, etc)
Cela m'a incité à contacter le domaine auquel j'avais essayé de me connecter, et en effet, ils avaient un problème de leur côté qui s'était glissé. Il a été résolu et mon script est retourné au travail.
Donc... si vous vous arrachez les cheveux, donnez un coup de feu à openssl et voyez s'il y a quelque chose avec la réponse de l'emplacement que vous essayez de connecter. Peut-être le problème n'est pas si "local" après tout, parfois.
Je viens de rencontrer ce même problème avec le framework PHP Laravel 4 qui utilise le paquet guzzlehttp/guzzle
composer. Pour une raison quelconque, le certificat SSL pour mailgun a cessé de valider soudainement et j'ai reçu le même message "Erreur 60".
Si, comme moi, vous êtes sur un hébergement mutualisé sans accès à php.ini
, les autres solutions ne sont pas possibles. Dans tous les cas, Guzzle a ce code d'initialisation du client qui annulerait probablement les effets php.ini
:
// vendor/guzzlehttp/guzzle/src/Client.php
$settings = [
'allow_redirects' => true,
'exceptions' => true,
'decode_content' => true,
'verify' => __DIR__ . '/cacert.pem'
];
Ici Guzzle force l'utilisation de son propre cacert.fichier pem, qui est probablement maintenant obsolète, au lieu d'utiliser celui fourni par l'environnement de cURL. Changer cette ligne (sous Linux au moins) configure Guzzle pour utiliser la logique de vérification SSL par défaut de cURL et a corrigé mon problème:
'verify' => true
Vous pouvez également définir ceci sur false
Si vous ne vous souciez pas de la sécurité de votre connexion SSL, mais ce n'est pas une bonne solution.
Puisque les fichiers de vendor
ne sont pas destinés à être falsifiés, une meilleure solution serait être à configurer le client Guzzle sur l'utilisation, mais c'était trop difficile à faire dans Laravel 4.
J'espère que cela économise quelques heures de débogage à quelqu'un d'autre...
Cela peut être un cas limite, mais dans mon cas, le problème n'était pas la client conf (j'ai déjà eu curl.cainfo
configuré en php.ini
), mais plutôt le serveur distant ne pas être correctement configuré:
Il n'a pas envoyé de certificats intermédiaires dans la chaîne. Il n'y avait pas d'erreur en naviguant sur le site en utilisant Chrome, mais avec PHP j'ai eu l'erreur suivante.
Erreur de boucle 60
Après avoir inclus les certificats intermédiaires dans la télécommande configuration du serveur Web cela a fonctionné.
Vous pouvez utiliser ce site pour vérifier la configuration SSL de votre serveur:
J'ai passé trop de temps à comprendre ce problème pour moi.
J'avais PHP version 5.5 et j'avais besoin de passer à 5.6.
Dans les versions
J'ai également téléchargé le fichier à partir d'ici https://curl.haxx.se/docs/caextract.html {[9] } et définissez-le en php.ini.
Réponse trouvée dans Guzzles StreamHandler.fichier php https://github.com/guzzle/guzzle/blob/0773d442aa96baf19d7195f14ba6e9c2da11f8ed/src/Handler/StreamHandler.php#L437
// PHP 5.6 or greater will find the system cert by default. When // < 5.6, use the Guzzle bundled cacert.
Avez-vous essayé..
curl_setopt($process, CURLOPT_SSL_VERIFYPEER, false);
Si vous consommez une source de confiance, vous n'avez sans doute pas besoin de vérifier le certificat SSL.
Assurez-vous que vous ouvrez le fichier php.ini
directement par votre explorateur de fenêtres. (dans mon cas: C:\DevPrograms\wamp64\bin\php\php5.6.25
).
N'utilisez pas le raccourci vers php.ini
dans le menu de l'icône Wamp / Xamp dans la barre D'état système. Ce raccourci ne fonctionne pas dans ce cas.
Puis éditez ce php.ini
:
curl.cainfo ="C:/DevPrograms/wamp64/bin/php/cacert.pem"
Et
openssl.cafile="C:/DevPrograms/wamp64/bin/php/cacert.pem"
Après avoir enregistré php.ini
, vous n'avez pas besoin de "redémarrer tous les Services" dans l'icône Wamp ou de fermer/rouvrir CMD.
Quand je cours 'var_dump(php_ini_loaded_file());'
Je reçois cette sortie sur ma page
'C:\Development\bin\apache\apache2.4.33\bin\php.ini' (length=50)'
Et pour que php charge mon fichier cert, j'ai dû éditer le php.ini dans ce chemin 'C:\Development\bin\apache\apache2.4.33\bin\php.ini'
et ajoutez openssl.cafile="C:/Development/bin/php/php7.2.4/extras/ssl/cacert.pem"
où j'avais téléchargé et placez mon fichier cert à partir de https://curl.haxx.se/docs/caextract.html
Suis sur windows 10, en utilisant drupal 8, wamp et php7.2. 4
Comme vous utilisez Windows, je pense que votre séparateur de chemin est ' \ '(et ' / ' sous Linux).
Essayez d'utiliser la constante DIRECTORY_SEPARATOR
. Votre code sera plus portable.
Essayez:
curl_setopt($process, CURLOPT_CAINFO, dirname(__FILE__) . DIRECTORY_SEPARATOR . 'cacert.pem');
EDIT: et écrivez le chemin complet. J'ai eu quelques problèmes avec les chemins relatifs (peut-être que curl est exécuté à partir d'un autre répertoire de base?)
Si vous utilisez WAMP, vous devez également ajouter la ligne de certificat en php.ini pour Apache (outre le php par défaut.fichier ini):
[curl]
curl.cainfo = C:\your_location\cacert.pem
Fonctionne pour php5. 3 +