@@ -633,6 +633,65 @@ TEST_P(EPStoreEvictionTest, xattrExpiryOnFullyEvictedItem) {
633633 << " The foo attribute should be gone" ;
634634}
635635
636+ TEST_P (EPStoreEvictionTest, UnDelWithPrepare) {
637+ if (GetParam () == " value_only" ) {
638+ return ;
639+ }
640+
641+ store->setVBucketState (
642+ vbid,
643+ vbucket_state_active,
644+ {{" topology" , nlohmann::json::array ({{" active" , " replica" }})}});
645+
646+ // 1) Store, delete, and persist the item. We need to do this to ensure that
647+ // the bloom filter tells us to go to disk when we try gets if there is
648+ // no delete in the HashTable.
649+ auto key = makeStoredDocKey (" key" );
650+ storeAndDeleteItem (vbid, key, " value" );
651+ auto vb = store->getVBucket (vbid);
652+ EXPECT_EQ (0 , vb->getNumItems ());
653+
654+ // 1) Store the new item and persist
655+ store_item (vbid, key, " value" );
656+ flushVBucketToDiskIfPersistent (vbid, 1 );
657+ EXPECT_EQ (1 , vb->getNumItems ());
658+
659+ // 2) Store the new item but don't persist it yet. We want to test what
660+ // happens when it's dirty.
661+ delete_item (vbid, key);
662+
663+ // 1 because we haven't persisted the delete yet
664+ EXPECT_EQ (1 , vb->getNumItems ());
665+
666+ // 3) Get now returns not found
667+ auto options = static_cast <get_options_t >(
668+ QUEUE_BG_FETCH | HONOR_STATES | TRACK_REFERENCE | DELETE_TEMP |
669+ HIDE_LOCKED_CAS | TRACK_STATISTICS);
670+ auto gv = getInternal (key, vbid, cookie, ForGetReplicaOp::No, options);
671+ EXPECT_EQ (ENGINE_KEY_ENOENT, gv.getStatus ());
672+
673+ // 4) Add prepare
674+ auto prepare = makePendingItem (key, " value" );
675+ EXPECT_EQ (ENGINE_SYNC_WRITE_PENDING, store->add (*prepare, cookie));
676+ // EXPECT_EQ(ENGINE_SYNC_WRITE_PENDING, addItem(*prepare, cookie));
677+
678+ // 1 because we haven't persisted the delete yet
679+ EXPECT_EQ (1 , vb->getNumItems ());
680+
681+ // 5) Check that the HashTable state is now correct
682+ {
683+ auto htRes = vb->ht .findForUpdate (key);
684+ ASSERT_TRUE (htRes.committed );
685+ EXPECT_TRUE (htRes.committed ->isDeleted ());
686+ EXPECT_TRUE (htRes.pending );
687+ }
688+
689+ // @TODO RDB: Rocks item counting is broken and overcounts assuming
690+ // everything is a new item
691+ flushVBucketToDiskIfPersistent (vbid, 2 );
692+ EXPECT_EQ (0 , vb->getNumItems ());
693+ }
694+
636695/* *
637696 * Verify that when getIf is used it only fetches the metdata from disk for
638697 * the filter, and not the complete document.
0 commit comments