节点 js 错误: 不支持协议“ https:”

我正在使用 IBMBluemix 为一个学校项目开发 Web 服务。

我的项目需要从 API 请求 JSON,这样我就可以使用它提供的数据。我对数据集使用 http get方法,我不确定它是否正常工作。

当我运行我的代码时,我得到的消息是:

错误: 不支持协议“ https:”

是什么原因造成的? 我怎样才能解决这个问题?

这是我的 .js文件:

// Hello.
//
// This is JSHint, a tool that helps to detect errors and potential
// problems in your JavaScript code.
//
// To start, simply enter some JavaScript anywhere on this page. Your
// report will appear on the right side.
//
// Additionally, you can toggle specific options in the Configure
// menu.


function main() {
return 'Hello, World!';
}


main();/*eslint-env node*/


//------------------------------------------------------------------------------
// node.js starter application for Bluemix
//------------------------------------------------------------------------------


// HTTP request - duas alternativas
var http = require('http');
var request = require('request');


// cfenv provides access to your Cloud Foundry environment
// for more info, see: https://www.npmjs.com/package/cfenv
var cfenv = require('cfenv');


//chama o express, que abre o servidor
var express = require('express');


// create a new express server
var app = express();


// serve the files out of ./public as our main files
app.use(express.static(__dirname + '/public'));


// get the app environment from Cloud Foundry
var appEnv = cfenv.getAppEnv();


// start server on the specified port and binding host
app.listen(appEnv.port, '0.0.0.0', function() {
// print a message when the server starts listening
console.log("server starting on " + appEnv.url);
});




app.get('/home1', function (req,res) {
http.get('http://developers.agenciaideias.com.br/cotacoes/json', function (res2) {
var body = '';
res2.on('data', function (chunk) {
body += chunk;
});
res2.on('end', function () {
var json = JSON.parse(body);
var CotacaoDolar = json["dolar"]["cotacao"];
var VariacaoDolar = json["dolar"]["variacao"];
var CotacaoEuro = json["euro"]["cotacao"];
var VariacaoEuro = json["euro"]["variacao"];
var Atualizacao = json["atualizacao"];


obj=req.query;


DolarUsuario=obj['dolar'];
RealUsuario=Number(obj['dolar'])*CotacaoDolar;


EuroUsuario=obj['euro'];
RealUsuario2=Number(obj['euro'])*CotacaoEuro;


Oi=1*VariacaoDolar;
Oi2=1*VariacaoEuro;


if (VariacaoDolar<0) {
recomend= "Recomenda-se, portanto, comprar dólares.";
}


else if (VariacaoDolar=0){
recomend="";
}


else {
recomend="Recomenda-se, portanto, vender dólares.";
}


if (VariacaoEuro<0) {
recomend2= "Recomenda-se, portanto, comprar euros.";
}


else if (VariacaoEuro=0){
recomend2="";
}
else {
recomend2="Recomenda-se,portanto, vender euros.";
}


res.render('cotacao_response.jade', {
'CotacaoDolar':CotacaoDolar,
'VariacaoDolar':VariacaoDolar,
'Atualizacao':Atualizacao,
'RealUsuario':RealUsuario,
'DolarUsuario':DolarUsuario,
'CotacaoEuro':CotacaoEuro,
'VariacaoEuro':VariacaoEuro,
'RealUsuario2':RealUsuario2,
'recomend':recomend,
'recomend2':recomend2,
'Oi':Oi,
'Oi2':Oi2
});


app.get('/home2', function (req,res) {
http.get('https://www.quandl.com/api/v3/datasets/BCB/432.json?api_key=d1HxqKq2esLRKDmZSHR2', function (res3) {
var body = '';
res3.on('data', function (chunk) {
body += chunk;
});
res3.on('end', function () {
var x=json.dataset.data[0][1];
console.log("My JSON is "+x); });


});
});
});
});
});

下面是我得到的错误屏幕:enter image description here

102564 次浏览

When you want to request an https resource, you need to use https.get, not http.get.

https://nodejs.org/api/https.html

As a side note to anyone looking for a solution from Google... make sure you are not using an http.Agent with an https request or you will get this error.

The reason for this error is that you are trying to call a HTTPS URI from a HTTP client. The ideal solution would have been for a generic module to figure out the URI protocol and take the decision to use HTTPS or HTTP internally.

The way I overcame this problem is by using the switching logic on my own. Below is some code which did the switching for me.

    var http = require('http');
var https = require('https');
// Setting http to be the default client to retrieve the URI.
var url = new URL("https://www.google.com")
var client = http; /* default  client */
// You can use url.protocol as well
/*if (url.toString().indexOf("https") === 0){
client = https;
}*/
/* Enhancement : using the  URL.protocol  parameter
* the  URL  object ,  provides a  parameter url.protocol that gives you
* the protocol  value  ( determined  by the  protocol ID  before
* the ":" in the  url.
* This makes it easier to  determine the protocol, and to  support other
* protocols like ftp ,  file  etc)
*/
client = (url.protocol == "https:") ? https : client;
// Now the client is loaded with the correct Client to retrieve the URI.
var req = client.get(url, function(res){
// Do what you wanted to do with the response 'res'.
console.log(res);
});

Not sure why, but the issue for me happened after updating node to version 17, i was previously using version 12.

In my setup, i have node-fetch using HttpsProxyAgent as an agent in the options object.

options['agent'] = new HttpsProxyAgent(`http://${process.env.AWS_HTTP_PROXY}`)
response = await fetch(url, options)

Switching back to node 12 fixed the problem:

nvm use 12.18.3

I got this error while deploying the code.

INFO    error=> TypeError [ERR_INVALID_PROTOCOL]: Protocol "https:" not supported. Expected "http:"
at new NodeError (node:internal/errors:372:5)

To fix this issue, I have updated the "https-proxy-agent" package version to "^5.0.0"

Now the error was gone and it's working for me.