使用await保存时,猫鼬后钩悬而未决

问题描述 投票:0回答:1

我正在创建一个帖子挂钩,以在保存帖子后创建一个 slug。当我尝试使用 Postman 检查结果时,该过程陷入困境(未返回任何数据)。我正在使用 [电子邮件受保护]

后挂钩代码:

PostsSchema.post("save", async function (doc, next) {
  try {
    doc.postSlug = slugify(doc.postTitle, { lower: true });
    await doc.save();
    return next();
  } catch (err) {
    console.log("inside catch method");
    return next(createError(500, err.message));
  }
});

我使用的路线代码:

module.exports.createPost = async (req, res, next) => {
  const { postTitle, postContent, postAuthor } = req.body;
  try {
    // check if author exist
    const authorExist = await AccountsModel.findById(postAuthor);
    if (!authorExist) {
      return next(createError(404, `Author ID: ${postAuthor} Not Found`));
    }
    // create post
    console.log("route 1")
    const postNew = new PostsModel({
      postTitle: postTitle,
      postContent: postContent,
      postAuthor: postAuthor,
    });
    await postNew.save();
    // populate data for return
    let postCreated = await postNew.populate("postAuthor");
    return res.status(200).json({
      code: 1,
      success: true,
      message: "New Post Created",
      data: postCreated,
    });
  } catch (error) {
    return next(createError(500, error.message));
  }
};

我确实通过删除

await
前面的
doc.save()
来修复此问题:

PostsSchema.post("save", async function (doc, next) {
  try {
    doc.postSlug = slugify(doc.postTitle, { lower: true });
    doc.save();
    return next();
  } catch (err) {
    console.log("inside catch method");
    return next(createError(500, err.message));
  }
});

此外,使用

.then()
也会返回结果:

PostsSchema.post("save", async function (doc, next) {
  doc.postSlug = slugify(doc.postTitle, { lower: true });
  console.log(1);
  doc
    .save()
    .then(() => {
      console.log(2);
      return next();
    })
    .catch((error) => {
      return next(createError(500, err.message));
    });
});

但发现其他一些帖子有等待,答案表明这不是问题:

所以,我想知道是等待破坏了进程还是其他原因?

javascript node.js mongoose mongoose-schema
1个回答
0
投票

我发现了问题,当我在你的帖子挂钩中

console.log(1)
时,它会创建一个无限循环。根据帖子Mongoose post save hook 1下的评论,更新文档,post hook在执行
.save()
后执行;在你的 post hook 中,你执行另一个
.save()
再次调用你的 post hook,创建一个无限循环。

你的

await doc.save()
不起作用,因为它正在等待无限循环完成。这就是为什么邮递员没有回复,它从未到达
return next()

您的

doc.save()
“有效”,因为
.save()
是异步的,在完成之前它已经返回
next()
,这就是为什么有一个值返回给邮递员而代码保持在无限循环中。

您的

doc.save().then()
“有效”,因为
.then()
解析了您的
.save()
并到达
return next()
,但它再次调用 post 挂钩,从而创建无限循环。

我建议更改 hook 中的关键字 pass 或更改为 pre hook:

PostsSchema.pre('save', function(next) {
    if (this.isNew || this.isModified('PostTitle')) {
        this.slug = slugify(this.PostTitle, { lower: true });
    }
    return next();
});

此预挂钩在实际

save()
操作之前运行,因此保存后不会再次调用此挂钩。

© www.soinside.com 2019 - 2024. All rights reserved.