删除Mongoose中的多对多引用

sms*_*omb 10 many-to-many mongoose mongodb nosql node.js

我的一个mongoose模式是多对多的关系:

var UserSchema = new Schema({
   name       : String,
   groups  : [ {type : mongoose.Schema.ObjectId, ref : 'Group'} ]
});

var GroupSchema = new Schema({
   name       : String,
   users  : [ {type : mongoose.Schema.ObjectId, ref : 'User'} ]
});
Run Code Online (Sandbox Code Playgroud)

如果我删除一个组,无论如何都要从所有用户的'groups'数组中删除该组objectId?

GroupSchema.pre('remove', function(next){
    //Remove group._id from all the users
})
Run Code Online (Sandbox Code Playgroud)

Joh*_*yHK 17

您正准备使用'remove'中间件来实现此目的.在中间件功能中,this是要删除组实例,您可以通过其model方法访问其他模型.所以你可以这样做:

GroupSchema.pre('remove', function(next){
    this.model('User').update(
        {_id: {$in: this.users}}, 
        {$pull: {groups: this._id}}, 
        {multi: true},
        next
    );
});
Run Code Online (Sandbox Code Playgroud)

或者,如果您希望支持users组实例中的字段可能不完整的情况,您可以执行以下操作:

GroupSchema.pre('remove', function(next){
    this.model('User').update(
        {groups: this._id}, 
        {$pull: {groups: this._id}}, 
        {multi: true},
        next
    );
});
Run Code Online (Sandbox Code Playgroud)

但正如WiredPrairie指出的那样,对于这个选项,你需要一个索引groups才能获得良好的性能.

  • 如果`groups`没有编入索引,你将强制进行全表扫描和用户阵列扫描. (3认同)