Comment réparer l'erreur de certificat SSL lors de l'exécution de Npm sous Windows?

88

Lorsque j'essaye d'installer un package avec npm, cela ne fonctionne pas. Après une longue attente, j'obtiens finalement une erreur «Le socket de tunneling n'a pas pu être établi, sutatusCode = 403».

$ npm install coffee-script
npm http GET https://registry.npmjs.org/coffee-script
npm http GET https://registry.npmjs.org/coffee-script
npm http GET https://registry.npmjs.org/coffee-script
npm ERR! Error: tunneling socket could not be established, sutatusCode=403
npm ERR!     at ClientRequest.onConnect (c:\Program Files\nodejs\node_modules\npm\node_modules\request\tunnel.js:148:19)
npm ERR!     at ClientRequest.g (events.js:193:14)
npm ERR!     at ClientRequest.EventEmitter.emit (events.js:123:20)
npm ERR!     at Socket.socketOnData (http.js:1393:11)
npm ERR!     at TCP.onread (net.js:403:27)

Cependant, lorsque je navigue vers cette même URL dans mon navigateur Web (Google Chrome), cela se charge correctement (voir la note de bas de page). https://registry.npmjs.org/coffee-script

Qu'est-ce qui ne va pas?


Bien que j'utilise un proxy https, je suis convaincu que ce n'est pas le problème. J'ai configuré la variable d'environnement https_proxy(selon le guide de l'utilisateur npm ). Je sais que la variable d'environnement est correcte, car le gestionnaire de packages Python la pipsuit correctement.

Je pense que le problème concerne les certificats SSL, car si je télécharge cette URL avec wget, j'obtiens une erreur explicite concernant les certificats

$ wget https://registry.npmjs.org/coffee-script
SYSTEM_WGETRC = c:/progra~1/wget/etc/wgetrc
syswgetrc = c:/progra~1/wget/etc/wgetrc
--2012-12-17 12:14:07--  https://registry.npmjs.org/coffee-script
Resolving corpproxy... 10.254.215.35
Connecting to corpproxy|10.254.215.35|:8080... connected.
ERROR: cannot verify registry.npmjs.org's certificate, issued by `/C=US/ST=CA/L=Oakland/O=npm/OU=npm Certificate Authority/CN=npmCA/[email protected]':
  Unable to locally verify the issuer's authority.
To connect to registry.npmjs.org insecurely, use `--no-check-certificate'.
Unable to establish SSL connection.

Comment puis-je réparer cela? Sans compromettre la sécurité.


J'avais l'habitude d'obtenir des erreurs de certificat SSL dans mon navigateur Web aussi, jusqu'à ce que j'installe le certificat `` npmCA '' en tant qu '`` autorité de certification racine de confiance' 'dans les options Internet du panneau de configuration (capture d'écran entrez la description de l'image ici)


Edit: j'ai essayé une solution de contournement non sécurisée par https://npmjs.org/doc/config.html#strict-ssl

npm set strict-ssl false

Pourtant, il expire toujours avec la même erreur

$ npm install coffee-script
npm http GET https://registry.npmjs.org/coffee-script
npm http GET https://registry.npmjs.org/coffee-script
npm http GET https://registry.npmjs.org/coffee-script
npm ERR! Error: tunneling socket could not be established, sutatusCode=403
Colonel Panic
la source
C'est similaire au problème que j'ai: stackoverflow.com/questions/11773509/…
nwinkler
1
Salut. Voir aussi github.com/isaacs/npm/issues/2728
Colonel Panic
La saisie de "npm set strict-ssl false" a résolu un problème
MrD

Réponses:

142

TL; DR - Exécutez simplement ceci et ne désactivez pas votre sécurité:

Remplacer les certificats existants

# Windows/MacOS/Linux 
npm config set cafile "<path to your certificate file>"

# Check the 'cafile'
npm config get cafile

ou étendre les certificats existants

Définissez cette variable d'environnement pour étendre les certificats prédéfinis: NODE_EXTRA_CA_CERTSà"<path to certificate file>"

Histoire complète

J'ai dû travailler avec npm, pip, maven, etc. derrière un pare-feu d'entreprise sous Windows - ce n'est pas amusant. Je vais essayer de garder cette plate-forme indépendante / consciente dans la mesure du possible.

HTTP_PROXY et HTTPS_PROXY

HTTP_PROXY& HTTPS_PROXYsont des variables d'environnement utilisées par de nombreux logiciels pour savoir où se trouve votre proxy. Sous Windows, de nombreux logiciels utilisent également le proxy spécifié par votre système d'exploitation, ce qui est totalement différent. Cela signifie que vous pouvez faire en sorte que Chrome (qui utilise le proxy spécifié dans vos options Internet) se connecte à l'URL très bien, mais npm, pip, maven, etc. ne fonctionnent pas car ils utilisent HTTPS_PROXY (sauf lorsqu'ils utilisent HTTP_PROXY - voir plus tard). Normalement, la variable d'environnement ressemblerait à quelque chose comme:

http://proxy.example.com:3128

Mais vous obtenez un 403 qui suggère que vous n'êtes pas authentifié par rapport à votre proxy. S'il s'agit d'une authentification de base sur le proxy, vous voudrez définir la variable d'environnement sur quelque chose de la forme:

http://user:[email protected]:3128

Le redoutable NTLM

Il existe un code d'état HTTP 407 (authentification proxy requise), ce qui est la manière la plus correcte de dire que c'est le proxy plutôt que le serveur de destination qui rejette votre demande. Ce code m'a tourmenté pendant très longtemps jusqu'à ce qu'après beaucoup de temps sur Google, j'ai appris que mon proxy utilisait l' authentification NTLM . L'authentification de base HTTP n'était pas suffisante pour satisfaire le proxy que mes seigneurs d'entreprise avaient installé. J'ai eu recours à l'utilisation de Cntlm sur ma machine locale (non authentifiée), puis je lui ai fait gérer l'authentification NTLM avec le proxy en amont. Ensuite, j'ai dû dire à tous les programmes qui ne pouvaient pas faire NTLM d'utiliser ma machine locale comme proxy - ce qui est généralement aussi simple que de paramétrer HTTP_PROXYet HTTPS_PROXY. Sinon, pour l'utilisation de npm (comme @Agus le suggère):

npm config set proxy http://proxy.example.com:3128
npm config set https-proxy http://proxy.example.com:3128

"Nous devons décrypter tout le trafic HTTPS car les virus"

Après que cette configuration ait fonctionné (maladroitement) pendant environ un an, les seigneurs de l'entreprise ont décidé de changer de proxy. Non seulement cela, mais il n'utiliserait plus NTLM! Un nouveau monde courageux pour être sûr. Mais comme ces auteurs de logiciels malveillants diffusaient désormais des logiciels malveillants via HTTPS, le seul moyen de protéger nous, pauvres utilisateurs innocents, était de gérer chaque connexion pour rechercher les menaces avant même qu'elles ne nous atteignent. Comme vous pouvez l'imaginer, j'ai été submergé par le sentiment de sécurité.

Pour faire court, le certificat auto-signé doit être installé dans npm pour éviter SELF_SIGNED_CERT_IN_CHAIN:

npm config set cafile "<path to certificate file>"

Sinon, la NODE_EXTRA_CA_CERTSvariable d'environnement peut être définie sur le fichier de certificat.

Je pense que c'est tout ce que je sais pour faire fonctionner npm derrière un proxy / pare-feu. Que quelqu'un le trouve utile.

Edit : C'est une suggestion très courante de désactiver HTTPS pour ce problème en utilisant un registre ou un paramètre HTTP NODE_TLS_REJECT_UNAUTHORIZED. Ce ne sont pas de bonnes idées, car vous vous ouvrez à d'autres attaques d'intermédiaire ou de redirection. Une usurpation rapide de vos enregistrements DNS sur la machine effectuant l'installation du package et vous vous retrouverez à faire confiance aux packages de n'importe où. Faire fonctionner HTTPS peut sembler beaucoup de travail, mais c'est fortement recommandé. Lorsque vous êtes responsable de l’autorisation du code non approuvé dans l’entreprise, vous comprendrez pourquoi.

Edit 2 : Gardez à l'esprit que la configuration npm config set cafile <path>fait en sorte que npm n'utilise que les certificats fournis dans ce fichier, au lieu d'étendre ceux existants avec lui.

Si vous souhaitez étendre les certificats existants (par exemple avec un certificat d'entreprise), utiliser la variable d'environnement NODE_EXTRA_CA_CERTSpour créer un lien vers le fichier est la voie à suivre et peut vous éviter beaucoup de tracas. Voir comment ajouter-une-autorité-de-certification-personnalisée-ca-to-nodejs

Alex Taylor
la source
9
Sous Windows, j'ai dû utiliser des barres obliques: npm config set cafile "C: /dev/Firefox/mycert.cer"
John Jesus
4
** Sans signe égal= npm config set cafile "<path to your certificate file>"
Moti Winkler
3
C'est une réponse géniale - je ne pourrais pas mieux résumer mes propres maux de tête concernant proxy + zscalar
Jpnh
7
rit si fort à cause de "Comme vous pouvez l'imaginer, j'ai été submergé par le sentiment de sécurité." :)
Mario B
3
Comment obtenir le fichier de certificat?
Aditya le
36

Ce problème a été résolu pour moi en utilisant la version http du référentiel:

npm config set registry http://registry.npmjs.org/
Ehsan
la source
52
C'est une très mauvaise solution!
KiT O
4
@HaBo Je suppose qu'il veut dire que ce n'est pas sûr.
gabeio
3
@KiTO C'est une mauvaise solution, d'accord. Mais pourquoi devrais-je me soucier des problèmes de certificat alors que je veux juste installer des packages?
Ich
17
Cette réponse est correcte. Il y a des cas où vous êtes derrière le désordre de proxy d'entreprise avec sa propre chaîne de certificats sur les autres et il n'y a pas d'autre moyen (à part la désactivation des câbles du tout) que cela (surtout quand ils ne vous donnent pas les droits d'administrateur). Cela ressemble à un bogue npm qui ne charge pas correctement les paramètres appropriés du système. Mais pour des raisons de compatibilité croisée, ils ne corrigeront pas le npm, c'est donc le résultat. Les gens qui disent que c'est une mauvaise réponse, ils n'ont aucune idée de ce dont ils parlent.
kenorb
3
@kenorb c'est incorrect, vous pouvez retracer les étapes suivies par votre proxy et ajouter ces certificats auto-signés à votre chaîne avec cafile.
dardo
15
npm config set strict-ssl false

résolu le problème pour moi. Dans ce cas, mon agent et mon dépositaire d'artefacts sont derrière un sous-réseau privé sur le cloud AWS

Anupam Mahapatra
la source
7

J'ai le même problème, je surmonte en utilisant

npm config set proxy http://my-proxy.com:1080
npm config set https-proxy http://my-proxy.com:1080

Informations supplémentaires sur node-doc

Agus
la source
6

Il m'est arrivé de rencontrer ce problème SSL similaire il y a quelques jours. Le problème est que votre npm ne définit pas de certificat racine pour le certificat utilisé par https://registry.npmjs.org .

Solutions:

  1. Utilisez wget https://registry.npmjs.org/coffee-script --ca-certificate=./DigiCertHighAssuranceEVRootCA.crtpour résoudre le problème wget
  2. Utilisez npm config set cafile /path/to/DigiCertHighAssuranceEVRootCA.crtpour définir le certificat racine de votre programme npm.

vous pouvez télécharger le certificat racine à partir de: https://www.digicert.com/CACerts/DigiCertHighAssuranceEVRootCA.crt

Remarque: un programme différent peut utiliser une manière différente de gérer le certificat racine, alors ne mélangez pas le navigateur avec d'autres.

Une analyse:

réglons d' wget https://registry.npmjs.org/coffee-scriptabord votre problème. votre extrait dit:

        ERREUR: impossible de vérifier le certificat de registry.npmjs.org,
        émis par / C = US / ST = CA / L = Oakland / O = npm / OU = npm 
       Autorité de certification/CN=npmCA/[email protected]:
       Impossible de vérifier localement l'autorité de l'émetteur.

Cela signifie que votre programme wget ne peut pas vérifier https://registry.npmjs.orgle certificat de. Deux raisons peuvent provoquer ce problème:

  1. Votre programme wget ne possède pas le certificat racine de ce domaine. Le certificat racine est généralement livré avec le système.
  2. Le domaine n'emballe pas le certificat racine dans son certificat.

La solution est donc explicitement définie pour le certificat racine https://registry.npmjs.org. Nous pouvons utiliser openssl pour nous assurer que la raison ci-dessous est le problème.

Essayez openssl s_client -host registry.npmjs.org -port 443sur la ligne de commande et nous obtiendrons ce message (les premières lignes):

    CONNECTÉ (00000003)
    profondeur = 1 / C = US / O = DigiCert Inc / OU = www.digicert.com / CN = DigiCert High Assurance CA-3
    Vérifier l'erreur: num = 20: impossible d'obtenir le certificat de l'émetteur local
    vérifier le retour: 0
    ---
    Chaîne de certificats
     0 s: / C = US / ST = Californie / L = San Francisco / O = Fastly, Inc./CN=a.sni.fastly.net
       i: / C = US / O = DigiCert Inc / OU = www.digicert.com / CN = DigiCert High Assurance CA-3
     1 s: / C = US / O = DigiCert Inc / OU = www.digicert.com / CN = DigiCert High Assurance CA-3
       i: / C = US / O = DigiCert Inc / OU = www.digicert.com / CN = DigiCert High Assurance EV Root CA
    ---

Cette ligne verify error:num=20:unable to get local issuer certificates'assure que https://registry.npmjs.orgne compresse pas le certificat racine. Nous avons donc un DigiCert High Assurance EV Root CAcertificat racine Google .

personne0jour
la source
Si vous ne pouvez fournir que le fichier de base texte (comme pour les versions Jenkins), ce certificat peut être converti en pem: openssl x509 -inform DER -outform PEM -in DigiCertHighAssuranceEVRootCA.crt -out DigiCertHighAssuranceEVRootCA.pem
Audrius Meskauskas
4

J'avais le même problème. Après quelques recherches, j'ai réalisé que de nombreux scripts de post / pré-installation essaieraient d'installer diverses dépendances et que des référentiels spécifiques étaient parfois utilisés. Un meilleur moyen est de désactiver la vérification des certificats pour le module https pour les nodejs qui ont fonctionné pour moi.

process.env.NODE_TLS_REJECT_UNAUTHORIZED = "0"

De cette question

haroon
la source
2
Comme mentionné précédemment, cela ne résoudra pas le problème SSL, cela ne fera que le contourner. La bonne façon de résoudre ce problème est de configurer correctement chaque package (git, npm, node) pour faire confiance au certificat de signature approprié. Si vous êtes derrière un proxy coporate, de couurse.
Aaron C
0

Le problème réside dans votre proxy. Étant donné que le fournisseur d'emplacement de votre package d'installation crée son propre certificat et n'achète pas de certificat vérifié auprès d'une autorité acceptée, votre proxy n'autorise pas l'accès à l'hôte ciblé. Je suppose que vous contournez le proxy lorsque vous utilisez le navigateur Chrome. Il n'y a donc pas de vérification.

Il existe des solutions à ce problème. Mais tous impliquent que vous faites confiance au fournisseur de packages.

Solutions possibles:

  1. Comme mentionné dans d'autres réponses, vous pouvez créer un http://accès qui peut contourner votre proxy. C'est un peu dangereux, car l'homme du milieu peut injecter des logiciels malveillants dans vos téléchargements.
  2. Le wgetvous suggère d'utiliser un drapeau --no-check-certificate. Cela ajoutera une directive proxy à votre demande. Le proxy, s'il comprend la directive, ne vérifie pas si le certificat du serveur est vérifié par une autorité et passe la requête. Il existe peut-être une configuration avec npm qui fait la même chose que l'indicateur wget.
  3. Vous configurez votre proxy pour accepter CA npm. Je ne connais pas votre mandataire, donc je ne peux pas vous donner un indice.
Peter Paul Kiefer
la source
0

définissez la propriété ci-dessous:

"npm config set strict-ssl false"

Rohit Maurya
la source
0

Si vous avez le contrôle du serveur proxy ou pouvez convaincre vos administrateurs informatiques, vous pouvez essayer d'exclure explicitement registry.npmjs.org de l'inspection SSL. Cela devrait éviter aux utilisateurs du serveur proxy d'avoir à désactiver la vérification strict-ssl ou à installer une nouvelle autorité de certification racine.

Thiezn
la source
-1

C'est ce que vous pouvez faire pour éviter le npm et utiliser du fil dans la machine à fenêtre.

yarn config set "strict-ssl" false
Ram Kumar Thapa
la source