ExpressJs - Mongoose:删除具有多对多关系的文档

ExpressJs - Mongoose: Delete documents with Many To Many relationship

我有两个模型,Post 和具有多对多关系的标签。

Post 架构:

const postSchema = new Schema(
  {
    user: {
      type: Schema.Types.ObjectId,
      ref: 'User',
      required: [true, 'A post must belong to a user.'],
    },
    title: {
      type: String,
      unique: [true, 'A Post already exists with this title.'],
      required: [true, 'A Post must have a title.'],
    },
    slug: { type: String, unique: true },
    body: { type: String, required: [true, 'A Post must have a body.'] },
    coverImage: String,
    images: Array,
    isDraft: { type: Boolean, default: false },
    isPublished: { type: Boolean, default: false },
    tags: [{ type: Schema.Types.ObjectId, ref: 'Tag' }],
  },
  {
    timestamps: { currentTime: () => Math.floor(Date.now() / 1000) },
    toJSON: { virtuals: true },
    toObject: { virtuals: true },
  }
)

标记架构:

const tagSchema = new Schema(
  {
    title: { type: String, required: true },
    slug: { type: String },
    posts: [{ type: Schema.Types.ObjectId, ref: 'Post' }],
  },
  {
    timestamps: { currentTime: () => Math.floor(Date.now() / 1000) },
    toJSON: { virtuals: true },
    toObject: { virtuals: true },
  }
)

现在我想在删除 Post 时从标记文档中删除对 Post 的所有引用。

我正在尝试 Post 模型中的以下 remove 中间件,但它不起作用。 post 被删除,但标签文档中的引用仍然存在。

postSchema.pre('remove', function (next) {
  var post = this
  post
    .model('Tag')
    .update(
      { posts: { $in: post.tags } },
      { $pull: { posts: post._id } },
      { multi: true },
      next
    )
})

经过多次尝试,我终于解决了我做错了什么。按照我为使其工作而进行的修复:

在 Post 控制器中,我之前是这样做的:

const post = await Post.findByIdAndDelete(req.params.id)

我改成了:

const post = await Post.findById(req.params.id)
await post.remove()

并且在 Post 型号中:

postSchema.pre('remove', async function (next) {
  await this.model('Tag').updateMany(
    { posts: this._id },
    { $pull: { posts: this._id } },
    { multi: true },
    next
  )
})