增加猫鼬数字字段的优雅方式

时间:2015-03-09 17:53:18

标签: node.js mongodb mongoose

增加猫鼬数字字段的最优雅方法是什么?

var Book = new Schema({
   name: String,
   total: Number
})

如何在API中增加它?

var book = new Book({
   name: req.body.name,
   total: ?
});

book.save(callback);

1 个答案:

答案 0 :(得分:3)

您可以编写一个mongoose插件来拦截保存调用并从计数器集合中返回当前计数器。

猫鼬插件

var mongoose = require('mongoose');
var Schema = mongoose.Schema;

module.exports = function(schema, options) {
    var options = options || {};
    options.name = options.name || 'generic';
    options.field = options.field || 'counter';

    var counterSchema = new Schema({ name : String, counter : Number });
    var CounterModel = mongoose.model('counters', counterSchema);

    schema.pre('save', function (next) {
        if (!this.isNew) {
            return next();
        }

        var self = this;

        CounterModel.findOneAndUpdate(
            { name : options.name }, 
            { 
                $inc : { counter : 1 }
            },
            { upsert : true }, function(err, counter) {
                if (err) { return next(err) };

                self.set(options.field, counter.counter);

                next();
        });
    });
}

此插件知道在名为counters的集合中保留多个命名计数器。

使用mongoose插件

var mongoose = require('mongoose');
var Schema = mongoose.Schema;
var counter = require('./plugin');

var TestSchema = new Schema({ counter : Number });
TestSchema.plugin(counter, { name : 'tests', counter : 'counter' });

var TestModel = mongoose.model('tests', TestSchema);

mongoose.connect('mongodb://localhost', function(err) {
    TestModel.create({}, function(err, test) {
        console.log(err, test);

        test.save(function(err, test) {
            console.log(err, test);
        });
    }); 
});