#include "fielddb/field_db.h" #include #include #include #include "leveldb/db.h" #include "leveldb/env.h" #include "leveldb/options.h" #include "leveldb/status.h" #include "db/write_batch_internal.h" #include "util/serialize_value.h" #include "fielddb/encode_index.h" namespace fielddb { using namespace leveldb; //TODO:打开fieldDB Status FieldDB::OpenFieldDB(const Options& options, const std::string& name, FieldDB** dbptr) { // options.env->CreateDir("./abc") if(*dbptr == nullptr){ return Status::NotSupported(name, "new a fieldDb first\n"); } // Status status; DB *indexdb, *kvdb, *metadb; status = Open(options, name+"_indexDB", &indexdb); if(!status.ok()) return status; status = Open(options, name+"_kvDB", &kvdb); if(!status.ok()) return status; status = Open(options, name+"_metaDB", &metadb); if(!status.ok()) return status; (*dbptr)->indexDB_ = indexdb; (*dbptr)->kvDB_ = kvdb; (*dbptr)->metaDB_ = metadb; (*dbptr)->dbname_ = name; status = (*dbptr)->Recover(); return status; } // todo Status FieldDB::Recover() { // return Status::OK(); } Status FieldDB::Put(const WriteOptions &options, const Slice &key, const Slice &value) { return kvDB_->Put(options, key, value); } // TODO:需要对是否进行index更新做处理 Status FieldDB::PutFields(const WriteOptions &Options, const Slice &key, const FieldArray &fields) { // return kvDB_->PutFields(Options, key, fields); } // todo: 删除有索引的key时indexdb也要同步 Status FieldDB::Delete(const WriteOptions &options, const Slice &key) { // return kvDB_->Delete(options, key); } // TODO:根据updates里面的东西,要对是否需要更新index进行分别处理 Status FieldDB::Write(const WriteOptions &options, WriteBatch *updates) { return Status::OK(); } Status FieldDB::Get(const ReadOptions &options, const Slice &key, std::string *value) { return kvDB_->Get(options, key, value); } Status FieldDB::GetFields(const ReadOptions &options, const Slice &key, FieldArray *fields) { return kvDB_->GetFields(options, key, fields); } std::vector FieldDB::FindKeysByField(Field &field) { return kvDB_->FindKeysByField(field); } std::vector> FieldDB::FindKeysAndValByFieldName ( const std::string &fieldName){ std::vector> result; auto iter = kvDB_->NewIterator(ReadOptions()); std::string val; for(iter->SeekToFirst();iter->Valid();iter->Next()) { InternalFieldArray fields(iter->value()); val = fields.ValOfName(fieldName); if(!val.empty()) { result.push_back(std::make_pair(iter->key().ToString(), val)); } } return result; } Status FieldDB::CreateIndexOnField(const std::string& field_name) { //taskQueue相关 //写锁 是不是只需要给putfields设置一把锁就行 std::vector> keysAndVal = FindKeysAndValByFieldName(field_name); WriteBatch writeBatch; Slice value = Slice(); for (auto &kvPair : keysAndVal){ std::string indexKey; AppendIndexKey(&indexKey, ParsedInternalIndexKey(kvPair.first, field_name, kvPair.second)); writeBatch.Put(indexKey, value); } Status s = indexDB_->Write(WriteOptions(), &writeBatch); if (!s.ok()) return s; index_[field_name] = Exist; //唤醒taskqueue } Status FieldDB::DeleteIndex(const std::string &field_name) { //taskQueue相关 //写锁 std::vector> keysAndVal = FindKeysAndValByFieldName(field_name); WriteBatch writeBatch; for (auto &kvPair : keysAndVal){ std::string indexKey; AppendIndexKey(&indexKey, ParsedInternalIndexKey(kvPair.first, field_name, kvPair.second)); writeBatch.Delete(indexKey); } Status s = indexDB_->Write(WriteOptions(), &writeBatch); if (!s.ok()) return s; index_.erase(field_name); //唤醒taskqueue } std::vector FieldDB::QueryByIndex(const Field &field, Status *s) { if (index_.count(field.first) == 0 || index_[field.first] != Exist){ *s = Status::NotFound(Slice()); return std::vector(); } std::string indexKey; AppendIndexKey(&indexKey, ParsedInternalIndexKey(Slice(), field.first, field.second)); Iterator *indexIterator = indexDB_->NewIterator(ReadOptions()); indexIterator->Seek(indexKey); std::vector result; for (; indexIterator->Valid(); indexIterator->Next()) { ParsedInternalIndexKey iterKey; if (ParseInternalIndexKey(indexIterator->key(), &iterKey)){ if (iterKey.name_ == field.first && iterKey.val_ == field.second){ result.push_back(iterKey.user_key_.ToString()); continue; //查到说明在范围里,否则break } } break; } *s = Status::OK(); return result; } Iterator * FieldDB::NewIterator(const ReadOptions &options) { return kvDB_->NewIterator(options); } // TODO:使用统一seq进行snapshot管理 const Snapshot * FieldDB::GetSnapshot() { return kvDB_->GetSnapshot(); } // TODO:同上 void FieldDB::ReleaseSnapshot(const Snapshot *snapshot) { kvDB_->ReleaseSnapshot(snapshot); } bool FieldDB::GetProperty(const Slice &property, std::string *value) { return kvDB_->GetProperty(property, value) | indexDB_->GetProperty(property, value); } void FieldDB::GetApproximateSizes(const Range *range, int n, uint64_t *sizes) { uint64_t temp = 0; kvDB_->GetApproximateSizes(range, n, sizes); indexDB_->GetApproximateSizes(range, n, &temp); *sizes += temp; } void FieldDB::CompactRange(const Slice *begin, const Slice *end) { kvDB_->CompactRange(begin, end); } } // end of namespace