diff options
author | Dan Pasette <dan@10gen.com> | 2015-09-16 19:52:06 -0400 |
---|---|---|
committer | Dan Pasette <dan@mongodb.com> | 2015-09-22 12:23:43 -0400 |
commit | 895db3539016bc9c0bba76c2505c7878a1fbb9ff (patch) | |
tree | 6494cdb487b1bafebfd37a09bb6b4e48a8efd264 | |
parent | 4119b212084ada7f544526f07cbf9352e7d5c910 (diff) | |
download | mongo-895db3539016bc9c0bba76c2505c7878a1fbb9ff.tar.gz |
SERVER-17425 Disallow creation of v0 indexes
-rw-r--r-- | jstests/core/create_indexes.js | 22 | ||||
-rw-r--r-- | jstests/core/index7.js | 15 | ||||
-rwxr-xr-x | jstests/dur/dur1.js | 2 | ||||
-rwxr-xr-x | jstests/dur/dur1_tool.js | 2 | ||||
-rwxr-xr-x | jstests/dur/manyRestart.js | 2 | ||||
-rw-r--r-- | jstests/mmap_v1/compact2.js | 52 | ||||
-rw-r--r-- | jstests/mmap_v1/dumprestore6.js | 50 | ||||
-rw-r--r-- | jstests/noPassthroughWithMongod/index_check10.js | 15 | ||||
-rw-r--r-- | jstests/replsets/initSyncV1Index.js | 52 | ||||
-rw-r--r-- | jstests/tool/dumprestore6.js | 26 | ||||
-rw-r--r-- | src/mongo/db/commands/create_indexes.cpp | 10 | ||||
-rw-r--r-- | src/mongo/db/db.cpp | 9 |
12 files changed, 58 insertions, 199 deletions
diff --git a/jstests/core/create_indexes.js b/jstests/core/create_indexes.js index 9669daf6205..ef11187f76a 100644 --- a/jstests/core/create_indexes.js +++ b/jstests/core/create_indexes.js @@ -126,20 +126,12 @@ assert.eq( 6, t.getIndexes().length ); - // - // Test that v0 indexes can only be created with mmapv1 - // - res = t.runCommand('createIndexes', - {indexes: [{key: {d: 1}, name: 'd_1', v: 0}]}); - - if (!isMongos) { - var status = db.serverStatus(); - assert.commandWorked(status); - if (status.storageEngine.name === 'mmapv1') { - assert.commandWorked(res, 'v0 index creation should work for mmapv1'); - } else { - assert.commandFailed(res, 'v0 index creation should fail for non-mmapv1 storage engines'); - } - } + // Test that v0 indexes cannot be created. + res = t.runCommand('createIndexes', {indexes: [{key: {d: 1}, name: 'd_1', v: 0}]}); + assert.commandFailed(res, 'v0 index creation should fail'); + + // Test that v1 indexes can be created explicitly. + res = t.runCommand('createIndexes', {indexes: [{key: {d: 1}, name: 'd_1', v: 1}]}); + assert.commandWorked(res, 'v1 index creation should succeed'); }()); diff --git a/jstests/core/index7.js b/jstests/core/index7.js deleted file mode 100644 index bd7c75b8b08..00000000000 --- a/jstests/core/index7.js +++ /dev/null @@ -1,15 +0,0 @@ -// Check that v0 keys are generated for v0 indexes SERVER-3375 - -t = db.jstests_indexw; -t.drop(); - -t.save( {a:[]} ); -assert.eq( 1, t.count( {a:[]} ) ); -t.ensureIndex( {a:1} ); -assert.eq( 1, t.count( {a:[]} ) ); -t.dropIndexes(); - -// The count result is incorrect - just checking here that v0 key generation is used. -t.ensureIndex( {a:1}, {v:0} ); -// QUERY_MIGRATION: WE GET THIS RIGHT...BY CHANCE? -// assert.eq( 0, t.count( {a:[]} ) ); diff --git a/jstests/dur/dur1.js b/jstests/dur/dur1.js index 4668b4921e2..a4cf88cf22e 100755 --- a/jstests/dur/dur1.js +++ b/jstests/dur/dur1.js @@ -62,7 +62,7 @@ function work() { d.a.update({ _id: 4 }, { $inc: { x: 1} }); // try building an index. however, be careful as object id's in system.indexes would vary, so we do it manually: - d.system.indexes.insert({ _id: 99, ns: "test.a", key: { x: 1 }, name: "x_1", v: 0 }); + d.system.indexes.insert({ _id: 99, ns: "test.a", key: { x: 1 }, name: "x_1" }); log("endwork");
return d; diff --git a/jstests/dur/dur1_tool.js b/jstests/dur/dur1_tool.js index f86e643b6f7..f0c2916012d 100755 --- a/jstests/dur/dur1_tool.js +++ b/jstests/dur/dur1_tool.js @@ -62,7 +62,7 @@ function work() { d.a.update({ _id: 4 }, { $inc: { x: 1} }); // try building an index. however, be careful as object id's in system.indexes would vary, so we do it manually: - d.system.indexes.insert({ _id: 99, ns: "test.a", key: { x: 1 }, name: "x_1", v: 0 }); + d.system.indexes.insert({ _id: 99, ns: "test.a", key: { x: 1 }, name: "x_1" }); log("endwork");
return d; } diff --git a/jstests/dur/manyRestart.js b/jstests/dur/manyRestart.js index d2e864a708b..fe48de9beec 100755 --- a/jstests/dur/manyRestart.js +++ b/jstests/dur/manyRestart.js @@ -62,7 +62,7 @@ function work() { d.a.update({ _id: 4 }, { $inc: { x: 1} }); // try building an index. however, be careful as object id's in system.indexes would vary, so we do it manually: - d.system.indexes.insert({ _id: 99, ns: "test.a", key: { x: 1 }, name: "x_1", v: 0 }); + d.system.indexes.insert({ _id: 99, ns: "test.a", key: { x: 1 }, name: "x_1" }); log("endwork"); return d; } diff --git a/jstests/mmap_v1/compact2.js b/jstests/mmap_v1/compact2.js deleted file mode 100644 index 0a7c343a3f9..00000000000 --- a/jstests/mmap_v1/compact2.js +++ /dev/null @@ -1,52 +0,0 @@ -// Compaction of a v0 index converts it to a v1 index using a v1 index comparator during external -// sort. SERVER-6499 - -t = db.jstests_compact2; -t.drop(); - -/** - * Assert that the index is of the expected version and its keys are ordered consistently with this - * version, and that the unique and background fields are set correctly. - */ -function assertIndex( expectedVersion, unique, background ) { - indexSpec = db.system.indexes.findOne( { ns:t.toString(), key:{ date:1 } } ); - // The index version is as expected. - assert.eq( expectedVersion, indexSpec.v ); - // The index uniqueness is as expected (treat missing and false unique specs as equivalent). - assert.eq( !unique, !indexSpec.unique ); - // Background is as expected. - assert.eq( !background, !indexSpec.background ); - // Check that 'date' key ordering is consistent with the index version. - dates = t.find().hint( { date:1 } ).toArray().map( function( x ) { return x.date; } ); - if ( expectedVersion == 0 ) { - // Under v0 index comparison, new Date( -1 ) > new Date( 1 ). - assert.eq( [ new Date( 1 ), new Date( -1 ) ], dates ); - } - else { - // Under v1 index comparsion, new Date( -1 ) < new Date( 1 ). - assert.eq( [ new Date( -1 ), new Date( 1 ) ], dates ); - } -} - -/** Compact a collection and check the resulting indexes. */ -function checkCompact( originalVersion, unique, background ) { - t.drop(); - t.save( { date:new Date( 1 ) } ); - t.save( { date:new Date( -1 ) } ); - t.ensureIndex( { date:1 }, { unique:unique, v:originalVersion, background:background } ); - assertIndex( originalVersion, unique, background ); - - // Under SERVER-6499, compact fails when a v0 index is converted to a v1 index and key - // comparisons are inconsistent, as with the date values in this test. - assert.commandWorked( t.runCommand( "compact" ) ); - assert( !db.getLastError() ); - - // Compact built an index with the default index version (v1). Uniqueness is maintained, but - // background always becomes false. - assertIndex( 1, unique, false ); -} - -checkCompact( 0, true, true ); -checkCompact( 0, false, false ); -checkCompact( 1, true, false ); -checkCompact( 1, false, true ); diff --git a/jstests/mmap_v1/dumprestore6.js b/jstests/mmap_v1/dumprestore6.js deleted file mode 100644 index 471a63cf150..00000000000 --- a/jstests/mmap_v1/dumprestore6.js +++ /dev/null @@ -1,50 +0,0 @@ -// dumprestore6.js -// Test restoring from a dump with an old index version - - -t = new ToolTest( "dumprestore6" ); - -c = t.startDB( "foo" ); -db = t.db -assert.eq( 0 , c.count() , "setup1" ); - -t.runTool("restore", "--dir", "jstests/tool/data/dumprestore6", "--db", "jstests_tool_dumprestore6") - -assert.soon( "c.findOne()" , "no data after sleep" ); -assert.eq( 1 , c.count() , "after restore" ); - -var indexes = c.getIndexes(); -assert.eq( 2, indexes.length, "there aren't the correct number of indexes" ); -var aIndex = null; -indexes.forEach(function(index) { - if (index.name === "a_1") { - aIndex = index; - } -}); -assert.neq(null, aIndex, "index doesn't exist" ); -assert.eq( 1 , aIndex.v, "index version wasn't updated"); - -assert.eq( 1, c.count({v:0}), "dropped the 'v' field from a non-index collection") - -db.dropDatabase() -assert.eq( 0 , c.count() , "after drop" ); - -t.runTool("restore", "--dir", "jstests/tool/data/dumprestore6", "--db", "jstests_tool_dumprestore6", "--keepIndexVersion") - -assert.soon( "c.findOne()" , "no data after sleep2" ); -assert.eq( 1 , c.count() , "after restore2" ); - -indexes = c.getIndexes(); -assert.eq( 2, indexes.length, "there aren't the correct number of indexes" ); -aIndex = null; -indexes.forEach(function(index) { - if (index.name === "a_1") { - aIndex = index; - } -}); -assert.neq(null, aIndex, "index doesn't exist" ); -assert.eq( 0 , aIndex.v, "index version wasn't maintained") - -assert.eq( 1, c.count({v:0}), "dropped the 'v' field from a non-index collection") - -t.stop(); diff --git a/jstests/noPassthroughWithMongod/index_check10.js b/jstests/noPassthroughWithMongod/index_check10.js index 5ace6951652..dd88e094cf2 100644 --- a/jstests/noPassthroughWithMongod/index_check10.js +++ b/jstests/noPassthroughWithMongod/index_check10.js @@ -5,7 +5,7 @@ Random.setRandomSeed(); t = db.test_index_check10; -function doIt( indexVersion ) { +function doIt() { t.drop(); @@ -95,9 +95,8 @@ function doIt( indexVersion ) { size -= f.length; } - var max = indexVersion == 0 ? 819 : 818; - - if ( size <= max /* KeyMax */ ) { + var max = 818; // KeyMax + if ( size <= max ) { assert.eq( c1, c3 , "size: " + size ); } } @@ -110,7 +109,7 @@ function doIt( indexVersion ) { } assert.writeOK(bulk.execute()); - t.ensureIndex( idx , { v : indexVersion } ); + t.ensureIndex( idx ); check(); bulk = t.initializeUnorderedBulkOp(); @@ -133,9 +132,5 @@ function doIt( indexVersion ) { } for( var z = 0; z < 5; ++z ) { - var indexVersion = z % 2; - var storageEngine = jsTest.options().storageEngine; - if (storageEngine === 'mmapv1' || indexVersion !== 0) { - doIt(indexVersion); - } + doIt(); } diff --git a/jstests/replsets/initSyncV1Index.js b/jstests/replsets/initSyncV1Index.js deleted file mode 100644 index 10b91949942..00000000000 --- a/jstests/replsets/initSyncV1Index.js +++ /dev/null @@ -1,52 +0,0 @@ -// Create {v:0} index on primary. Add new secondary. -// Make sure same index on secondary is {v:1} - SERVER-3852 -// Run only if storage engine is mmapv1 - SERVER-16893 - -(function() { - 'use strict'; - - var storageEngine = jsTest.options().storageEngine; - if (storageEngine !== 'mmapv1') { - return; - } - - var rs = new ReplSetTest( {name: 'rs', nodes: 1, host: 'localhost'} ); - rs.startSet(); - rs.initiate(); - var r1 = rs.getMaster(); - var db1 = r1.getDB('test'); - - var t = ''; - for (var i = 0; i < 1000; i++) t += 'a'; - for (var i = 0; i < 10000; i++) db1.foo.insert( {_id:i, x:i%1000, t:t} ); - - db1.foo.createIndex({x: 1}, {v: 0}); - - var r2 = rs.add(); - rs.reInitiate(60000); - - var db2 = r2.getDB('test'); - r2.setSlaveOk(); - rs.awaitSecondaryNodes(); - rs.awaitReplication(); - var idxes = db2.foo.getIndexes(); - assert.gt(idxes.length, 0, "Secondary reported no indexes on collection " + db2.foo); - var idx = idxes.filter(function(idx) { - return friendlyEqual(idx.key, {x: 1}); - })[0]; - assert(idx, "expected to find an index with key {x: 1} on the secondary's collection " + db2.foo); - assert.eq (idx.v, 1, - 'expected all indexes generated on Mongo version >= 2.0 to be {v:1}. See SERVER-3852'); - - // add another new node, make sure ports _aren't_ closed SERVER-4315 - r1 = rs.getMaster(); - rs.add(); - var c = r1.getDB("local").system.replset.findOne(); - var config = rs.getReplSetConfig(); - config.version = c.version+1; - var result = r1.getDB("admin").runCommand({replSetReconfig:config}); - assert.eq(result.ok, 1); - - rs.stopSet(15); - -})(); diff --git a/jstests/tool/dumprestore6.js b/jstests/tool/dumprestore6.js new file mode 100644 index 00000000000..e342e71f3f1 --- /dev/null +++ b/jstests/tool/dumprestore6.js @@ -0,0 +1,26 @@ +// Test restoring from a dump with v:0 indexes. +// mongodump strips the 'v' property from the index specification by default. When using +// --keepIndexVersion, the 'v' property is not stripped, but index creation will fail. + +var toolTest = new ToolTest( "dumprestore6" ); +var col = toolTest.startDB( "foo" ); +var testDb = toolTest.db; +assert.eq( 0 , col.count() , "setup1" ); + +// Normal restore should succeed and convert v:1 index. +toolTest.runTool("restore", "--dir", "jstests/tool/data/dumprestore6", "--db", + "jstests_tool_dumprestore6"); +assert.soon( "col.findOne()" , "no data after sleep" ); +assert.eq( 1 , col.count() , "after restore" ); +var indexes = col.getIndexes(); +assert.eq( 2, indexes.length, "there aren't the correct number of indexes" ); + +// Try with --keepIndexVersion, should fail to restore v:0 index. +testDb.dropDatabase(); +assert.eq( 0 , col.count() , "after drop" ); +toolTest.runTool("restore", "--dir", "jstests/tool/data/dumprestore6", "--db", + "jstests_tool_dumprestore6", "--keepIndexVersion"); +indexes = col.getIndexes(); +assert.eq( 1, indexes.length, "there aren't the correct number of indexes" ); + +toolTest.stop(); diff --git a/src/mongo/db/commands/create_indexes.cpp b/src/mongo/db/commands/create_indexes.cpp index 604ddaf7ac8..81552e57377 100644 --- a/src/mongo/db/commands/create_indexes.cpp +++ b/src/mongo/db/commands/create_indexes.cpp @@ -203,10 +203,16 @@ public: status = checkUniqueIndexConstraints(txn, ns.ns(), spec["key"].Obj()); if (!status.isOK()) { - appendCommandStatus(result, status); - return false; + return appendCommandStatus(result, status); } } + if (spec["v"].isNumber() && spec["v"].numberInt() == 0) { + return appendCommandStatus( + result, + Status(ErrorCodes::CannotCreateIndex, + str::stream() << "illegal index specification: " << spec << ". " + << "The option v:0 cannot be passed explicitly")); + } } MONGO_WRITE_CONFLICT_RETRY_LOOP_BEGIN { diff --git a/src/mongo/db/db.cpp b/src/mongo/db/db.cpp index 47c6f207ec9..413515612c3 100644 --- a/src/mongo/db/db.cpp +++ b/src/mongo/db/db.cpp @@ -373,6 +373,15 @@ static void repairDatabasesAndCheckVersion() { << " For more info see" << " http://dochub.mongodb.org/core/index-validation" << startupWarningsLog; } + + if (index["v"].isNumber() && index["v"].numberInt() == 0) { + log() << "WARNING: The collection: '" << coll->ns() << "' with index " << index + << " was created with the deprecated v:0 format. This format will not" + << " be supported in a future release." << startupWarningsLog; + log() << "\t To fix this, you need to rebuild this index." + << " For instructions, see http://dochub.mongodb.org/core/rebuild-v0-indexes" + << startupWarningsLog; + } } if (PlanExecutor::IS_EOF != state) { |