我想使用findAndModify使用Mongoose以原子方式递增字段。
但是,下面的代码会引发错误“TypeError:Object#have method'seadAndModify'”:
// defining schema for the "counters" table
var tableSchema = new Schema({
_id: String,
next: Number
});
// creating table object for the counters table
var counters_table = mongoose.model('counters', tableSchema);
var tableObj = new counters_table();
// increment the "next" field on the table object
var query = {_id: 'messagetransaction'};
var update = {'$inc': {next: 1}};
var ret = tableObj.findAndModify(query, [], update, true, true, function(err) {
if (err) {
throw err;
}
else {
console.log("updated!");
}
});
答案 0 :(得分:61)
该功能记录不完整(阅读:完全记录),但在阅读完源代码后,我想出了以下解决方案。
创建您的收藏架构。
var Counters = new Schema({
_id: String,
next: Number
});
在架构上创建一个静态方法,该方法将公开模型集合的findAndModify方法。
Counters.statics.findAndModify = function (query, sort, doc, options, callback) {
return this.collection.findAndModify(query, sort, doc, options, callback);
};
创建模型。
var Counter = mongoose.model('counters', Counters);
查找并修改
Counter.findAndModify({ _id: 'messagetransaction' }, [], { $inc: { next: 1 } }, {}, function (err, counter) {
if (err) throw err;
console.log('updated, counter is ' + counter.next);
});
<强>加成强>
Counters.statics.increment = function (counter, callback) {
return this.collection.findAndModify({ _id: counter }, [], { $inc: { next: 1 } }, callback);
};
Counter.increment('messagetransaction', callback);
答案 1 :(得分:18)
现在,Mongoose 3.x完全支持此功能,但名称略有不同。
http://mongoosejs.com/docs/api.html#model_Model.findOneAndUpdate
http://mongoosejs.com/docs/api.html#model_Model.findByIdAndUpdate
http://mongoosejs.com/docs/api.html#model_Model.findOneAndRemove
http://mongoosejs.com/docs/api.html#model_Model.findByIdAndRemove
答案 2 :(得分:14)
为Mongoose 3.x制作工作版本增量
var mongoose = require('mongoose');
var CounterSchema = new mongoose.Schema({
_id: String,
next: {type: Number, default: 1}
});
CounterSchema.statics.increment = function (counter, callback) {
return this.findByIdAndUpdate(counter, { $inc: { next: 1 } }, {new: true, upsert: true, select: {next: 1}}, callback);
};
使用类似的东西:
Counter.increment('photo', function (err, result) {
if (err) {
console.error('Counter on photo save error: ' + err); return;
}
photo.cid = result.next;
photo.save();
});
我希望有人派上用场。
答案 3 :(得分:6)
在版本3中,mongoose findOneAndUpdate方法公开了mongodb的findAndModify操作。它的工作原理如下:
var query = { name: 'Sprinkls' };
var update = { name: 'Sprinkles' };
var options = { new: false };
Cat.findOneAndUpdate(query, update, options, function (err, cat) {
if (err) ..
render('cat', cat);
});
此处有更多信息:http://aaronheckmann.tumblr.com/post/48943524629/mongoose-v3-part-2-findandmodify
答案 4 :(得分:3)
我将findAndModify改为
:
var Counters = new Schema({
_id:String, // the schema name
count: Number
});
Counters.statics.findAndModify = function (query, sort, doc, options, callback) {
return this.collection.findAndModify(query, sort, doc, options, callback);
};
var Counter = mongoose.model('Counter', Counters);
/**
* Increments the counter associated with the given schema name.
* @param {string} schemaName The name of the schema for which to
* increment the associated counter.
* @param {function(err, count)} The callback called with the updated
* count (a Number).
*/
function incrementCounter(schemaName, callback){
Counter.findAndModify({ _id: schemaName }, [],
{ $inc: { count: 1 } }, {"new":true, upsert:true}, function (err, result) {
if (err)
callback(err);
else
callback(null, result.count);
});
}
享受! - Curran
答案 5 :(得分:3)
很多答案,但我找到了这个简单的解决方案。
Counter.findByIdAndUpdate(ID, {$inc: {next:1}}, function (err, data) {
});
答案 6 :(得分:1)
从https://jsfiddle.net/Lpjxse6L/获取上述回复,这是我的promised
解决方案:
// eslint-disable-next-line func-names
localeTypesSchema.statics.findAndModify = function (query, sort, update, opts, callback) {
const cb = callback || (() => { });
try {
const result = this.collection.findAndModify(query || {}, sort || [], update || {}, opts);
cb(null, result);
return Promise.resolve(result);
} catch (err) {
cb(err);
return Promise.reject(err);
}
};
答案 7 :(得分:0)
我建议使用http://www.mongodb.org/display/DOCS/findAndModify+Command底部显示的直接命令样式。我对mongoose不太熟悉,不知道运行命令的方法,但所有驱动程序都提供了一些方法。如果mongoose没有,你可以使用http://www.mongodb.org/display/DOCS/Commands顶部描述的样式直接进行。
那就是说,你应该确保你真的需要findAndModify
而且update
不会做你需要它做的事情。要查看update
能够查看http://www.mongodb.org/display/DOCS/Updating的内容。
答案 8 :(得分:0)
只是添加到furf回答如果你在查询中使用objectId,mongoDB将无法找到你的文档。猫鼬层负责将你从路由参数获得的十六进制字符串对象id转换为正确的对象id。
要解决此问题,您需要:
var ObjectID = require('mongodb').ObjectID;
var itemId = req.params.itemId;
var objectId = ObjectID.createFromHexString(itemId);
Item.findAndModify({_id: objectId},