源代码如下:使用方法 createProxyServer
创建一个代理服务器, 监听在端口 8082 上,把请求发送给 localhost:9000 上监听的服务器。
后者仅仅返回一个 request successfully proxied 的消息给请求方。
var http = require('http'), httpProxy = require('http-proxy'); httpProxy.createProxyServer({target:'http://localhost:9000'}).listen(8082); http.createServer(function (req, res) { res.writeHead(200, { 'Content-Type': 'text/plain' }); res.write('request successfully proxied!' + '\n' + JSON.stringify(req.headers, true, 2)); res.end(); }).listen(9000);
遇到错误消息:
Access to XMLHttpRequest at ‘http://localhost:8082/https://services.odata.org/V2/Northwind/Northwind.svc/$metadata?sap-language=EN’ from origin ‘http://localhost:8080’ has been blocked by CORS policy: Response to preflight request doesn’t pass access control check: No ‘Access-Control-Allow-Origin’ header is present on the requested resource.
解决方案
在 HTTP response 头部字段增添一条字段:“Access-Control-Allow-Origin”: “*”
重启 proxy 服务器之后,错误消息变成了:
Access to XMLHttpRequest at ‘http://localhost:8082/https://services.odata.org/V2/Northwind/Northwind.svc/$metadata?sap-language=EN’ from origin ‘http://localhost:8080’ has been blocked by CORS policy: Request header field maxdataserviceversion is not allowed by Access-Control-Allow-Headers in preflight response.
解决办法是,在 response 里添加如下字段:
res.writeHead(200, { 'Content-Type': 'text/plain', "Access-Control-Allow-Origin": "*", "Access-Control-Allow-Headers": "*" });
修改之后问题消失:
SAP UI5 应用发起的 metadata 数据请求,被 proxy 服务器成功拦截并返回:
Error [ERR_TLS_CERT_ALTNAME_INVALID]: Hostname/IP does not match certificate’s altnames: Host: localhost. is not in the cert’s altnames: DNS:.azurewebsites.net, DNS:.scm.azurewebsites.net, DNS:.azure-mobile.net, DNS:.scm.azure-mobile.net, DNS:.sso.azurewebsites.net
at Object.checkServerIdentity (tls.js:287:12)
at TLSSocket.onConnectSecure (_tls_wrap.js:1511:27)
at TLSSocket.emit (events.js:315:20)
at TLSSocket._finishInit (_tls_wrap.js:936:8)
at TLSWrap.ssl.onhandshakedone (_tls_wrap.js:710:12) {
reason: "Host: localhost. is not in the cert’s altnames: DNS:.azurewebsites.net, DNS:.scm.azurewebsites.net, DNS:.azure-mobile.net, DNS:.scm.azure-mobile.net, DNS:.sso.azurewebsites.net",
host: ‘localhost’,
这个错误和这个 StackOverflow 讨论相关。
代码也类似:
var express = require('express'); var app = express(); var httpProxy = require('http-proxy'); var apiProxy = httpProxy.createProxyServer(); var serverOne = 'https://idena.navarra.es/ogc/wms?'; app.all('/idena', function (req, res) { apiProxy.web(req, res, {target: serverOne}); }); app.listen(3000, function () { console.log('Working!'); });
当请求发送给 idena 时,代理服务器试图发送往服务器:https://idena.navarra.es/ogc/wms?
源服务器是 HTTP,而目的服务器是 HTTPS.
解决这个错误的办法:在 proxy option 里,指定下列这个选项:
changeOrigin: true
重新 proxy 服务器之后,问题消失:ERR_TLS_CERT_ALTNAME_INVALID
错误被修复了。
但是这个错误消息又回来了:
http://localhost:8082/https://services.odata.org/V2/Northwind/Northwind.svc/$metadata?sap-language=EN’ from origin ‘http://localhost:8080’ has been blocked by CORS policy: Response to preflight request doesn’t pass access control check: No ‘Access-Control-Allow-Origin’ header is present on the requested resource.
400 bad request:
直接访问这个 url:http://localhost:8082/https://services.odata.org/V2/Northwind/Northwind.svc/$metadata?sap-language=EN
会遇到如下错误: