【问题标题】:Node hangs on POST request when using http-proxy and body-parser with express将 http-proxy 和 body-parser 与 express 一起使用时,节点挂起 POST 请求
【发布时间】:2015-04-14 15:54:21
【问题描述】:

我也发布了这个to the relevant issue on http-proxy

我将http-proxyexpress 一起使用,因此我可以拦截客户端和api 之间的请求,以便添加一些cookie 进行身份验证。

为了验证客户端必须发送一个带有x-www-form-urlencoded作为内容类型的POST请求。所以我使用body-parser中间件来解析请求体,这样我就可以在请求中插入数据了。

http-proxy 在使用 body-parser 时遇到问题,据说是因为它将主体解析为流并且从不关闭它,因此代理永远不会完成请求。

There is a solution in the http-proxy examples 在我尝试使用的解析后“重新传输”请求。我也尝试过使用connect-restreamer solution in the same issue,但没有成功。

我的代码是这样的

var express = require('express'),
    bodyParser = require('body-parser'),
    httpProxy = require('http-proxy');

var proxy = httpProxy.createProxyServer({changeOrigin: true});
var restreamer = function (){
  return function (req, res, next) { //restreame
    req.removeAllListeners('data')
    req.removeAllListeners('end')
    next()
    process.nextTick(function () {
      if(req.body) {
        req.emit('data', req.body) //error gets thrown here
      }
      req.emit('end')
    })
  }
}

var app = express();

app.use(bodyParser.urlencoded({extended: false, type: 'application/x-www-form-urlencoded'}));
app.use(restreamer());

app.all("/api/*", function(req, res) {
    //modifying req.body here
    //
    proxy.web(req, res, { target: 'http://urlToServer'});
});

app.listen(8080);

我收到此错误

/Code/project/node_modules/http-proxy/lib/http-proxy/index.js:119
throw err;
      ^
Error: write after end
    at ClientRequest.OutgoingMessage.write (_http_outgoing.js:413:15)
    at IncomingMessage.ondata (_stream_readable.js:540:20)
    at IncomingMessage.emit (events.js:107:17)
    at /Code/project/lib/server.js:46:25
    at process._tickCallback (node.js:355:11)

我已经尝试调试流程,但我正在寻找救命稻草。请问有什么建议吗??

【问题讨论】:

  • 只是想知道为什么不使用 express 中间件而不是 http-proxy?您可以使用中间件拦截/修改所有请求。

标签: javascript node.js express node-http-proxy body-parser


【解决方案1】:

我遇到了这个问题,我无法让重新流式传输正常工作。这是我提出的解决方案,虽然很粗糙,可能不适合您的项目。

我最终将 body-parser 中间件移动到路由本身而不是路由中间件,因为我的项目只有几个路由,并且重置是通过我的 http-proxy 中间件进行的。

所以不要这样:

router.use(bodyParser.json());

router.get('/', function(){...});

router.use(httpProxy());

我这样做了:

router.get('/', bodyParser.json(), function(){...})

router.use(httpProxy())

【讨论】:

  • 这对我有帮助。我在这个问题上被困了将近 2 天。浏览了网络上的多个帖子、博客和文章,但无法解决我的问题。最后我尝试了这个,我看到我的响应从代理服务器返回。谢谢@chrismckenzie
【解决方案2】:

http-proxy-middleware 我也面临同样的问题。在阅读了@ChrisMckenzie 的回答后,我决定简单地将正文解析器中间件移到代理中间件之后。

所以不要这样:

router.use(bodyParser.json());

router.get('/', function(){...});

router.use(httpProxy());

我这样做了:

router.use(httpProxy());

router.use(bodyParser.json());

router.get('/', function(){...});

【讨论】:

    【解决方案3】:

    http-proxy 在处理 POST 正文方面是出了名的糟糕,尤其是在最新版本的 Node 中;和中间件黑客并不总是适用于所有 POST 请求。我建议你使用专门的 http 代理引擎,比如 NGINX 或 HAPROXY 中的那个,效果最好。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-10-14
      • 1970-01-01
      • 1970-01-01
      • 2020-03-02
      • 2015-04-15
      • 1970-01-01
      相关资源
      最近更新 更多