Node.js 猫鼬嵌套(2级)查找

Node.js 猫鼬嵌套(2级)查找,node.js,mongodb,mongoose,mongoose-schema,casl,Node.js,Mongodb,Mongoose,Mongoose Schema,Casl,我正在尝试使用CASL对嵌套项进行授权检查。 它使用mongoose来查询数据和检查访问 我的领域是: “用户”可以拥有更多的“车辆” “文件”必须有车辆 模式: vehicle { users: [ {type: objectId, ref: 'user'} ] } document { vehicle: {type: objectId, ref: 'vehicle' }} 要“按用户”查找车辆,我需要: 这很有效 在文档集合中,数据具有以下记录: { "_id": Object

我正在尝试使用CASL对嵌套项进行授权检查。 它使用mongoose来查询数据和检查访问

我的领域是:

  • “用户”可以拥有更多的“车辆”
  • “文件”必须有车辆
模式:

vehicle { users: [ {type: objectId, ref: 'user'} ] }
document { vehicle: {type: objectId, ref: 'vehicle' }}
要“按用户”查找车辆,我需要:

这很有效

在文档集合中,数据具有以下记录:

{
    "_id": ObjectId("5aeaad1277e8a6009842564d"),
    "vehicle": ObjectId("5aea338b82d8170096b52ce9"),
    "company": "Allianz",
    "price": 500,
    "date_start": ISODate("2018-05-02T22:00:00.000Z"),
    "date_end": ISODate("2019-05-02T22:00:00.000Z"),
    "createdAt": ISODate("2018-05-03T06:32:50.590Z"),
    "updatedAt": ISODate("2018-05-03T06:32:50.590Z"),
    "__v": 0
}
要“按用户”查找文档,我需要:


它不起作用。是否可以在一个“查找”查询中执行此操作?

您不能在简单的MongoDB中执行此操作,因为有关车辆用户的数据存在于车辆集合中,而不是文档集合中

但是,可以使用运算符链接两个不同集合中的数据。聚合如下所示:

db.document.aggregate([
{$lookup:{
“发件人”:“车辆”,
“localField”:“vehicle”,
“外域”:“\u id”,
“as”:“车辆详情”,
}},
{$match:{“vehicleDetails.users”:ObjectId(“5ae1a957d67500018efa2c9d”)}
])

您可能需要添加更多的阶段,以按照您需要的方式重塑数据,但关键是使用$lookup链接来自两个集合的数据,然后使用筛选结果集。

为了使此查询正常工作,您需要将
用户
ID数组存储在
车辆
文档中。Mongo和CASL都不会自动管理外部引用

替代解决方案

因此,我认为有几种方法:

  • 定义规则时检索所有车辆的ID。如果车辆数量不大({ const vehicle=wait vehicle.findById(请求参数id) 要求通过无扫描(“读取”,车辆)的能力 const documents=Document.find({vehicle:vehicle.id}) res.send({documents}) })
    Hi Adriano;您能在第二次查询中再次检查集合名称吗?您说要查询文档,但它再次显示
    getCollection('vehicles')
    。看起来你不小心查询了错误的收藏。是的,很抱歉我修复了我的帖子正文。我正在查询结果为0的文档。好的,这就清楚了。我还有另一个问题:你能粘贴一个文档记录的例子吗?它应该通过你的查询返回?{“\u id”:ObjectId(“5aeaad1277e8a6009842564d”),“vehicle”:ObjectId(“5aea338b82d8170096b52ce9”),“company”:“安联”,“price”:500,“date\u start”:ISODate(“2018-05-02T22:00:00.000Z”),“date\u end”:ISODate(“2019-05-02T22:00:00.000Z”),“createdAt”:ISODate(“2018-05-03T06:32:50.590Z”),“updatedAt”:ISODate(“2018-05-03T06:32:50.590Z”),“_uv”:0}我真的不需要这些数据。我只需检查是否存在一个文档,该文档是否“通过”车辆与用户相关。要了解此查询的用法,可以查看其中的示例
    {
        "_id": ObjectId("5aeaad1277e8a6009842564d"),
        "vehicle": ObjectId("5aea338b82d8170096b52ce9"),
        "company": "Allianz",
        "price": 500,
        "date_start": ISODate("2018-05-02T22:00:00.000Z"),
        "date_end": ISODate("2019-05-02T22:00:00.000Z"),
        "createdAt": ISODate("2018-05-03T06:32:50.590Z"),
        "updatedAt": ISODate("2018-05-03T06:32:50.590Z"),
        "__v": 0
    }
    
    db.getCollection('document').find(
        { "vehicle.users": {$in: [ ObjectId("5ae1a957d67500018efa2c9d") ]} }
    )
    
    vehicle {
      documents: [Document],
      users: [ {type: objectId, ref: 'user'} ]
    }