Mongodb 使用数组过滤器更新 |写入异常:写入错误:[无法将数组更新应用于非数组元素组:null]

Mongodb update with arrayfilters | write exception: write errors: [Cannot apply array updates to non-array element groups: null]

我有以下 employee 数据结构:

{
   "_id":{
      "$oid":"62836b0b3c1e2c19eaaac07e"
   },
   "firstname":"jean",
   "lastname":"paul",
   "email":"employee@test.co",
   "password":"d94307e0eabb9bba1ea1291e4b043175e11dcc43875a4858690e5c236b989f3e",
   "salt":"2CzpCiIbiyYcSxQ",
   "organizations":[
      {
         "organizationid":{
            "$oid":"62836aa93c1e2c19eaaac07d"
         },
         "organizationname":"test",
         "ismanager":false,
         "groups":[
            {
               "name":"mongroupe",
               "permissions":[
                  0,
                  2
               ]
            }
         ],
         "permissions":[
            1
         ]
      }
   ]
}

我正在尝试在 go 中构建一个向 organizations.[x].groups.[x].permissions 数组添加一组权限的函数。每个 permission 都是一个简单的整数。

我想出了以下代码:


func AddPermissionsToGroup(groupName string, organizationId primitive.ObjectID, permissions []global.Permission) error {
        if res, err := employeesCollection.UpdateMany(
        context.TODO(),
        bson.M{},
        bson.M{
            "$addToSet": bson.M{
                "organizations.$[org].groups.$[grp].permissions": bson.M{
                    "$each": permissions,
                },
            },
        },
        options.Update().SetArrayFilters(
            options.ArrayFilters{
                Filters: []interface{}{
                    bson.M{
                        "org.organizationid": organizationId,
                    },
                    bson.M{
                        "grp.name": groupName,
                    },
                },
            },
        ),
    ); res.MatchedCount == 0 {
        return global.ErrEntityNotFound
    } else if res.ModifiedCount == 0 {
        return global.ErrNoUpdateNeeded
    } else if err != nil {
        return fmt.Errorf("failed updating employees | %s", err.Error())
    }
    return nil

}

代码returns出现以下错误:写入异常:写入错误:[无法将数组更新应用于非数组元素组:空]。

我不知道这是什么意思。

也许引擎不喜欢我使用两个 ArrayFilter 的事实?

好的,所以我创建了这个有效的游乐场:https://mongoplayground.net/p/Tznz7btfLkH

实际上问题不是因为请求本身在语法上是有效的。这是因为我在 employee 集合中有另一个文档,看起来像这样:

{
   "_id":{
      "$oid":"62836aa93c1e2c19eaaac07c"
   },
   "firstname":"jean",
   "lastname":"charles",
   "email":"manager@test.co",
   "password":"6776c354fce809e7be234f84d0ea907cfd3aba350871a18858ceccc10eabc036",
   "salt":"IHaPJIKVVplC8ni",
   "organizations":[
      {
         "organizationid":{
            "$oid":"62836aa93c1e2c19eaaac07d"
         },
         "organizationname":"test",
         "ismanager":true,
         "groups":null,
         "permissions":null
      }
   ]
}

如您所见,此处的 groups 值为空。这就是问题所在。

基本上,当名为 grp 的数组过滤器遇到一个空对象时,它会引发一个错误,因为它不能应用于它。

因此,使请求有效的解决方案是确保集合中的每个文档都初始化了这个 group 数组(即使它是空的,也没关系)。一旦我这样做就没有问题了。