| // Copyright (c) 2011-present, Facebook, Inc. All rights reserved. |
| // This source code is licensed under both the GPLv2 (found in the |
| // COPYING file in the root directory) and Apache 2.0 License |
| // (found in the LICENSE.Apache file in the root directory). |
| |
| #include "db/table_properties_collector.h" |
| |
| #include "db/dbformat.h" |
| #include "util/coding.h" |
| #include "util/string_util.h" |
| |
| namespace rocksdb { |
| |
| Status InternalKeyPropertiesCollector::InternalAdd(const Slice& key, |
| const Slice& value, |
| uint64_t file_size) { |
| ParsedInternalKey ikey; |
| if (!ParseInternalKey(key, &ikey)) { |
| return Status::InvalidArgument("Invalid internal key"); |
| } |
| |
| // Note: We count both, deletions and single deletions here. |
| if (ikey.type == ValueType::kTypeDeletion || |
| ikey.type == ValueType::kTypeSingleDeletion) { |
| ++deleted_keys_; |
| } else if (ikey.type == ValueType::kTypeMerge) { |
| ++merge_operands_; |
| } |
| |
| return Status::OK(); |
| } |
| |
| Status InternalKeyPropertiesCollector::Finish( |
| UserCollectedProperties* properties) { |
| assert(properties); |
| assert(properties->find( |
| InternalKeyTablePropertiesNames::kDeletedKeys) == properties->end()); |
| assert(properties->find(InternalKeyTablePropertiesNames::kMergeOperands) == |
| properties->end()); |
| |
| std::string val_deleted_keys; |
| PutVarint64(&val_deleted_keys, deleted_keys_); |
| properties->insert( |
| {InternalKeyTablePropertiesNames::kDeletedKeys, val_deleted_keys}); |
| |
| std::string val_merge_operands; |
| PutVarint64(&val_merge_operands, merge_operands_); |
| properties->insert( |
| {InternalKeyTablePropertiesNames::kMergeOperands, val_merge_operands}); |
| |
| return Status::OK(); |
| } |
| |
| UserCollectedProperties |
| InternalKeyPropertiesCollector::GetReadableProperties() const { |
| return {{"kDeletedKeys", ToString(deleted_keys_)}, |
| {"kMergeOperands", ToString(merge_operands_)}}; |
| } |
| |
| namespace { |
| |
| EntryType GetEntryType(ValueType value_type) { |
| switch (value_type) { |
| case kTypeValue: |
| return kEntryPut; |
| case kTypeDeletion: |
| return kEntryDelete; |
| case kTypeSingleDeletion: |
| return kEntrySingleDelete; |
| case kTypeMerge: |
| return kEntryMerge; |
| default: |
| return kEntryOther; |
| } |
| } |
| |
| uint64_t GetUint64Property(const UserCollectedProperties& props, |
| const std::string property_name, |
| bool* property_present) { |
| auto pos = props.find(property_name); |
| if (pos == props.end()) { |
| *property_present = false; |
| return 0; |
| } |
| Slice raw = pos->second; |
| uint64_t val = 0; |
| *property_present = true; |
| return GetVarint64(&raw, &val) ? val : 0; |
| } |
| |
| } // namespace |
| |
| Status UserKeyTablePropertiesCollector::InternalAdd(const Slice& key, |
| const Slice& value, |
| uint64_t file_size) { |
| ParsedInternalKey ikey; |
| if (!ParseInternalKey(key, &ikey)) { |
| return Status::InvalidArgument("Invalid internal key"); |
| } |
| |
| return collector_->AddUserKey(ikey.user_key, value, GetEntryType(ikey.type), |
| ikey.sequence, file_size); |
| } |
| |
| Status UserKeyTablePropertiesCollector::Finish( |
| UserCollectedProperties* properties) { |
| return collector_->Finish(properties); |
| } |
| |
| UserCollectedProperties |
| UserKeyTablePropertiesCollector::GetReadableProperties() const { |
| return collector_->GetReadableProperties(); |
| } |
| |
| |
| const std::string InternalKeyTablePropertiesNames::kDeletedKeys |
| = "rocksdb.deleted.keys"; |
| const std::string InternalKeyTablePropertiesNames::kMergeOperands = |
| "rocksdb.merge.operands"; |
| |
| uint64_t GetDeletedKeys( |
| const UserCollectedProperties& props) { |
| bool property_present_ignored; |
| return GetUint64Property(props, InternalKeyTablePropertiesNames::kDeletedKeys, |
| &property_present_ignored); |
| } |
| |
| uint64_t GetMergeOperands(const UserCollectedProperties& props, |
| bool* property_present) { |
| return GetUint64Property( |
| props, InternalKeyTablePropertiesNames::kMergeOperands, property_present); |
| } |
| |
| } // namespace rocksdb |