@ -1,12 +1,5 @@ | |||
<?xml version="1.0" encoding="UTF-8"?> | |||
<project version="4"> | |||
<component name="BackendCodeEditorMiscSettings"> | |||
<option name="/Default/RiderDebugger/RiderRestoreDecompile/RestoreDecompileSetting/@EntryValue" value="false" type="bool" /> | |||
<option name="/Default/Housekeeping/GlobalSettingsUpgraded/IsUpgraded/@EntryValue" value="true" type="bool" /> | |||
<option name="/Default/Housekeeping/FeatureSuggestion/FeatureSuggestionManager/DisabledSuggesters/=SwitchToGoToActionSuggester/@EntryIndexedValue" value="true" type="bool" /> | |||
<option name="/Default/Housekeeping/FeatureSuggestion/FeatureSuggestionManager/DisabledSuggesters/=SwitchToGoToActionSuggester/@EntryIndexRemoved" /> | |||
<option name="/Default/Environment/Hierarchy/GeneratedFilesCacheKey/Timestamp/@EntryValue" value="5" type="long" /> | |||
</component> | |||
<component name="CMakePythonSetting"> | |||
<option name="pythonIntegrationState" value="YES" /> | |||
</component> | |||
@ -1,15 +1,36 @@ | |||
#include "table/vtable_builder.h" | |||
#include "leveldb/env.h" | |||
namespace leveldb { | |||
VTableBuilder::VTableBuilder(const Options& options, WritableFile* file) | |||
: file_(file) {} | |||
: file_(file), | |||
encoder_() {} | |||
void VTableBuilder::Add(const VTableRecord& record, VTableHandle* handle) { | |||
if (!ok()) return; | |||
encoder_.Encode(record); | |||
handle->offset = file_size_; | |||
handle->size = encoder_.GetEncodedSize(); | |||
file_size_ += encoder_.GetEncodedSize(); | |||
status_ = file_->Append(encoder_.GetHeader().ToString() + | |||
encoder_.GetRecord().ToString()); | |||
assert(ok()); | |||
//TODO: meta info support in the future | |||
} | |||
Status VTableBuilder::Finish() { | |||
if (!ok()) return status(); | |||
status_ = file_->Flush(); | |||
return status(); | |||
} | |||
void VTableBuilder::Abandon() { } | |||
} // namespace leveldb |
@ -0,0 +1,39 @@ | |||
#include <string> | |||
#include "leveldb/env.h" | |||
#include <table/vtable_reader.h> | |||
namespace leveldb { | |||
Status VTableReader::Open(const Options& options, std::string fname) { | |||
options_ = options; | |||
return options_.env->NewRandomAccessFile(fname, &file_); | |||
} | |||
Status VTableReader::Get(const VTableHandle& handle, | |||
VTableRecord* record) const { | |||
auto buf = new char[handle.size]; | |||
Slice input; | |||
Status s = file_->Read(handle.offset, handle.size, &input, buf); | |||
if (!s.ok()) { | |||
return s; | |||
} | |||
if (handle.size != static_cast<uint64_t>(input.size())) { | |||
return Status::Corruption("Read input size not equal to record size: " + | |||
std::to_string(input.size()) + ":" + | |||
std::to_string(handle.size)); | |||
} | |||
RecordDecoder decoder; | |||
s = decoder.DecodeHeader(&input); | |||
if (!s.ok()) { | |||
return s; | |||
} | |||
s = decoder.DecodeRecord(&input, record); | |||
return s; | |||
} | |||
} // namespace leveldb |
@ -0,0 +1,30 @@ | |||
#ifndef VTABLE_READER_H | |||
#define VTABLE_READER_H | |||
#include <memory> | |||
#include "leveldb/env.h" | |||
#include "leveldb/options.h" | |||
#include "leveldb/slice.h" | |||
#include "leveldb/status.h" | |||
#include "util/coding.h" | |||
#include "vtable_format.h" | |||
namespace leveldb { | |||
class VTableReader { | |||
public: | |||
Status Open(const Options& options, std::string fname); | |||
Status Get(const VTableHandle& handle, | |||
VTableRecord* record) const ; | |||
private: | |||
Options options_; | |||
RandomAccessFile* file_{nullptr}; | |||
}; | |||
} // namespace leveldb | |||
#endif //VTABLE_READER_H |
@ -0,0 +1,43 @@ | |||
#include <iostream> | |||
#include <gtest/gtest.h> | |||
#include "leveldb/db.h" | |||
#include "leveldb/env.h" | |||
#include "table/vtable_builder.h" | |||
#include "table/vtable_reader.h" | |||
#include "table/vtable_format.h" | |||
using namespace std; | |||
using namespace leveldb; | |||
int main() { | |||
VTableHandle handle1; | |||
VTableHandle handle2; | |||
VTableRecord record1; | |||
VTableRecord record2; | |||
record1.key = "001"; | |||
record1.value = "value1"; | |||
record2.key = "002"; | |||
record2.value = "value2"; | |||
Options opt; | |||
WritableFile *file; | |||
opt.env->NewWritableFile("1.vtb", &file); | |||
VTableBuilder builder(opt, file); | |||
builder.Add(record1, &handle1); | |||
builder.Add(record2, &handle2); | |||
builder.Finish(); | |||
VTableReader reader; | |||
reader.Open(opt, "1.vtb"); | |||
VTableRecord res_record; | |||
reader.Get(handle2, &res_record); | |||
cout << res_record.key.ToString() << " " << res_record.value.ToString() << endl; | |||
reader.Get(handle1, &res_record); | |||
cout << res_record.key.ToString() << " " << res_record.value.ToString() << endl; | |||
} |