用mongoose和快车处理数据validation的最佳位置

也许这里没有确定的答案,但是我想知道在处理express.js和mongoose时,在哪里处理数据validation。 以下哪一项是最佳做法(我目前正在使用一种组合,开始觉得很笨拙):

  1. 模型(mongoose)
  2. 控制器/路由(快速)

我读过的一些旧post是:

  • 这个 ;
  • 这个 ;
  • 这个 ;

但相互矛盾的答案只会增加混乱。 也许这根本不是明确的削减,在这种情况下是一个更好的select?

当使用mongoose,我会推动我的大部分validation逻辑mongoose模型/架构。 您可以使用mongoose-validator ,它只是节点validation程序的一个包装,用于简单的模型validation。 如果您需要validation其他模型或validation中更复杂的逻辑,您可以编写自己的自定义mongoose预先validation或发布validation挂钩( 请参阅mongoose中间件 )。

当使用mongoose来validation你的模型时,你获得额外的好处是mongoose会为你的模型添加一个错误属性,可以通过model.errors[property]来访问它。 此属性可用于在Web上或为服务客户端validation错误消息。

当编写更多/非常复杂的软件时,将validation与模型绑定可能会成为一个问题。 但是,当它出现时我会处理这个问题。 由于JavaScript具有一等公民的function,即使在这些复杂的情况下,您的validationfunction仍然可以被重用。

mongoosevalidation器是在模型级开始的好地方,但是如果您需要具有控制器特定的validation,则在utils.js文件中使用以下代码:

 var async = require('async') exports.validator = function (reqProps, props, mongoEnt, next) { var propsErr = []; var mongoErr = {}; async.parallel([function (cb) { reqProps.forEach(function (rp) { if (!props[rp])propsErr.push(rp); }) cb() }, function (cb) { if (mongoEnt != null) { var test = new mongoEnt(props); test.validate(function (err) { mongoErr = err; cb(); }); } else { mongoErr = null; cb(); } }], function (err, result) { if (propsErr.length != 0) { return next(new Error('The following props were not included: ' + propsErr)); } else if(mongoErr != null) { return next(new Error('The following prop was not included: ' +mongoErr.errors[Object.keys(mongoErr.errors).pop()].path)); } else { return next(null); } }) } 

这允许我使用mongoosevalidation器进行validation,并检查一行代码中包含在reqProps属性中的附加道具。 虽然这只是检查所需的属性,但您可以轻松地将其扩展为您自己的validationscheme。

此代码的用法示例:

 var Person = mongoose.model('Person') exports.addUSCitizen = function(props, next){ utils.validator(['ssn'], props, Person, function (err) { if(err) return next(err); //do something using props.ssn }) }