6

这个测试程序连接到一个 https 服务器并获取一些内容。我已经在浏览器和 curl 中检查了我的服务器,并且证书工作正常。如果我运行 curl 从服务器获取数据,它会正确地抱怨证书未知,除非我使用 --cacert 传递它或使用 -k 关闭安全性。

所以我遇到的问题是,虽然我认为我的客户应该进行证书身份验证并且我告诉它公共证书在哪里,但它总是有效。如果我删除 ca: 选项,因此它不知道来自服务器的证书是什么,那么它会静默工作。我想捕捉身份验证错误,但我似乎做不到。

var https = require('https');
var fs = require('fs');

function main() {

      var data = '';

      var get = https.get({
        path: '/',
        host: 'localhost',
        port: 8000,
        agent: false,
        ca: [ fs.readFileSync('https_simple/cacert.pem') ]

      }, function(x) {

        x.setEncoding('utf8');
        x.on('data', function(c) {data += c});
        x.on('error', function(e) {
          throw e;
        });
        x.on('end', function() {
          console.log('Hai!. Here is the response:');
          console.log(data);
        });

      });

      get.on('error', function(e) {throw e});

      get.end();

    }

main();
4

4 回答 4

10

为了完成这项工作,我需要升级到 v0.7.8(尽管任何 v0.7 都应该没问题),其中 rejectUnauthorized 功能已添加到 https.get

需要这种选项组合:

agent: false, // or you can supply your own agent, but if you don't you must set to false
rejectUnauthorized: true, 
ca: [ fs.readFileSync('https_simple/cacert.pem') ]

现在,如果身份验证失败,您将收到一个“错误”事件,并且请求将不会继续。

有关制作自己的代理的详细信息,请参阅 https.request文档

在此更改中提交了错误修复:https ://github.com/joyent/node/commit/f8c335d0

于 2012-04-20T03:55:18.273 回答
5

根据 的文档,两者https.request的选项和是来自 的选项。模块功能选项的文档说明:cahttps.gethttps.requesttls.connecttls.connect

ca:受信任证书的字符串或缓冲区数组。如果省略,将使用几个众所周知的“根”CA,例如 VeriSign。这些用于授权连接。

深入研究 node.js 源代码,可以在此处找到使用的根证书:https ://github.com/joyent/node/blob/master/src/node_root_certs.h

所以简而言之,如果没有提供作为模块选项https.get的授权证书tls,无论如何都会尝试使用根证书列表来验证连接。

于 2012-04-17T21:59:58.590 回答
2

我在 npm 中使用请求模块执行此操作。它是这样的:

var cacert = ... // in npm, this is a config setting
var request = require("request")
request.get({ url: "https://...",
              ca: cacert,
              strictSSL: true })
  .on("response", function (resp) { ... })
  .on("error", function (er) { ... })

如果 ssl 无效,将引发错误事件。

于 2012-04-20T05:14:17.290 回答
1

在 V 0.6.15 中,您需要明确检查证书验证是通过还是失败。

if (x.connection.authorized === false) {    
   console.log('SSL Authentication failed');
} else if (x.connection.authorized === true) {    
   console.log('SSL Authentication succeeded');
} 
于 2012-04-19T05:38:08.817 回答