diff --git a/tools/sst_dump.cc b/tools/sst_dump.cc index 903889556c..ba586aca12 100644 --- a/tools/sst_dump.cc +++ b/tools/sst_dump.cc @@ -15,6 +15,7 @@ #include "rocksdb/env.h" #include "rocksdb/iterator.h" #include "rocksdb/table.h" +#include "rocksdb/table_properties.h" #include "table/block.h" #include "table/block_builder.h" #include "table/format.h" @@ -38,22 +39,51 @@ class SstFileReader { bool has_to, const std::string& to_key); + Status ReadTableProperties(TableProperties* table_properties); uint64_t GetReadNumber() { return read_num_; } -private: + private: + Status NewTableReader(const std::string& file_path); + std::string file_name_; uint64_t read_num_; bool verify_checksum_; bool output_hex_; EnvOptions soptions_; + + Status init_result_; + unique_ptr table_reader_; + unique_ptr file_; + // table_options_ and internal_comparator_ will also be used in + // ReadSequential internally (specifically, seek-related operations) + Options table_options_; + InternalKeyComparator internal_comparator_; }; SstFileReader::SstFileReader(const std::string& file_path, bool verify_checksum, bool output_hex) - :file_name_(file_path), read_num_(0), verify_checksum_(verify_checksum), - output_hex_(output_hex) { - std::cout << "Process " << file_path << "\n"; + :file_name_(file_path), read_num_(0), verify_checksum_(verify_checksum), + output_hex_(output_hex), internal_comparator_(BytewiseComparator()) { + fprintf(stdout, "Process %s\n", file_path.c_str()); + + init_result_ = NewTableReader(file_name_); +} + +Status SstFileReader::NewTableReader(const std::string& file_path) { + table_options_.comparator = &internal_comparator_; + Status s = table_options_.env->NewRandomAccessFile(file_path, &file_, + soptions_); + if (!s.ok()) { + return s; + } + uint64_t file_size; + table_options_.env->GetFileSize(file_path, &file_size); + unique_ptr table_factory; + s = table_options_.table_factory->GetTableReader(table_options_, soptions_, + std::move(file_), file_size, + &table_reader_); + return s; } Status SstFileReader::ReadSequential(bool print_kv, @@ -61,29 +91,12 @@ Status SstFileReader::ReadSequential(bool print_kv, bool has_from, const std::string& from_key, bool has_to, - const std::string& to_key) -{ - unique_ptr table_reader; - InternalKeyComparator internal_comparator_(BytewiseComparator()); - Options table_options; - table_options.comparator = &internal_comparator_; - unique_ptr file; - Status s = table_options.env->NewRandomAccessFile(file_name_, &file, - soptions_); - if(!s.ok()) { - return s; - } - uint64_t file_size; - table_options.env->GetFileSize(file_name_, &file_size); - unique_ptr table_factory; - s = table_options.table_factory->GetTableReader(table_options, soptions_, - std::move(file), file_size, - &table_reader); - if(!s.ok()) { - return s; + const std::string& to_key) { + if (!table_reader_) { + return init_result_; } - Iterator* iter = table_reader->NewIterator(ReadOptions(verify_checksum_, + Iterator* iter = table_reader_->NewIterator(ReadOptions(verify_checksum_, false)); uint64_t i = 0; if (has_from) { @@ -113,21 +126,29 @@ Status SstFileReader::ReadSequential(bool print_kv, } if (print_kv) { - std::cout << ikey.DebugString(output_hex_) - << " => " - << value.ToString(output_hex_) << "\n"; + fprintf(stdout, "%s => %s\n", + ikey.DebugString(output_hex_).c_str(), + value.ToString(output_hex_).c_str()); } + } - } + read_num_ += i; - read_num_ += i; - - Status ret = iter->status(); - delete iter; - return ret; + Status ret = iter->status(); + delete iter; + return ret; } -} // namespace rocksdb +Status SstFileReader::ReadTableProperties(TableProperties* table_properties) { + if (!table_reader_) { + return init_result_; + } + + *table_properties = table_reader_->GetTableProperties(); + return init_result_; +} + +} // namespace rocksdb static void print_help() { fprintf(stderr, @@ -137,7 +158,8 @@ static void print_help() { " [--input_key_hex]" " [--from=]" " [--to=]" - " [--read_num=NUM]\n"); + " [--read_num=NUM]" + " [--show_properties]\n"); } string HexToString(const string& str) { @@ -158,7 +180,6 @@ string HexToString(const string& str) { } int main(int argc, char** argv) { - const char* dir_or_file = nullptr; uint64_t read_num = -1; std::string command; @@ -170,10 +191,10 @@ int main(int argc, char** argv) { bool input_key_hex = false; bool has_from = false; bool has_to = false; + bool show_properties = false; std::string from_key; std::string to_key; - for (int i = 1; i < argc; i++) - { + for (int i = 1; i < argc; i++) { if (strncmp(argv[i], "--file=", 7) == 0) { dir_or_file = argv[i] + 7; } else if (strcmp(argv[i], "--output_hex") == 0) { @@ -194,7 +215,9 @@ int main(int argc, char** argv) { } else if (strncmp(argv[i], "--to=", 5) == 0) { to_key = argv[i] + 5; has_to = true; - }else { + } else if (strcmp(argv[i], "--show_properties") == 0) { + show_properties = true; + } else { print_help(); exit(1); } @@ -210,7 +233,7 @@ int main(int argc, char** argv) { } } - if(dir_or_file == nullptr) { + if (dir_or_file == nullptr) { print_help(); exit(1); } @@ -225,18 +248,19 @@ int main(int argc, char** argv) { dir = false; } - std::cout << "from [" << rocksdb::Slice(from_key).ToString(true) - << "] to [" << rocksdb::Slice(to_key).ToString(true) << "]\n"; + fprintf(stdout, "from [%s] to [%s]\n", + rocksdb::Slice(from_key).ToString(true).c_str(), + rocksdb::Slice(to_key).ToString(true).c_str()); uint64_t total_read = 0; for (size_t i = 0; i < filenames.size(); i++) { std::string filename = filenames.at(i); if (filename.length() <= 4 || filename.rfind(".sst") != filename.length() - 4) { - //ignore + // ignore continue; } - if(dir) { + if (dir) { filename = std::string(dir_or_file) + "/" + filename; } rocksdb::SstFileReader reader(filename, verify_checksum, @@ -257,5 +281,20 @@ int main(int argc, char** argv) { break; } } + if (show_properties) { + rocksdb::TableProperties table_properties; + st = reader.ReadTableProperties(&table_properties); + if (!st.ok()) { + fprintf(stderr, "%s: %s\n", filename.c_str(), st.ToString().c_str()); + } else { + fprintf(stdout, + "Table Properties:\n" + "------------------------------\n" + " %s", table_properties.ToString("\n ", ": ").c_str()); + fprintf(stdout, "# deleted keys: %lu\n", + rocksdb::GetDeletedKeys( + table_properties.user_collected_properties)); + } + } } }