2

我正在尝试从我的 Firebase 函数向需要证书 (.pfx) 的自定义服务器发出请求。基于这个答案:

将 TLS 客户端证书上传到 Firebase 云函数

我的代码如下:

const functions = require('firebase-functions');
const request = require('request');

var fs = require('fs');

// The Firebase Admin SDK to access the Firebase Realtime Database.
const admin = require('firebase-admin');
admin.initializeApp();

exports.postBankId = functions.https.onRequest(async (req, res) => {
  console.log('PostBankId');
  const ipAddress = req.query.ipAddress;
  const requestBody = '{ "endUserIp": "' + ipAddress +'" }';
  console.log('requestBody:', requestBody); 
  const options = {
      url: 'https://appapi2.test.bankid.com/rp/v5/auth',
      json: true,
      pfx: fs.readFileSync('bankidtest.pfx'),
      passphrase: 'myPassPhraseHere',
      body: requestBody
  }

  request.post(options, (err, response) => {
      if (err) {
            console.log('bankid creation error: ' + JSON.stringify(err))
            res.status(500).send('Failed with error: ' + JSON.stringify(err));
      }
      if (response) {
          res.status(200).send('Success');
          console.log('Succes body: ' + response.body)
      }
  });
});

我得到的答案:

{"code":"UNABLE_TO_VERIFY_LEAF_SIGNATURE"}

我将 bankidtest.pfx 放在与 index.js 相同的文件夹中。它似乎已上传,因为如果删除它会产生另一个错误:

Error: could not handle the request

编辑1:

将证书的路径放在 agentOptions 中也不起作用。给出同样UNABLE_TO_VERIFY_LEAF_SIGNATURE的错误。

var options = {
    url: 'https://appapi2.test.bankid.com/rp/v5/auth',
    headers: {
        "content-type": "application/json",
    },
    agentOptions: {
        pfx: fs.readFileSync('bankidtest.pfx'),
        passphrase: '********'
    }
};

编辑2: 得到它半工作。将请求参数“rejectUnauthorized”设置为“false”,使请求生效。但根据 BankId,这不是安全或推荐的方式。半工作代码是:

  request({
    url: "https://appapi2.test.bankid.com/rp/v5/auth",
    host: "appapi2.test.bankid.com",
    rejectUnauthorized: false, // This like makes it work
    requestCert: true,
    method: "POST",
    headers: {
        "content-type": "application/json", 
        'Connection': "Keep-Alive"
    },

    body: requestBody,
    agentOptions: {
        pfx: fs.readFileSync('bankidtest.pfx'),
        passphrase: '*****'
    },

Edit3: 尝试npm install ssl-root-cas然后将其添加到我的 index.js 的顶部:

var sslRootCAs = require('ssl-root-cas/latest')
sslRootCAs.inject()

但后来我得到了这个错误:

Error: EROFS: read-only file system, open '/srv/node_modules/ssl-root-cas/pems/mozilla-certdata.txt'
   at Object.fs.openSync (fs.js:646:18)
   at Object.fs.writeFileSync (fs.js:1299:33)
   at /srv/node_modules/ssl-root-cas/ca-store-generator.js:219:10
   at IncomingMessage.<anonymous> 
     (/srv/node_modules/@coolaj86/urequest/index.js:154:9)

Edit4: 尝试使用这些来代替,inject()但没有成功。这次没有只读错误,但仍然UNABLE_TO_VERIFY_LEAF_SIGNATURE

var rootCas = require('ssl-root-cas/latest').create();

//rootCas.addFile(__dirname + '/mycerts.crt');
rootCas.addFile('mycerts.cer');
rootCas.addFile('mycerts.crt');
rootCas.addFile('bankidtest.pfx'); // Also tried with __dirname

require('https').globalAgent.options.ca = rootCas;

// Also tried this:
//require('https').globalAgent.options.ca = require('ssl-root-cas').rootCas

Edit5解决了

似乎需要一个不是从 pfx 文件派生的 CA。

4

1 回答 1

1

Bank-ID 在其文档中提供了 CA 作为文本。从“-----BEGIN CERTIFICATE”开始...我将文本复制到一个 pem 文件中,并从我的 index.js 文件中引用它,如下所示:

agentOptions: {
    pfx: fs.readFileSync('bankidtest.pfx'),
    passphrase: '*****',
    ca: fs.readFileSync('certificate.pem')
},
于 2020-03-13T16:39:12.760 回答