Compare commits

...

3 Commits
r2.0.9 ... v2.0

Author SHA1 Message Date
Greg Studer
c28079649e SERVER-10458 sanity check before critical section that all cloned docs sent 2013-08-12 10:35:02 -04:00
Greg Studer
e5a7faaecd SERVER-10478 fix batch limit check for _cloneLocs in migration 2013-08-12 10:34:56 -04:00
Ernie Hershey
ec60d7de77 post 2.0.9 2013-04-02 17:14:20 -04:00
5 changed files with 100 additions and 4 deletions

View File

@@ -752,6 +752,8 @@ namespace mongo {
int len() const { return _b.len(); }
int arrSize() const { return _i; }
private:
void fill( const StringData& name ) {
char *r;

View File

@@ -3,7 +3,7 @@
#---------------------------------------------------------------------------
DOXYFILE_ENCODING = UTF-8
PROJECT_NAME = MongoDB
PROJECT_NUMBER = 2.0.9
PROJECT_NUMBER = 2.0.10-pre-
OUTPUT_DIRECTORY = docs/doxygen
CREATE_SUBDIRS = NO
OUTPUT_LANGUAGE = English

View File

@@ -0,0 +1,65 @@
//
// Tests migration behavior of large documents
//
var st = new ShardingTest({ shards : 2, mongos : 1,
other : { separateConfig : true,
mongosOptions : { noAutoSplit : "" },
shardOptions : { /* binVersion : "latest" */ } } });
var mongos = st.s0;
var coll = mongos.getCollection( "foo.bar" );
var admin = mongos.getDB( "admin" );
var shards = mongos.getCollection( "config.shards" ).find().toArray();
var shardAdmin = st.shard0.getDB( "admin" );
mongos.getDB( "config" ).settings.update({ _id : "balancer" },
{ $set : { stopped : true } }, true, false);
assert( admin.runCommand({ enableSharding : coll.getDB() + "" }).ok );
printjson( admin.runCommand({ movePrimary : coll.getDB() + "", to : shards[0]._id }) );
assert( admin.runCommand({ shardCollection : coll + "", key : { _id : 1 } }).ok );
assert( admin.runCommand({ split : coll + "", middle : { _id : 0 } }).ok );
jsTestLog( "Preparing large insert..." );
var data1MB = "x"
while ( data1MB.length < 1024 * 1024 )
data1MB += data1MB;
var data15MB = "";
for ( var i = 0; i < 15; i++ ) data15MB += data1MB;
var data15PlusMB = data15MB;
for ( var i = 0; i < 1023 * 1024; i++ ) data15PlusMB += "x";
print("~15MB object size is : " + Object.bsonsize({ _id : 0, d : data15PlusMB }));
jsTestLog( "Inserting docs of large and small sizes..." );
// Two large docs next to each other
coll.insert({ _id : -2, d : data15PlusMB });
coll.insert({ _id : -1, d : data15PlusMB });
// Docs of assorted sizes
coll.insert({ _id : 0, d : "x" });
coll.insert({ _id : 1, d : data15PlusMB });
coll.insert({ _id : 2, d : "x" });
coll.insert({ _id : 3, d : data15MB });
coll.insert({ _id : 4, d : "x" });
coll.insert({ _id : 5, d : data1MB });
coll.insert({ _id : 6, d : "x" });
assert.eq( null, coll.getDB().getLastError() );
assert.eq( 9, coll.find().itcount() );
jsTestLog( "Starting migration..." );
assert( admin.runCommand({ moveChunk : coll + "", find : { _id : 0 }, to : shards[1]._id }).ok );
assert( admin.runCommand({ moveChunk : coll + "", find : { _id : -1 }, to : shards[1]._id }).ok );
assert.eq( 9, coll.find().itcount() );
jsTestLog( "DONE!" );
st.stop();

View File

@@ -507,7 +507,8 @@ namespace mongo {
// use the builder size instead of accumulating 'o's size so that we take into consideration
// the overhead of BSONArray indices
if ( a.len() + o.objsize() + 1024 > BSONObjMaxUserSize ) {
if ( a.arrSize() != 0 &&
a.len() + o.objsize() + 1024 > BSONObjMaxUserSize ) {
filledBuffer = true; // break out of outer while loop
break;
}
@@ -554,6 +555,11 @@ namespace mongo {
long long mbUsed() const { return _memoryUsed / ( 1024 * 1024 ); }
std::size_t cloneLocsRemaining() {
scoped_spinlock lk( _trackerLocks );
return _cloneLocs.size();
}
bool getInCriticalSection() const { scoped_lock l(_m); return _inCriticalSection; }
void setInCriticalSection( bool b ) { scoped_lock l(_m); _inCriticalSection = b; }
@@ -907,11 +913,14 @@ namespace mongo {
timing.done( 3 );
// 4.
// Track last result from TO shard for sanity check
BSONObj res;
for ( int i=0; i<86400; i++ ) { // don't want a single chunk move to take more than a day
assert( dbMutex.getState() == 0 );
sleepsecs( 1 );
ScopedDbConnection conn( to );
BSONObj res;
res = BSONObj();
bool ok = conn->runCommand( "admin" , BSON( "_recvChunkStatus" << 1 ) , res );
res = res.getOwned();
conn.done();
@@ -947,6 +956,26 @@ namespace mongo {
timing.done(4);
// 5.
// Before we get into the critical section of the migration, let's double check
// that the docs have been cloned
log() << "About to check if it is safe to enter critical section" << endl;
// Ensure all cloned docs have actually been transferred
std::size_t locsRemaining = migrateFromStatus.cloneLocsRemaining();
if ( locsRemaining != 0 ) {
errmsg =
str::stream() << "moveChunk cannot enter critical section before all data is"
<< " cloned, " << locsRemaining << " locs were not transferred"
<< " but to-shard reported " << res;
// Should never happen, but safe to abort before critical section
error() << errmsg << migrateLog;
dassert( false );
return false;
}
{
// 5.a
// we're under the collection lock here, so no other migrate can change maxVersion or ShardChunkManager state

View File

@@ -38,7 +38,7 @@ namespace mongo {
* 1.2.3-rc4-pre-
* If you really need to do something else you'll need to fix _versionArray()
*/
const char versionString[] = "2.0.9";
const char versionString[] = "2.0.10-pre-";
// See unit test for example outputs
static BSONArray _versionArray(const char* version){