diff options
author | Aaron <aaron@10gen.com> | 2009-03-04 15:57:35 -0500 |
---|---|---|
committer | Aaron <aaron@10gen.com> | 2009-03-04 15:57:35 -0500 |
commit | ae7864878173cd9274abf8a97414317bb7b8ce20 (patch) | |
tree | b70d95efbe61b013b54b42c5b335123fb73179d0 /db/cloner.cpp | |
parent | 54160011dec1379485165ec410827521f4510f47 (diff) | |
download | mongo-ae7864878173cd9274abf8a97414317bb7b8ce20.tar.gz |
Better cloneCollection checkpoint
Diffstat (limited to 'db/cloner.cpp')
-rw-r--r-- | db/cloner.cpp | 56 |
1 files changed, 45 insertions, 11 deletions
diff --git a/db/cloner.cpp b/db/cloner.cpp index 3d781825aae..3589a8e2058 100644 --- a/db/cloner.cpp +++ b/db/cloner.cpp @@ -35,7 +35,7 @@ namespace mongo { bool replAuthenticate(DBClientConnection *); class Cloner: boost::noncopyable { - auto_ptr< DBClientInterface > conn; + auto_ptr< DBClientWithCommands > conn; void copy(const char *from_ns, const char *to_ns, bool isindex, bool logForRepl, bool masterSameProcess, bool slaveOk, BSONObj query = emptyObj); public: @@ -156,7 +156,7 @@ namespace mongo { conn = c; } else { - conn = auto_ptr< DBClientInterface >( new DBDirectClient() ); + conn.reset( new DBDirectClient() ); } c = conn->query( ns.c_str(), emptyObj, 0, 0, 0, slaveOk ? Option_SlaveOk : 0 ); } @@ -230,6 +230,9 @@ namespace mongo { } bool Cloner::cloneCollection( const char *fromhost, const char *ns, BSONObj query, string &errmsg, bool logForRepl, bool copyIndexes ) { + char db[256]; + nsToClient( ns, db ); + { dbtemprelease r; auto_ptr< DBClientConnection > c( new DBClientConnection() ); @@ -238,17 +241,44 @@ namespace mongo { if( !replAuthenticate(c.get()) ) return false; conn = c; + + // Start temporary op log + BSONObj info; + if ( !conn->runCommand( db, BSON( "logCollection" << ns << "start" << 1 ), info ) ) { + errmsg = "logCollection failed: " + (string)info; + return false; + } } - + copy( ns, ns, false, logForRepl, false, false, query ); - if ( !copyIndexes ) - return true; - char db[256]; - nsToClient( ns, db ); - string indexNs = string( db ) + ".system.indexes"; - copy( indexNs.c_str(), indexNs.c_str(), true, logForRepl, false, false, BSON( "ns" << ns ) ); + if ( copyIndexes ) { + string indexNs = string( db ) + ".system.indexes"; + copy( indexNs.c_str(), indexNs.c_str(), true, logForRepl, false, false, BSON( "ns" << ns ) ); + } + + // According to the docs, the machine I'm cloning from is supposed to be + // locked during this part. Need to learn more about the plan for that. + string logNS = "local.temp.oplog." + string( ns ); + auto_ptr< DBClientCursor > c = conn->query( logNS.c_str(), Query() ); + while( 1 ) { + { + dbtemprelease t; + if ( !c->more() ) + break; + } + ReplSource::applyOperation( c->next() ); + } + + { + dbtemprelease t; + BSONObj info; + if ( !conn->runCommand( db, BSON( "logCollection" << ns << "drop" << 1 ), info ) ) { + errmsg = "logCollection failed: " + (string)info; + return false; + } + } return true; } @@ -290,11 +320,15 @@ namespace mongo { } virtual bool run(const char *ns, BSONObj& cmdObj, string& errmsg, BSONObjBuilder& result, bool fromRepl) { string fromhost = cmdObj.getStringField("from"); - if ( fromhost.empty() ) + if ( fromhost.empty() ) { + errmsg = "missing from spec"; return false; + } string collection = cmdObj.getStringField("cloneCollection"); - if ( collection.empty() ) + if ( collection.empty() ) { + errmsg = "missing cloneCollection spec"; return false; + } BSONObj query = cmdObj.getObjectField("query"); if ( query.isEmpty() ) query = emptyObj; |