if (it != keyIndex.end()) {
rv = EXISTING_ITEM;
std::list<queued_item>::iterator currPos = it->second.position;
- uint64_t currMutationId = it->second.mutation_id;
+ const int64_t currMutationId{it->second.mutation_id};
// Given the key already exists, need to check all cursors in this
// Checkpoint and see if the existing item for this key is to
// decrement if the the existing item is strictly less than
// the cursor, as meta-items can share a seqno with
// a non-meta item but are logically before them.
- uint64_t cursor_mutation_id = cursor_item_idx->second.mutation_id;
+ int64_t cursor_mutation_id{cursor_item_idx->second.mutation_id};
if (cursor_item->isCheckPointMetaItem()) {
--cursor_mutation_id;
}
*/
enum queue_dirty_t {
/*
- * The item exists on the right hand side of the persistence cursor. The
- * item will be deduplicated and doesn't change the size of the checkpoint.
+ * The item exists on the right hand side of the persistence cursor - i.e.
+ * the persistence cursor has not yet processed this key.
+ * The item will be deduplicated and doesn't change the size of the checkpoint.
*/
EXISTING_ITEM,
/**
- * The item exists on the left hand side of the persistence cursor. It will
- * be dedeuplicated and moved the to right hand side, but the item needs
- * to be re-persisted.
+ * The item exists on the left hand side of the persistence cursor - i.e.
+ * the persistence cursor has already processed one (or more) instances of
+ * this key.
+ * It will be dedeuplicated and moved the to right hand side, but the item
+ * needs to be re-persisted.
*/
PERSIST_AGAIN,
createManager();
}
- void createManager() {
+ void createManager(int64_t last_seqno = 1000) {
manager.reset(new CheckpointManager(global_stats, vbucket->getId(),
checkpoint_config,
- /*lastSeqno*/1000,
+ last_seqno,
/*lastSnapStart*/0,/*lastSnapEnd*/0,
callback));
}
EXPECT_EQ(1002, items.at(0)->getBySeqno());
EXPECT_EQ("key", items.at(0)->getKey());
}
+
+// Regression test for MB-21925 - when a duplicate key is queued and the
+// persistence cursor is still positioned on the initial dummy key,
+// should return EXISTING_ITEM.
+TEST_F(CheckpointTest,
+ MB21925_QueueDuplicateWithPersistenceCursorOnInitialMetaItem) {
+
+ // Need a manager starting from seqno zero.
+ createManager(0);
+ ASSERT_EQ(0, manager->getHighSeqno());
+ ASSERT_EQ(1, manager->getNumItems())
+ << "Should start with queue_op::empty on checkpoint.";
+
+ // Add an item with some new key.
+ ASSERT_TRUE(queueNewItem("key"));
+
+ // Test - second item (duplicate key) should return false.
+ EXPECT_FALSE(queueNewItem("key"));
+}