MongoDB后台创建索引

MongoDB后台创建索引

MongoDB 中创建一个索引,有两种方式,即前台创建与后台创建。缺省情况下,当为一个集合创建索引时,这个操作将阻塞其他的所有操作。即该集合上的无法正常读写,直到索引创建完毕。任意基于所有数据库申请读或写锁都将等待直到前台完成索引创建操作。

将索引创建置于到后台,适用于那些需要长时间创建索引的情形。这样子在创建索引期间,MongoDB 依旧可以正常的为提供读写操作服务,等同于关系型数据库在创建索引的时候指定 online,而 MongoDB 则是指定 background,其目的都是相同的,即在索引创建期间,尽可能的以一种占用较少的资源占用方式来实现,同时又可以提供读写服务。

MongoDB后台创建索引详解

语法

db_name.table_name.ensureIndex({field:1|-1}, {background: true})

参数

名称 描述
db_name 数据库名
table_name 集合名
field 要创建索引的字段

说明

通过指定 background 为 true,创建后台索引,缺省情况下 background 选项的值为 false。

MongoDB后台创建索引细节

说明

基于后台创建索引时,其他的数据库操作能被完成。但是对于 mongo shell 会话或者你正在创建索引的这个连接将不可用,直到所有创建完毕。如果需要做一些其它的操作。则需要再建立其它的连接。

在索引创建期间,即使完成了部分索引的创建,索引依旧不可用,但是一旦创建完成即可使用。基于后台创建索引期间不能完成涉及该集合的相关管理操作,如:

repairDatabase db.collection.drop() compact

意外中断索引创建

如果在后台创建索引期间,mongod 实例异常终止,当 mongod 实例重新启动后,未完成的索引创建将作为前台进程来执行。如果索引创建失败,比如由于重复的键等,mongod 将提示错误并退出。

在一个索引创建失败后启动 mongod,可以使用 storage.indexBuildRetry or --noIndexBuildRetry 跳过索引创建来启动。

索引创建期间性能

后台创建索引比前台慢,如果索引大于实际可用内存,则需要更长的时间来完成索引创建。所有涉及到该集合的相关操作在后台期间其执行效能会下降,应在合理的维护空挡期完成索引的创建。

索引的命名规则

缺省情况下,索引名以键名加上其创建顺序(1 或者 -1)组合而成。比如:

db.products.createIndex( { item: 1, quantity: -1 } )

比如上面的索引创建后,其索引名为 item_1_quantity_-1,可以指定自定义的索引名称

db.products.createIndex( { item: 1, quantity: -1 } , { name: "inventory_idx" } )

如上方式,我们指定了了索引名称为 inventory_idx。

查看索引创建进度

可使用 db.currentOp() 命令观察索引创建的完成进度,语法如下:

db.currentOp()

终止索引的创建

db.killOp()

案例

我们首先,使用 mongo 命令,连接上数据库,具体命令如下:

mongo

如下图所示:

07_MongoDB后台创建索引.png

现在,我们使用 use 命令,切换到 haicoder 数据库,具体命令如下:

use haicoder

现在,我们使用 insert 插入四条记录,具体命令如下:

db.haicoder.insert([ {id:1, "url" : "haicoder.net/c", "score" : 100 }, {id:2, "url" : "haicoder.net/cpp", "score" : 90 }, {id:3, "url" : "haicoder.net/golang", "score" : 80 }, {id:4, "url" : "haicoder.net/java", "score" : 60 } ]);

执行完毕后,此时,如下图所示:

08_MongoDB后台创建索引.png

我们看到,此时提示我们成功插入了多条记录,现在,我们给 score 字段创建后台索引,具体命令如下:

db.haicoder.ensureIndex({score:1}, {background: true});

执行完毕后,此时,如下图所示:

09_MongoDB后台创建索引.png

我们看到,此时,我们使用了后台的方式创建了一个索引。

MongoDB后台创建索引总结

在 MongoDB 中创建一个索引,有两种方式,即前台创建与后台创建。缺省情况下,当为一个集合创建索引时,这个操作将阻塞其他的所有操作。即该集合上的无法正常读写,直到索引创建完毕。任意基于所有数据库申请读或写锁都将等待直到前台完成索引创建操作。