2013-11-04 56 views
2

我对express.urlencoded()中间件生成的request.body有点问题。在某些情况下,在request.body对象的末尾添加__proto__和比它不能直接用于启动moongose模型,像这样var user = new User(req.body)Express.js请求正文__proto__

作为一个例子,我将使用node-express-mongoose-demo库。所有形式的工作得很好,但app.post('/users', users.create)临危req.body“污染”与__proto__

预先感谢任何帮助

回答

0

嗯,这很有趣。 __proto__是一些javascript实现(包括node/v8)中所有对象的特殊/自动/内部属性。虽然我没有见过猫鼬做这种事。将传递给模型构造函数的属性转换为模型/文档实例is here的代码。虽然我没有看到任何可疑的东西。

你知道究竟发生了哪种情况,你确定它是urlencoded吗?当您尝试保存已被此“污染”的用户时会发生什么?通常猫鼬会忽略模式中未定义的字段,那么会发生什么?

你应该能够(也许?)用下面的中间件解决这个问题,但我很好奇,要真正隔离和理解根本原因。下划线/ lodash有omit这在这里运作良好。

var _ = require('lodash'); 

function unpollute(req, res, next) { 
    req.body = _.omit(req.body, '__proto__'); 
    next(); 
} 
app.use(express.urlencoded()); 
app.use(unpollute); 

然后运行你的路由处理时,req.body不会有__proto__

+0

这种解决方法可以像以下那样重新创建正文对象:'var fields = Object.create(req.body)'但是您是否真的知道为什么有时会添加__proto__并且有时不会? –

+0

我在创建对象时没有看到任何奇怪的东西,所以我不确定'req.body.proto'来自哪里,但是您的应用中可能还有其他一些中间件是在污染它? https://github.com/senchalabs/connect/blob/7edb875a9f305e38f4d960fa46ac674038241892/lib/middleware/urlencoded.js#L47 –

+0

我发现'__proto__'没有添加,当窗体有属性'enctype =“multipart/form-数据“'。所以多部分中间件不会产生额外的密钥。 –

2

看来问题来自urlencoded中间件,它包含在Express 3中。

可能的解决方案不是使用Express bodyParser,而是使用body-parser模块。

而不是

app.use(express.urlencoded()) 

你可以写

var bodyparser = require('body-parser') 

.......... 

app.use(bodyparser.urlencoded()) 

这个问题似乎来自qs模块(由express 3模块使用的版本)。它强制在其构建的对象上添加一个__proto__。最后的版本没有这个问题。