中年engineerの独り言 - crumbjp

LinuxとApacheの憂鬱

MongoDB 2.4 の性能 徹底評価

まとめ

超長くなったのでまとめを上に持ってきた。
巷で言われているチューニングは結構嘘が多い事が解ってきた。

ツール等

workingSet Analyzer は信用ならない。(overSecondsはまあ良い)
mongoperfの値は完全に参考にならない

insert

mongoperfの値はinsert性能と関連しない。(何を測ってるんだ?)
カラムのプリアロケーションによるUPDATE時のデータ肥大化回避($setOnInsert)はMUST
クリティカルな時間帯にストレージファイル(2GB)の生成を避けるチューニングの効果は懐疑的。
レコードプリアロケーション・チューニングは頑張る価値が無い。(むしろ逆効果)

update

上記の通り必ずin-placeになるようにする。
paddingFactorが動くようだとお話にならない性能劣化

remove

かなり高速。
全件削除の場合はdrop()なら一瞬。(データファイルは残る)
dropDatabase()はデータファイル削除を伴うのでそれなりに時間が掛るが気にする程でもない。

access

オンメモリデータに触れば高速。
シーケンシャルアクセスならディスクアクセスでもそれ程の性能劣化は無い。
ランダムアクセスのディスクアクセスでは明らかな性能劣化。
covered indexはかなり高速。(mmap領域のスワップアプトも起こし難いので更に良い)

index

インデックス張り。
高速だが相変わらずコレクションをロックするので注意。(backgroundも意味なし)
Background Construction

Building Indexes on Secondaries
Background index operations on a replica set primary become foreground indexing operations on secondary members of the set. All indexing operations on secondaries block replication.

1.8の頃から指摘してるんだけどなぁ・・・
プライマリだけバックグラウンドになっても何も嬉しくない!
どういう発想するとこうなるの?

group

安心して使えない・・・

db.testcol.group( { key :{ } , cond : { _id:{$lt : 10000000 , $gte : 0 } }, reduce: function(o,p) { p.value0 += o.value0 }, initial: {value0:0}})

こんな事するとmongodが死ぬ。
MongoDBで集計はまだまだ無謀・・・

検証内容

環境

Sakura VPS 2G

CPU (3 core)
$ cat /proc/cpuinfo  | grep -e processor -e 'model name' -e 'cpu MHz' -e 'cores'
processor       : 0
model name      : Intel(R) Xeon(R) CPU           E5645
cpu MHz         : 2400.068
cpu cores       : 1
processor       : 1
model name      : Intel(R) Xeon(R) CPU           E5645
cpu MHz         : 2400.068
cpu cores       : 1
processor       : 2
model name      : Intel(R) Xeon(R) CPU           E5645
cpu MHz         : 2400.068
cpu cores       : 1
Memory (2GB)
$ cat /proc/meminfo  | head -n 2
MemTotal:        1922440 kB
MemFree:           74460 kB
IO speed (write : 189 MB/s)
$ dd if=/dev/zero of=foo count=4000000
4000000+0 records in
4000000+0 records out
2048000000 bytes (2.0 GB) copied, 10.2278 s, 200 MB/s

mongoperf

MongoDB 付属のプロファイルツールでシステムの参考値を得る事ができます。
が、結論としてはなんの参考にもならない

ディスク書き込み性能 (10MB/sec)

書き込みは何スレッドで書いても一緒なのでスレッド数は1で計測

$ ./bin/mongoperf <<<'{ w:true, nThreads:1, fileSizeMB:2048 }'
<>
3121 ops/sec 12 MB/sec
3076 ops/sec 12 MB/sec
2648 ops/sec 10 MB/sec
2527 ops/sec 9 MB/sec
2546 ops/sec 9 MB/sec
2487 ops/sec 9 MB/sec
2859 ops/sec 11 MB/sec
2813 ops/sec 10 MB/sec
2531 ops/sec 9 MB/sec
2492 ops/sec 9 MB/sec
ディスク読み込み性能 (不明・・・参考値として 20MB /sec としておく)

明らかに値が変、何かの間違いな気がする。

./bin/mongoperf <<<'{ r:true, nThreads:1, fileSizeMB:2048 }'
<>
224 ops/sec 0 MB/sec
236 ops/sec 0 MB/sec
247 ops/sec 0 MB/sec
222 ops/sec 0 MB/sec
231 ops/sec 0 MB/sec
233 ops/sec 0 MB/sec

ファイルサイズを減らしたらいい感じの値になった。
プロファイラのバグじゃなかろうか?

