diff --git a/CMakeLists.txt b/CMakeLists.txt index fda9e01bb..060c3d602 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -330,6 +330,7 @@ if(LEVELDB_BUILD_TESTS) "db/autocompact_test.cc" "db/corruption_test.cc" "db/db_test.cc" + "db/snapshot_test.cc" "db/dbformat_test.cc" "db/filename_test.cc" "db/log_test.cc" diff --git a/db/db_impl.cc b/db/db_impl.cc index f96d24558..8ca2b731b 100644 --- a/db/db_impl.cc +++ b/db/db_impl.cc @@ -1575,4 +1575,12 @@ Status DestroyDB(const std::string& dbname, const Options& options) { return result; } +std::vector DBImpl::GetAllSnapshots() { + std::vector snapshots; + mutex_.Lock(); + snapshots = snapshots_.GetAllSnapshots(); // Call the SnapshotList method + mutex_.Unlock(); + return snapshots; +} + } // namespace leveldb diff --git a/db/db_impl.h b/db/db_impl.h index c7b01721b..d98ab1e94 100644 --- a/db/db_impl.h +++ b/db/db_impl.h @@ -9,6 +9,7 @@ #include #include #include +#include #include "db/dbformat.h" #include "db/log_writer.h" @@ -48,6 +49,9 @@ class DBImpl : public DB { bool GetProperty(const Slice& property, std::string* value) override; void GetApproximateSizes(const Range* range, int n, uint64_t* sizes) override; void CompactRange(const Slice* begin, const Slice* end) override; + + // Retrieve all active snapshots in the database + std::vector GetAllSnapshots() override; // Extra methods (for testing) that are not in the public DB interface diff --git a/db/snapshot.h b/db/snapshot.h index 817bb7ba1..5be56ac99 100644 --- a/db/snapshot.h +++ b/db/snapshot.h @@ -85,6 +85,17 @@ class SnapshotList { delete snapshot; } + // Retrieves all snapshots in the list. + // + // This method iterates through the linked list and collects all snapshots. + std::vector GetAllSnapshots() const { + std::vector snapshots; + for (const SnapshotImpl* s = head_.next_; s != &head_; s = s->next_) { + snapshots.push_back(static_cast(s)); + } + return snapshots; + } + private: // Dummy head of doubly-linked list of snapshots SnapshotImpl head_; diff --git a/db/snapshot_test.cc b/db/snapshot_test.cc new file mode 100644 index 000000000..ea1b03f31 --- /dev/null +++ b/db/snapshot_test.cc @@ -0,0 +1,30 @@ +#include "db/db_impl.h" +#include "gtest/gtest.h" + +namespace leveldb { + +// Test to validate GetAllSnapshots retrieves all snapshots correctly. +TEST(SnapshotTest, GetAllSnapshots) { + SnapshotList snapshot_list; + + // Create some snapshots + SnapshotImpl* s1 = snapshot_list.New(1); + SnapshotImpl* s2 = snapshot_list.New(2); + SnapshotImpl* s3 = snapshot_list.New(3); + + // Use GetAllSnapshots to retrieve them + std::vector snapshots = snapshot_list.GetAllSnapshots(); + + // Validate the results + ASSERT_EQ(snapshots.size(), 3); + EXPECT_EQ(static_cast(snapshots[0])->sequence_number(), 1); + EXPECT_EQ(static_cast(snapshots[1])->sequence_number(), 2); + EXPECT_EQ(static_cast(snapshots[2])->sequence_number(), 3); + + // Clean up + snapshot_list.Delete(s1); + snapshot_list.Delete(s2); + snapshot_list.Delete(s3); +} + +} diff --git a/include/leveldb/db.h b/include/leveldb/db.h index a13d14716..a79aa9c2a 100644 --- a/include/leveldb/db.h +++ b/include/leveldb/db.h @@ -145,6 +145,9 @@ class LEVELDB_EXPORT DB { // Therefore the following call will compact the entire database: // db->CompactRange(nullptr, nullptr); virtual void CompactRange(const Slice* begin, const Slice* end) = 0; + + // Retrieve all active snapshots in the database. + virtual std::vector GetAllSnapshots() = 0; }; // Destroy the contents of the specified database.