|
@ -1,8 +1,13 @@ |
|
|
#include "gtest/gtest.h"
|
|
|
#include "gtest/gtest.h"
|
|
|
#include "leveldb/env.h"
|
|
|
#include "leveldb/env.h"
|
|
|
#include "leveldb/db.h"
|
|
|
#include "leveldb/db.h"
|
|
|
|
|
|
#include "util/coding.h"
|
|
|
|
|
|
|
|
|
using namespace leveldb; |
|
|
using namespace leveldb; |
|
|
|
|
|
|
|
|
|
|
|
using Field=std::pair<Slice,Slice>; |
|
|
|
|
|
using FieldArray=std::vector<std::pair<Slice, Slice>>; |
|
|
|
|
|
|
|
|
constexpr int value_size = 2048; |
|
|
constexpr int value_size = 2048; |
|
|
constexpr int data_size = 128 << 20; |
|
|
constexpr int data_size = 128 << 20; |
|
|
|
|
|
|
|
@ -12,7 +17,73 @@ Status OpenDB(std::string dbName, DB **db) { |
|
|
return DB::Open(options, dbName, db); |
|
|
return DB::Open(options, dbName, db); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
TEST(TestTTL, OurTTL) { |
|
|
|
|
|
|
|
|
bool CompareFieldArray(const FieldArray &a, const FieldArray &b) { |
|
|
|
|
|
if (a.size() != b.size()) return false; |
|
|
|
|
|
for (size_t i = 0; i < a.size(); ++i) { |
|
|
|
|
|
if (a[i].first != b[i].first || a[i].second != b[i].second) return false; |
|
|
|
|
|
} |
|
|
|
|
|
return true; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
bool CompareKey(const std::vector<std::string> a, std::vector<std::string> b) { |
|
|
|
|
|
if (a.size() != b.size()) return false; |
|
|
|
|
|
for (size_t i = 0; i < a.size(); ++i) { |
|
|
|
|
|
if (a[i] != b[i]) return false; |
|
|
|
|
|
} |
|
|
|
|
|
return true; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
std::string SerializeValue(const FieldArray& fields){ |
|
|
|
|
|
std::string res_=""; |
|
|
|
|
|
PutVarint64(&res_,(uint64_t)fields.size()); |
|
|
|
|
|
for(auto pr:fields){ |
|
|
|
|
|
PutLengthPrefixedSlice(&res_, pr.first); |
|
|
|
|
|
PutLengthPrefixedSlice(&res_, pr.second); |
|
|
|
|
|
} |
|
|
|
|
|
return res_; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// 反序列化为字段数组
|
|
|
|
|
|
void DeserializeValue(const std::string& value_str,FieldArray* res){ |
|
|
|
|
|
Slice slice=Slice(value_str.c_str()); |
|
|
|
|
|
uint64_t siz; |
|
|
|
|
|
bool tmpres=GetVarint64(&slice,&siz); |
|
|
|
|
|
assert(tmpres); |
|
|
|
|
|
res->clear(); |
|
|
|
|
|
for(int i=0;i<siz;i++){ |
|
|
|
|
|
Slice value_name; |
|
|
|
|
|
Slice value; |
|
|
|
|
|
tmpres=GetLengthPrefixedSlice(&slice,&value_name); |
|
|
|
|
|
assert(tmpres); |
|
|
|
|
|
tmpres=GetLengthPrefixedSlice(&slice,&value); |
|
|
|
|
|
assert(tmpres); |
|
|
|
|
|
res->emplace_back(value_name,value); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
Status Get_keys_by_field(DB *db,const ReadOptions& options, const Field field,std::vector<std::string> *keys){ |
|
|
|
|
|
auto it=db->NewIterator(options); |
|
|
|
|
|
it->SeekToFirst(); |
|
|
|
|
|
keys->clear(); |
|
|
|
|
|
while(it->Valid()){ |
|
|
|
|
|
auto val=it->value(); |
|
|
|
|
|
FieldArray arr; |
|
|
|
|
|
auto str_val=std::string(val.data(),val.size()); |
|
|
|
|
|
DeserializeValue(str_val,&arr); |
|
|
|
|
|
for(auto pr:arr){ |
|
|
|
|
|
if(pr.first==field.first&&pr.second==field.second){ |
|
|
|
|
|
Slice key=it->key(); |
|
|
|
|
|
keys->push_back(std::string(key.data(),key.size())); |
|
|
|
|
|
break; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
it->Next(); |
|
|
|
|
|
} |
|
|
|
|
|
delete it; |
|
|
|
|
|
return Status::OK(); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
TEST(Test, CheckGetFields) { |
|
|
DB *db; |
|
|
DB *db; |
|
|
WriteOptions writeOptions; |
|
|
WriteOptions writeOptions; |
|
|
ReadOptions readOptions; |
|
|
ReadOptions readOptions; |
|
@ -20,36 +91,67 @@ TEST(TestTTL, OurTTL) { |
|
|
std::cerr << "open db failed" << std::endl; |
|
|
std::cerr << "open db failed" << std::endl; |
|
|
abort(); |
|
|
abort(); |
|
|
} |
|
|
} |
|
|
std::string key = "k_1"; |
|
|
|
|
|
|
|
|
std::string key1 = "k_1"; |
|
|
|
|
|
std::string key2 = "k_2"; |
|
|
|
|
|
|
|
|
std::string key1 = "k_2"; |
|
|
|
|
|
|
|
|
|
|
|
FieldArray fields = { |
|
|
|
|
|
|
|
|
FieldArray fields1 = { |
|
|
{"name", "Customer#000000001"}, |
|
|
{"name", "Customer#000000001"}, |
|
|
{"address", "IVhzIApeRb"}, |
|
|
{"address", "IVhzIApeRb"}, |
|
|
{"phone", "25-989-741-2988"} |
|
|
{"phone", "25-989-741-2988"} |
|
|
}; |
|
|
}; |
|
|
|
|
|
|
|
|
FieldArray fields1 = { |
|
|
|
|
|
|
|
|
FieldArray fields2 = { |
|
|
{"name", "Customer#000000001"}, |
|
|
{"name", "Customer#000000001"}, |
|
|
{"address", "abc"}, |
|
|
{"address", "abc"}, |
|
|
{"phone", "def"} |
|
|
{"phone", "def"} |
|
|
}; |
|
|
}; |
|
|
|
|
|
|
|
|
db->Put_with_fields(WriteOptions(), key, fields); |
|
|
|
|
|
|
|
|
auto value1=SerializeValue(fields1); |
|
|
|
|
|
auto value2=SerializeValue(fields2); |
|
|
|
|
|
|
|
|
db->Put_with_fields(WriteOptions(), key1, fields1); |
|
|
|
|
|
|
|
|
db->Put(WriteOptions(), key1, value1); |
|
|
|
|
|
db->Put(WriteOptions(), key2, value2); |
|
|
|
|
|
|
|
|
// 读取并反序列化
|
|
|
// 读取并反序列化
|
|
|
FieldArray value_ret; |
|
|
|
|
|
db->Get_with_fields(ReadOptions(), key, &value_ret);; |
|
|
|
|
|
for(auto pr:value_ret){ |
|
|
|
|
|
|
|
|
std::string value_ret; |
|
|
|
|
|
FieldArray res1; |
|
|
|
|
|
|
|
|
|
|
|
db->Get(ReadOptions(), key1, &value_ret); |
|
|
|
|
|
DeserializeValue(value_ret, &res1); |
|
|
|
|
|
for(auto pr:res1){ |
|
|
std::cout<<std::string(pr.first.data(),pr.first.size())<<" "<<std::string(pr.second.data(),pr.second.size())<<"\n"; |
|
|
std::cout<<std::string(pr.first.data(),pr.first.size())<<" "<<std::string(pr.second.data(),pr.second.size())<<"\n"; |
|
|
} |
|
|
} |
|
|
|
|
|
ASSERT_TRUE(CompareFieldArray(fields1, res1)); |
|
|
|
|
|
|
|
|
|
|
|
std::cout<<"get serialized value done"<<std::endl; |
|
|
|
|
|
delete db; |
|
|
|
|
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
TEST(Test, CheckSearchKey) { |
|
|
|
|
|
DB *db; |
|
|
|
|
|
ReadOptions readOptions; |
|
|
|
|
|
if(OpenDB("testdb_for_XOY", &db).ok() == false) { |
|
|
|
|
|
std::cerr << "open db failed" << std::endl; |
|
|
|
|
|
abort(); |
|
|
|
|
|
} |
|
|
|
|
|
std::string key1 = "k_1"; |
|
|
|
|
|
std::string key2 = "k_2"; |
|
|
|
|
|
|
|
|
|
|
|
FieldArray fields1 = { |
|
|
|
|
|
{"name", "Customer#000000001"}, |
|
|
|
|
|
{"address", "IVhzIApeRb"}, |
|
|
|
|
|
{"phone", "25-989-741-2988"} |
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
std::vector<std::string> keys = {key1, key2}; |
|
|
|
|
|
std::vector<std::string> key_res; |
|
|
|
|
|
Get_keys_by_field(db,ReadOptions(),fields1[0],&key_res); |
|
|
|
|
|
for(auto s:key_res)std::cout<<s<<"\n"; |
|
|
|
|
|
|
|
|
|
|
|
ASSERT_TRUE(CompareKey(key_res, keys)); |
|
|
|
|
|
|
|
|
std::vector<std::string> v; |
|
|
|
|
|
db->Get_keys_by_field(ReadOptions(),fields[0],&v); |
|
|
|
|
|
for(auto s:v)std::cout<<s<<"\n"; |
|
|
|
|
|
|
|
|
std::cout<<"get key by field done"<<std::endl; |
|
|
delete db; |
|
|
delete db; |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|