./bin/mongoperf <<<'{ r:true, nThreads:1, fileSizeMB:128 }'
<>
5136 ops/sec 20 MB/sec
5126 ops/sec 20 MB/sec
4856 ops/sec 18 MB/sec
4830 ops/sec 18 MB/sec
4848 ops/sec 18 MB/sec
マップファイル経由で書き込む速度 (160MB/sec)

ddの速度に近い。
mmapが巧く働き、ハードの限界性能を引き出していることを示している。

./bin/mongoperf <<<'{ w:true, mmf:true, nThreads:1, fileSizeMB:1024 }'
<>
61514 ops/sec
59479 ops/sec
77352 ops/sec
87438 ops/sec
75498 ops/sec
63869 ops/sec

裏からiostat で書き込みバイトを監視する。

<>
Device:            tps    MB_read/s    MB_wrtn/s    MB_read    MB_wrtn
vda           20271.00         0.00       164.79          0        164
vda           19943.00         0.00       161.03          0        161
vda           20755.00         0.00       168.41          0        168
モリーから読む速度 (60万レコード/sec)

物理メモリーが2Gしか無いのでマップファイルを1GBにする。
1GBがメモリに乗りきるまで時間が掛るが、乗り切った状態でこの速度

./bin/mongoperf <<<'{ r:true, mmf:true, nThreads:32, fileSizeMB:1024 }'
<>
643635 ops/sec
642684 ops/sec
636734 ops/sec
648714 ops/sec
637600 ops/sec
638460 ops/sec
608880 ops/sec

mongod

