2

我想创建一个索引,以确保我在+serialNr的组合中没有重复。但有些项目没有. 这些我不想检查/索引。 manufacturerartserialNr

代码

mySchema.index({ serialNr: 1, art: 1 , manufacturer: 1, deleted: 1}, { unique: true, sparse: true)

我也尝试过 partialFilterExpression: { serialNr: {$ne:null} }在索引选项中添加部分过滤器:。

问题

我怎样才能索引它插入: [{art: 'a', manufacturer:'a', deleted:null}, {art: 'a', manufacturer:'a', deleted:null}]通过

[{serialNr: '123', art: 'a', manufacturer:'a', deleted:null}, {serialNr: '123', art: 'a', manufacturer:'a', deleted:null}]失败

我不想保存: [{serialNr: null, art: 'a', manufacturer:'a', deleted:null}, {serialNr: null, art: 'a', manufacturer:'a', deleted:null}]


mongo 文档指出,如果复合索引中缺少字段,则不应对其进行索引:

稀疏索引仅根据索引字段的存在来选择要索引的文档,或者对于复合索引,索引字段的存在。 https://docs.mongodb.org/manual/core/index-partial/

编辑:

新指数

implantSchema.index({ serialNr: 1, art: 1 , manufacturer: 1, deleted: 1}, { unique: true, partialFilterExpression: { serialNr: {$exists:true} }})

在对索引进行更改之前,我将我的索引collection放入我的开发数据库中,以确保不存在旧索引。这是返回的新索引db.items.getIndexes()

/* 0 */
{
    "0": {
        "v" : 1,
        "key" : {
            "_id" : 1
        },
        "name" : "_id_",
        "ns" : "LOC_db.items"
    },
    "1": {
        "v" : 1,
        "unique" : true,
        "key" : {
            "serialNr" : 1,
            "art" : 1,
            "manufacturer" : 1,
            "deleted" : 1
        },
        "name" : "serialNr_1_art_1_manufacturer_1_deleted_1",
        "ns" : "LOC_db.items",
        "partialFilterExpression" : {
            "serialNr" : {
                "$exists" : true
            }
        },
        "background" : true
    }
}

数据

  • 我有一个预保存挂钩,我在其中检查 的值serialNr,该值以前不存在,然后dup error返回。
  • 查询数据库时,不doc存在具有null""作为 的值serialNr
  • 查询db.items.find({ serialNr: {$exists:true} })不匹配任何项目。

错误

insertDocument :: caused by :: 11000 E11000 duplicate key error index: LOC_db.items.$serialNr_1_art_1_manufacturer_1_deleted_1 dup key: { : null, : "Robo", : "Olymp", : null }

附加信息

也许错误与: https ://github.com/Automattic/mongoose/issues/2457有关

4

1 回答 1

4

您实际上非常接近解决方案,在创建 index 时您需要使用它:

partialFilterExpression: { serialNr: {$exists:true} }

确保至少有 3.2 版本的 mongo


例子 :

db.col.createIndex({a:1, b:1},{unique:true, partialFilterExpression: { a: {$exists:true} })
db.col.save({a:50, b:27}) //pass
db.col.save({a:50, b:27}) //fails
db.col.save({b:27}) //pass
db.col.save({b:27}) //pass
db.col.save({b:27}) //pass
db.col.save({a:50, b:27}) //fails
db.col.save({a:50}) //pass
db.col.save({a:50}) //fails

PS:也许你可以做一点“hack”并使用它:partialFilterExpression: { serialNr: {$exists:true}, serialNr: {$gte:0} }

我尝试使用 $ne,但它给我一个错误。

于 2016-03-10T16:33:24.803 回答