在 Mongoose 中为对象数组创建索引

Posted

技术标签:

【中文标题】在 Mongoose 中为对象数组创建索引【英文标题】:Create index in Mongoose for array of objects 【发布时间】:2017-10-15 00:36:45 【问题描述】:

我有两个模型设置:

ShopsModel

var ShopsSchema = new mongoose.Schema(
  name: 
    type: String,
    required: true
  
);

var ShopsModel = mongoose.model("Shops", ShopsSchema);

字段组模型

var FieldGroupsSchema = new mongoose.Schema(
  title: 
    type: String,
    required: true
  ,
  fields: [
    label: 
      type: String,
      required: true
    ,
    handle: 
      type: String,
      required: true
    
  ],
  shop: 
    type: mongoose.Schema.Types.ObjectId,
    ref: "Shops"
  
);

var FieldGroupsModel = mongoose.model("FieldGroups", FieldGroupsSchema)

每个 FieldGroups 实例都有一个与之关联的 ShopsModel。

我需要为FieldGroupsModelfields[i].handle值创建一个索引,这个索引需要两条规则;它需要对每个 FieldGroupsModel 实例都是唯一的,因此该数据将无效:


  title: "Some field group title here",
  fields: [
    
      label: "Some label 1"
      handle: "some-label-1"
    ,
    
      label: "Some label 1"
      handle: "some-label-1" // Error: `some-label-1` already exists as a value of `fields[i].handle`.
    
  ],
  shop: 
    "$oid": "1"
  

第二条规则是第一条规则应该只适用于共享相同shop 值的 FieldGroupsModel 实例。所以这个数据是无效的:

// First bit of data

  title: "Some field group title here",
  fields: [
    
      label: "Some label 1"
      handle: "some-label-1"
    
  ],
  shop: 
    "$oid": "1"
  


// Second bit of data

  title: "Another field group title here",
  fields: [
    
      label: "Some label 1"
      handle: "some-label-1" // Error: `some-label-1` already exists as a value of `fields[i].handle` of a document which shares the same `shop` value.
    
  ],
  shop: 
    "$oid": "1"
  

但是,这将是有效的:

// First bit of data

  title: "Some field group title here",
  fields: [
    
      label: "Some label 1"
      handle: "some-label-1"
    
  ],
  shop: 
    "$oid": "1"
  


// Second bit of data

  title: "Another field group title here",
  fields: [
    
      label: "Some label 1"
      handle: "some-label-1" // This is valid because there's no other documents with the same `shop` value with the same `fields[i].handle` value.
    
  ],
  shop: 
    "$oid": "2"
  

我对 Mongo 和 Mongoose 还很陌生,所以这里的任何帮助都会非常感谢! :)

【问题讨论】:

【参考方案1】:

您在 Schema 对象上调用 index 方法来执行此操作,如 here 所示。对于您的情况,它将类似于:

FieldGroupsSchema.index("shop": 1, "fields.handle": 1, unique: true);

请阅读有关 Compound Indexes 的 MongoDB 文档了解更多详细信息。

【讨论】:

嘿Đức,感谢您的帮助!我试过了,但没有成功,仍在保存重复项。 嗨@Tom,在应用复合索引之前,您必须删除集合或删除集合中存在的所有内容。 嘿@Đức Nguyễn,是的,我试过这个,现在它有点工作;它可以防止具有相同shop 值的其他文档包含重复的fields.handle 值,这很好,也是我想要的,但它仍然允许同一文档的重复fields.handle;有什么想法吗? 嗨@Tom,要在文档的数组元素中创建索引,只需向 Schema 添加另一个索引,如下所示:ensureIndex("fields.handle":1) 无论如何,我认为您应该使用 $addToSet 将元素添加到字段数组。 $addToSet 确保您的数组是唯一的。详细请参考 mongodb $addToSet 文档:docs.mongodb.com/manual/reference/operator/update/addToSet

以上是关于在 Mongoose 中为对象数组创建索引的主要内容,如果未能解决你的问题,请参考以下文章

mongoose createIndex: false 是不是意味着索引将在后台创建或根本不创建?

如何从 Mongoose 获取定义的索引

如何在 SQL 中为选择查询创建索引?

Mongoose 不断为不再存在的旧字段创建索引

在 SQLite 中为全文搜索索引创建 SQL 触发器

在结构中为前 5 个创建最高值的索引