在填充猫鼬之前,按对象ID数组中的ID进行过滤

时间:2020-04-07 17:45:50

标签: mongodb mongoose

我有这样的帖子架构

const postSchema = new mongoose.Schema({
  title: { type: String, minlength: 2 },
  description: { type: String },
  categoryId: [{ type: mongoose.Schema.ObjectId, ref: "category" }],
});

我必须从帖子中获取随机文档,并填充其中的所有类别。到目前为止,我所取得的成就是

await Post.aggregate([
      {
        $lookup: {
          from: "categories",
          localField: "categoryId",
          foreignField: "_id",
          as: "categoryId",
        },
      },
    ]).sample(5)

需要做

假设我在变量 catId 中具有类别的 id ,我需要做的是过滤掉包含以下内容的帖子在获得这些随机帖子之前,将其 id 放入其categoryId数组中。通过过滤掉,我的意思是我需要在其数组中具有 catId 的随机帖子。

1 个答案:

答案 0 :(得分:1)

您可以按照以下步骤进行操作:

Post.aggregate([
  /** Use match to Get docs where 'categoryId' has passed in value */
  {
    $match: {
      categoryId: catId /** Input 'catId', make sure you convert input request of string to 'ObjectId()' to match with type in DB*/
    }
  },
  {
    $sample: { /** Picks some random 3 docs (Sometimes a single doc can be repeated) */
      size: 3
    }
  },
  {
    $lookup: {
      from: "categories",
      localField: "categoryId",
      foreignField: "_id",
      as: "categoryId"
    }
  }
])

测试: MongoDB-Playground

参考: $sample

注意:因此,$sample可以完成工作,但是通过阅读文档了解更多信息的限制很小。使用$explain检查您的查询是否运行良好,无论如何$sample都不适合您,那么您实际上可以使用$skip$limit来获取这项工作完成了。

让我们说一下,如果您可以为skip自动生成至少比集合大小小3的数字,并跳过这些文档,最终对其余文档进行limit的{​​{1}}处理。您可以在3skip之间进行排序-可以通过这种方式对其进行更好的唯一性测试。检查以下内容:skip-and-limit-in-aggregation-framework-通常用于分页,但至少在某些情况下可能对您有帮助。