扱うデータ
レコード数
1000万
レコードサイズ
4kb
カラム数
11
for i in {0..10000000}; 
do
echo \{\"_id\":$i, \
\"value1\":\"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa$i\",\
\"value2\":\"bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb$i\",\
\"value3\":\"cccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccc$i\",\
\"value4\":\"ddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddeeeeeeeeeeeeeeeeeeeeeeeeeeee$i\",\
\"value5\":`expr $i % 40`,\
\"value6\":\"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff$i\",\
\"value7\":\"gggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggggg$i\",\
\"value8\":\"hhhhhhhhhhhh$i\",\
\"value9\":\"iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii$i\",\
\"value0\":$i\}
done
  • _id , value5 , value0 が数値データ
  • _id と value0 は同じ値
  • value5 は _id % 40 でランダムアクセスや非ユニークインデックスの検証に使う。

insert系

全件insert
時間
960 sec = 16 min
単位時間辺りレコード
10417 rec / sec
単位時間辺りサイズ
41 MB /sec

mongoperfの値は参考にならない事が解った

ファイル生成が起こらない全件insert
時間
1125 sec = 19 min
単位時間辺りレコード
8889 rec / sec
単位時間辺りサイズ
35 MB /sec

事前にファイル(storageSize)がある場合ファイル生成コスト分だけ早くなる筈がほんの少し遅くなった
ただ、数回計測してはいるが、検証環境がVPS(非占有マシン)なので断定はできない。

インサート前の状態。
count = 0
storageSize = 43GB

 db.testcol.stats()
{
        "ns" : "test.testcol",
        "count" : 0,
        "size" : 0,
        "storageSize" : 43026657008,
        "numExtents" : 41,
        "nindexes" : 1,
        "lastExtentSize" : 2146426864,
        "paddingFactor" : 1,
        "systemFlags" : 1,
        "userFlags" : 0,
        "totalIndexSize" : 8176,
        "indexSizes" : {
                "_id_" : 8176
        },
        "ok" : 1
}
プリアロケート&upsert (insertの代わり)
時間
1239 sec = 20 min
単位時間辺りレコード
8071 rec / sec
単位時間辺りサイズ
31 MB / sec

schema design pitfallsの4. Preallcate decuments の手法。
インサートは事前にやっておき、レコード生成をアップデート処理に置き換えて速度を稼ぐ方法。

全然効かない。。。むしろ遅い。。

プリアロケート状態
> db.testcol.stats()
{
        "ns" : "test.testcol",
        "count" : 10000001,
        "size" : 40800004080,
        "avgObjSize" : 4080,
        "storageSize" : 43026657008,
        "numExtents" : 41,
        "nindexes" : 1,
        "lastExtentSize" : 2146426864,
        "paddingFactor" : 1,
        "systemFlags" : 1,
        "userFlags" : 0,
        "totalIndexSize" : 479824912,
        "indexSizes" : {
                "_id_" : 479824912
        },
        "ok" : 1
}
upsert後
> db.testcol.stats()
{
        "ns" : "test.testcol",
        "count" : 10000001,
        "size" : 40800004080,
        "avgObjSize" : 4080,
        "storageSize" : 43026657008,
        "numExtents" : 41,
        "nindexes" : 1,
        "lastExtentSize" : 2146426864,
        "paddingFactor" : 1,
        "systemFlags" : 1,
        "userFlags" : 0,
        "totalIndexSize" : 479824912,
        "indexSizes" : {
                "_id_" : 479824912
        },
        "ok" : 1
}

update系

全件(in-place)1カラムupdate
時間
646 sec
単位時間辺りレコード
15480 rec / sec
単位時間辺りサイズ
60 MB / sec
db.testcol.update({},{$set:{value0:"3"}},{multi:true})

ディスクから読んで書く処理になる。
プロファイラの結果から書き込み速度(10MB /sec)+読み込み速度(20MB /sec)に近くなると予想していたが
遥かに早かった。
全件処理でシーケンシャルread & write になった事が要因か?

dd書き込み速度の1/3は優秀と言えるが、そもそもNoSQLで全件アップデートをしたら負けとも言う・・・

Device:            tps    MB_read/s    MB_wrtn/s    MB_read    MB_wrtn
vda            1220.00       105.62       182.12        105        182
vda            1174.00       134.38        40.00        134         40
vda            1126.00       107.88       108.00        107        108
vda             885.00        85.75        84.01         85         84
vda             916.00        88.75        88.00         88         88
vda            1176.00        96.12       196.12         96        196
vda            1178.00       136.12        36.00        136         36
paddingFactor
in-placeアップデートの場合は1になります。
db.testcol.stats().paddingFactor
1
workingSet Analyzer は信用ならない・・・
6370207ページ = 24GB

ページを重複カウントしてるとしか思えない。

db.serverStatus({workingSet:1}).workingSet
{
        "note" : "thisIsAnEstimate",
        "pagesInMemory" : 6370207,
        "computationTimeMicros" : 3561940,
        "overSeconds" : 31
}
全件(in-place)10カラムupdate
時間
737 sec
単位時間辺りレコード
13569 rec / sec
単位時間辺りサイズ
53 MB / sec

1カラムupdateより若干遅いがIO総量は変わった様に見えない。
明らかにCPU負荷が高くなるのでドキュメント更新処理の分か。

db.testcol.update(
  {},
  { $set:{
   value0:"",
   value1:"",
   value2:"",
   value3:"",
   value4:"",
   value5:"",
   value6:"",
   value7:"",
   value8:"",
   value9:""}},
  {multi:true})'
全件(relocation)1カラムアップデート
時間
3905 sec = 65 min
単位時間辺りレコード
2564 rec / sec
単位時間辺りサイズ
22 MB / sec

レコード移動とストレージスペース肥大化でダブルパンチ。
実に6倍もの性能劣化。
これを起こしてしまったらお話にならない。

db.testcol.update({},{$set:{value0:"ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ"}},{multi:true})
update前
> db.tsetcol.stats()
{
        "ns" : "test.tsetcol",
        "count" : 10000001,
        "size" : 40800004080,
        "avgObjSize" : 4080,
        "storageSize" : 43026657008,
        "numExtents" : 41,
        "nindexes" : 1,
        "lastExtentSize" : 2146426864,
        "paddingFactor" : 1,
        "systemFlags" : 1,
        "userFlags" : 0,
        "totalIndexSize" : 479824912,
        "indexSizes" : {
                "_id_" : 479824912
        },
        "ok" : 1
}
update後
> db.tsetcol.stats()
{
        "ns" : "test.testcol",
        "count" : 10000001,
        "size" : 90872101360,
        "avgObjSize" : 9087.209227279078,
        "storageSize" : 133176585296,
        "numExtents" : 84,
        "nindexes" : 2,
        "lastExtentSize" : 2146426864,
        "paddingFactor" : 1.9970000002930703,
        "systemFlags" : 1,
        "userFlags" : 0,
        "totalIndexSize" : 742560672,
        "indexSizes" : {
                "_id_" : 251583696,
                "value5_1" : 490976976
        },
        "ok" : 1
}
paddingFactor
ほぼ最大値(=2)
確実にリロケーションが起きている。
storageSize
結果、実データ量の2倍の領域を使ってしまった。
全件削除(remove)
時間
503 sec
単位時間辺りレコード
19881 rec / sec
単位時間辺りサイズ
77 MB / sec
db.testcol.remove()

これはあくまでremoveの性能測定。
全件削除の場合はdrop()なら一瞬。

db.testcol.drop()

data access

ディスクデータにアクセスする速度(転送無し)
時間
20 sec
単位時間辺りレコード
12500 rec / sec
単位時間辺りサイズ
48 MB / sec

まずはデータ転送に関わらない性能を測る為groupを使う

4080 * 250000件 = 972MB (約1GB) のデータを扱う。

モリーに乗ってないデータ域を1GB程度アクセス

db.testcol.group( {
 key :{ } , 
 cond : { _id:{$lt : 9500000 , $gte : 9000000 } }, 
 reduce: function(o,p) { p.value0 += o.value0 }, 
 initial: {value0:0}})

ちなみに件数が多いとmongodが死にます。

db.testcol.group( { 
  key :{ } , 
  cond : { _id:{$lt : 10000000 , $gte : 0 } }, 
  reduce: function(o,p) { p.value0 += o.value0 }, 
  initial: {value0:0}})

怖くて使えない・・・

オンメモリデータにアクセスする速度(転送無し)
時間
9 sec
単位時間辺りレコード
31250 rec / sec
単位時間辺りサイズ
108 MB / sec

上記スクリプトをもう一度実行

ディスクデータにアクセスする速度(転送有り)
時間
21 sec
単位時間辺りレコード
11905 rec / sec
単位時間辺りサイズ
46 MB / sec
転送データ量
5.5MB

mongoシェル(クライアント側)のCPU使用率が振り切れてるので正確ではないかもしれないが
上記groupの結果と合わせて考える。

DBQuery.shellBatchSize=250000
db.testcol.find({ _id:{$lt : 9250000 , $gte : 9000000 }},{_id:0,value0:1})

iostatによると5秒程度で必要なデータを読み切っている事が解る。
(オンメモリデータアクセスと比べてのオーバヘッドが1GBで5秒程度という事)

但しこれは連続域にアクセスしているのでディスクをシーケンシャルリードしている。
ランダムアクセスすれば相当性能劣化するはず。

Device:         rrqm/s   wrqm/s     r/s     w/s    rMB/s    wMB/s avgrq-sz avgqu-sz   await  svctm  %util
vda               0.00     0.00    0.00    0.00     0.00     0.00     0.00     0.00    0.00   0.00   0.00
vda               0.00     0.00 1278.00    1.00   159.63     0.00   255.62     0.86    0.68   0.57  72.80
vda               0.00     0.00 1329.00    0.00   166.11     0.00   255.98     0.82    0.62   0.53  69.90
vda               0.00     0.00 1283.00    0.00   160.50     0.00   256.20     0.81    0.63   0.56  72.20
vda               0.00     0.00 1395.00    0.00   174.25     0.00   255.82     0.89    0.64   0.56  78.60
vda               0.00     0.00 1430.00    0.00   178.88     0.00   256.18     0.87    0.61   0.53  75.10
vda               0.00     0.00  955.00    2.00   119.25     0.01   255.21     0.51    0.54   0.46  44.10
vda               0.00     0.00    0.00    0.00     0.00     0.00     0.00     0.00    0.00   0.00   0.00
vda               6.00     0.00    2.00    0.00     0.03     0.00    32.00     0.01    4.00   2.00   0.40
vda               0.00     0.00    0.00    0.00     0.00     0.00     0.00     0.00    0.00   0.00   0.00
vda               0.00     0.00    0.00    0.00     0.00     0.00     0.00     0.00    0.00   0.00   0.00
vda               0.00     0.00    0.00    0.00     0.00     0.00     0.00     0.00    0.00   0.00   0.00
vda               0.00     1.00    0.00    2.00     0.00     0.01    12.00     0.00    0.50   0.50   0.10
オンメモリデータにアクセスする速度(転送有り)
時間
18 sec
単位時間辺りレコード
13889 rec / sec
単位時間辺りサイズ
54 MB / sec
転送データ量
5.5MB

上記スクリプトをもう一度実行

オンメモリ(coverd indexes)データにアクセスする速度
時間
15 sec
単位時間辺りレコード
16667 rec / sec
単位時間辺りサイズ
データには触らない。

7. Can you use covered indexes?
_idにしか触らないので、適用される。

流石に速い。

DBQuery.shellBatchSize=250000
db.testcol.find({ _id:{$lt : 9250000 , $gte : 9000000 }},{_id:1})
ディスクデータにアクセスする速度(転送有り)(ランダムアクセス)
時間
224 sec
単位時間辺りレコード
1116 rec / sec
転送データ量
5.5MB
DBQuery.shellBatchSize=250000
db.testcol.find({ value5:0 },{value0:1,_id:0})

value5カラムは % 40 なので40行飛ばしたアクセスになり、シーケンシャルアクセスではなくなる。
同じディスクアクセスでも10倍以上の差が出てしまう。

Index

ensureIndex
時間
266 sec
ソート
241 sec
BTree
25 sec
db.testcol.ensureIndex({value5:1},{unique:1})'
ensureIndex (ユニーク)
時間
249 sec
ソート
227 sec
BTree
22 sec

ユニークインデックスの方が若干早いが有意な差ではない。

dropIndex

一瞬で終わる。