it-swarm.com.de

Ungültiges selbstsigniertes SSL-Zertifikat in node.js mit https.request ignorieren?

Ich arbeite an einer kleinen App, die sich bei meinem lokalen WLAN-Router (Linksys) anmeldet, habe jedoch ein Problem mit dem selbstsignierten SSL-Zertifikat des Routers.

Ich ließ wget 192.168.1.1 laufen und erhielt:

ERROR: cannot verify 192.168.1.1's certificate, issued by `/C=US/ST=California/L=Irvine/O=Cisco-Linksys, LLC/OU=Division/CN=Linksys/[email protected]':
Self-signed certificate encountered.
ERROR: certificate common name `Linksys' doesn't match requested Host name `192.168.1.1'.
To connect to 192.168.1.1 insecurely, use `--no-check-certificate'.

In node wird der folgende Fehler abgefangen:

{ [Error: socket hang up] code: 'ECONNRESET' }

Mein aktueller Beispielcode ist:

var req = https.request({ 
    Host: '192.168.1.1', 
    port: 443,
    path: '/',
    method: 'GET'

}, function(res){

    var body = [];
    res.on('data', function(data){
        body.Push(data);
    });

    res.on('end', function(){
        console.log( body.join('') );
    });

});
req.end();

req.on('error', function(err){
    console.log(err);
});

Wie kann ich node.js dazu bringen, das Äquivalent von "--no-check-certificate" zu tun?

263
Geuis

Preiswerte und unsichere Antwort:

Hinzufügen

process.env["NODE_TLS_REJECT_UNAUTHORIZED"] = 0;

im Code, bevor https.request() aufgerufen wird

Ein sichererer Weg (die obige Lösung macht den gesamten Knotenprozess unsicher) wird in diesem Frage beantwortet

531
Juanra

Versuchen Sie in Ihren Anforderungsoptionen Folgendes einzuschließen:

   var req = https.request({ 
      Host: '192.168.1.1', 
      port: 443,
      path: '/',
      method: 'GET',
      rejectUnauthorized: false,
      requestCert: true,
      agent: false
    },
148
Meg Sharkey

Glauben Sie nicht allen, die versuchen, Sie in die Irre zu führen.

Fügen Sie Ihrer Anfrage einfach Folgendes hinzu:

ca: [fs.readFileSync([certificate path], {encoding: 'utf-8'})]

Wenn Sie nicht autorisierte Zertifikate aktivieren, sind Sie überhaupt nicht geschützt (MITM ausgesetzt, um Ihre Identität nicht zu validieren), und die Arbeit ohne SSL ist kein großer Unterschied. Die Lösung besteht darin, das erwartete CA-Zertifikat anzugeben, wie im nächsten Snippet gezeigt. Stellen Sie sicher, dass der allgemeine Name des Zertifikats mit der Adresse übereinstimmt, die Sie in der Anforderung angerufen haben (wie im Host angegeben):

Was Sie dann bekommen, ist:

var req = https.request({ 
      Host: '192.168.1.1', 
      port: 443,
      path: '/',
      ca: [fs.readFileSync([certificate path], {encoding: 'utf-8'})],
      method: 'GET',
      rejectUnauthorized: true,
      requestCert: true,
      agent: false
    },

Bitte lesen Sie diesen Artikel (Offenlegung: Blog-Beitrag des Autors dieser Antwort) hier, um Folgendes zu verstehen:

  • So funktionieren CA-Zertifikate
  • So erstellen Sie CA-Zertifikate zum einfachen Testen, um die Produktionsumgebung zu simulieren
53
Hesham Yassin

Fügen Sie die folgende Umgebungsvariable hinzu:

NODE_TLS_REJECT_UNAUTHORIZED=0

z.B. mit export:

export NODE_TLS_REJECT_UNAUTHORIZED=0

(Mit großem Dank an Juanra)

42
Armand

Hinzufügen zu @Armand Antwort:

Fügen Sie die folgende Umgebungsvariable hinzu:

NODE_TLS_REJECT_UNAUTHORIZED = 0, z. mit export:

export NODE_TLS_REJECT_UNAUTHORIZED = 0 (mit großem Dank an Juanra)

Wenn Sie unter Windows arbeiten:

set NODE_TLS_REJECT_UNAUTHORIZED=0

Danke an: @ weagle08

12
IamStalker

Sie können auch eine Anforderungsinstanz mit Standardoptionen erstellen:

require('request').defaults({ rejectUnauthorized: false })
8
Eduardo

Für meteorJS können Sie mit npmRequestOptions festlegen.

HTTP.post(url, {
    npmRequestOptions: {
        rejectUnauthorized: false // TODO remove when deploy
    },
    timeout: 30000, // 30s
    data: xml
}, function(error, result) {
    console.log('error: ' + error);
    console.log('resultXml: ' + result);
});
3
digz6666

Sie können auch versuchen, eine lokale Namensauflösung hinzuzufügen (hosts Datei im Verzeichnis etc in den meisten Betriebssystemen, Details unterscheiden sich):

192.168.1.1 Linksys 

und als nächstes

var req = https.request({ 
    Host: 'Linksys', 
    port: 443,
    path: '/',
    method: 'GET'
...

wird funktionieren.

1
piaf