Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

SERVER-6648 make TTLMonitor sync userFlags on secondaries

  • Loading branch information...
commit b54a71fd4838196ba178a56f3b49a02cc94f9e10 1 parent 3f79f47
matulef authored August 01, 2012
81  jstests/slowNightly/ttl_repl.js
... ...
@@ -0,0 +1,81 @@
  1
+/** Test TTL collections with replication
  2
+ *  Part 1: Initiate replica set. Insert some docs and create a TTL index. Check that both primary
  3
+ *          and secondary get userFlags=1 (indicating that usePowerOf2Sizes is on),
  4
+ *          and check that the correct # of docs age out.
  5
+ *  Part 2: Add a new member to the set.  Check it also gets userFlags=1 and correct # of docs.
  6
+ */
  7
+
  8
+var rt = new ReplSetTest( { name : "ttl_repl" , nodes: 2 } );
  9
+
  10
+/******** Part 1 ***************/
  11
+
  12
+// setup set
  13
+var nodes = rt.startSet();
  14
+rt.initiate();
  15
+var master = rt.getMaster();
  16
+rt.awaitSecondaryNodes();
  17
+var slave1 = rt.liveNodes.slaves[0];
  18
+
  19
+// shortcuts
  20
+var masterdb = master.getDB( 'd' );
  21
+var mastercol = masterdb[ 'c' ];
  22
+var slave1col = slave1.getDB( 'd' )[ 'c' ];
  23
+
  24
+// create new collection. insert 24 docs, aged at one-hour intervalss
  25
+mastercol.drop();
  26
+now = (new Date()).getTime();
  27
+for ( i=0; i<24; i++ )
  28
+    mastercol.insert( { x : new Date( now - ( 3600 * 1000 * i ) ) } );
  29
+masterdb.getLastError();
  30
+rt.awaitReplication();
  31
+assert.eq( 24 , mastercol.count() , "docs not inserted on primary" );
  32
+assert.eq( 24 , slave1col.count() , "docs not inserted on secondary" );
  33
+
  34
+// before TTL index created, check that userFlags are 0
  35
+print("Initial Stats:")
  36
+print("Master:");
  37
+printjson( mastercol.stats() );
  38
+print("Slave1:");
  39
+printjson( slave1col.stats() );
  40
+
  41
+assert.eq( 0 , mastercol.stats().userFlags , "userFlags not 0 on primary");
  42
+assert.eq( 0 , slave1col.stats().userFlags , "userFlags not 0 on secondary");
  43
+
  44
+// create TTL index, wait for TTL monitor to kick in, then check that
  45
+// userFlags get set to 1, and correct number of docs age out
  46
+mastercol.ensureIndex( { x : 1 } , { expireAfterSeconds : 20000 } );
  47
+masterdb.getLastError();
  48
+rt.awaitReplication();
  49
+
  50
+sleep(70*1000); // TTL monitor runs every 60 seconds, so wait 70
  51
+
  52
+print("Stats after waiting for TTL Monitor:")
  53
+print("Master:");
  54
+printjson( mastercol.stats() );
  55
+print("Slave1:");
  56
+printjson( slave1col.stats() );
  57
+
  58
+assert.eq( 1 , mastercol.stats().userFlags , "userFlags not 1 on primary" );
  59
+assert.eq( 1 , slave1col.stats().userFlags , "userFlags not 1 on secondary" );
  60
+assert.eq( 6 , mastercol.count() , "docs not deleted on primary" );
  61
+assert.eq( 6 , slave1col.count() , "docs not deleted on secondary" );
  62
+
  63
+
  64
+/******** Part 2 ***************/
  65
+
  66
+// add a new secondary, wait for it to fully join
  67
+var slave = rt.add();
  68
+rt.reInitiate();
  69
+rt.awaitSecondaryNodes();
  70
+
  71
+var slave2col = slave.getDB( 'd' )[ 'c' ];
  72
+
  73
+// check that its userFlags are also 1, and it has right number of docs
  74
+print("New Slave stats:");
  75
+printjson( slave2col.stats() );
  76
+
  77
+assert.eq( 1 , slave2col.stats().userFlags , "userFlags not 1 on new secondary");
  78
+assert.eq( 6 , slave2col.count() , "wrong number of docs on new secondary");
  79
+
  80
+// finish up
  81
+rt.stopSet();
17  src/mongo/db/ttl.cpp
@@ -39,15 +39,17 @@ namespace mongo {
39 39
         
40 40
         void doTTLForDB( const string& dbName ) {
41 41
             
42  
-            if ( ! isMasterNs( dbName.c_str() ) )
43  
-                return;
44  
-            
45 42
             Client::GodScope god;
46 43
 
47 44
             vector<BSONObj> indexes;
48 45
             {
49  
-                auto_ptr<DBClientCursor> cursor = db.query( dbName + ".system.indexes" , 
50  
-                                                            BSON( secondsExpireField << BSON( "$exists" << true ) ) );
  46
+                auto_ptr<DBClientCursor> cursor =
  47
+                                db.query( dbName + ".system.indexes" ,
  48
+                                          BSON( secondsExpireField << BSON( "$exists" << true ) ) ,
  49
+                                          0 , /* default nToReturn */
  50
+                                          0 , /* default nToSkip */
  51
+                                          0 , /* default fieldsToReturn */
  52
+                                          QueryOption_SlaveOk ); /* perform on secondaries too */
51 53
                 if ( cursor.get() ) {
52 54
                     while ( cursor->more() ) {
53 55
                         indexes.push_back( cursor->next().getOwned() );
@@ -86,6 +88,11 @@ namespace mongo {
86 88
                     if ( nsd->setUserFlag( NamespaceDetails::Flag_UsePowerOf2Sizes ) ) {
87 89
                         nsd->syncUserFlags( ns );
88 90
                     }
  91
+                    // only do deletes if on master
  92
+                    if ( ! isMasterNs( dbName.c_str() ) ) {
  93
+                        continue;
  94
+                    }
  95
+
89 96
                     n = deleteObjects( ns.c_str() , query , false , true );
90 97
                 }
91 98
 

0 notes on commit b54a71f

Please sign in to comment.
Something went wrong with that request. Please try again.