2023-07-19 19:07:53 +08:00
|
|
|
|
//
|
|
|
|
|
// Created by shuxin <20><><EFBFBD><EFBFBD>zheng on 2023/7/19.
|
|
|
|
|
//
|
|
|
|
|
|
|
|
|
|
#include "stdafx.h"
|
|
|
|
|
#include "redis_object.h"
|
|
|
|
|
|
|
|
|
|
namespace pkv {
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
redis_object::redis_object(std::vector<redis_object*>& cache, size_t cache_max)
|
|
|
|
|
: parent_(this)
|
|
|
|
|
, cache_max_(cache_max)
|
|
|
|
|
, cache_(cache)
|
|
|
|
|
{
|
2023-07-21 14:20:47 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-24 18:16:09 +08:00
|
|
|
|
redis_object::~redis_object() {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
for (auto obj : objs_) {
|
|
|
|
|
delete obj;
|
|
|
|
|
}
|
2023-07-24 18:16:09 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
void redis_object::set_parent(redis_object* parent) {
|
|
|
|
|
if (parent) {
|
|
|
|
|
parent_ = parent;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void redis_object::reset() {
|
|
|
|
|
for (auto obj : objs_) {
|
|
|
|
|
if (cache_.size() < cache_max_) {
|
|
|
|
|
obj->reset();
|
|
|
|
|
cache_.emplace_back(obj);
|
|
|
|
|
} else {
|
|
|
|
|
delete obj;
|
|
|
|
|
}
|
2023-07-21 19:12:12 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
status_ = redis_s_begin;
|
|
|
|
|
type_ = REDIS_OBJ_UNKOWN;
|
|
|
|
|
parent_ = this;
|
|
|
|
|
obj_ = nullptr;
|
|
|
|
|
cnt_ = 0;
|
|
|
|
|
|
|
|
|
|
objs_.clear();
|
|
|
|
|
buf_.clear();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const char* redis_object::get_cmd() const {
|
|
|
|
|
if (type_ == REDIS_OBJ_STRING) {
|
|
|
|
|
return buf_.c_str();
|
2023-07-21 19:12:12 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
if (objs_.empty() || type_ != REDIS_OBJ_ARRAY) {
|
2023-07-21 19:12:12 +08:00
|
|
|
|
return nullptr;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return objs_[0]->get_cmd();
|
|
|
|
|
}
|
|
|
|
|
|
2023-07-23 23:18:37 +08:00
|
|
|
|
const char* redis_object::get_str() const {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
if (type_ == REDIS_OBJ_STRING) {
|
|
|
|
|
return buf_.c_str();
|
2023-07-23 23:18:37 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return nullptr;
|
|
|
|
|
}
|
|
|
|
|
|
2023-07-19 19:07:53 +08:00
|
|
|
|
struct status_machine {
|
|
|
|
|
/* ״̬<D7B4><CCAC> */
|
|
|
|
|
int status;
|
|
|
|
|
|
|
|
|
|
/* ״̬<D7B4><CCAC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> */
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* (redis_object::*func) (const char*, size_t&);
|
2023-07-19 19:07:53 +08:00
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
static struct status_machine status_tab[] = {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
{ redis_s_begin, &redis_object::parse_begin },
|
|
|
|
|
{ redis_s_status, &redis_object::parse_status },
|
|
|
|
|
{ redis_s_error, &redis_object::parse_error },
|
2023-07-19 19:07:53 +08:00
|
|
|
|
{ redis_s_number, &redis_object::parse_number },
|
|
|
|
|
{ redis_s_strlen, &redis_object::parse_strlen },
|
|
|
|
|
{ redis_s_string, &redis_object::parse_string },
|
2023-07-20 19:24:18 +08:00
|
|
|
|
{ redis_s_strend, &redis_object::parse_strend },
|
|
|
|
|
{ redis_s_arlen, &redis_object::parse_arlen },
|
|
|
|
|
{ redis_s_array, &redis_object::parse_array },
|
2023-07-19 19:07:53 +08:00
|
|
|
|
};
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::update(const char *data, size_t& len) {
|
|
|
|
|
if (failed() || finish()) {
|
|
|
|
|
return data;
|
|
|
|
|
}
|
2023-07-19 19:07:53 +08:00
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (obj_) {
|
|
|
|
|
return parse_object(data, len);
|
|
|
|
|
}
|
2023-07-19 19:07:53 +08:00
|
|
|
|
|
|
|
|
|
while (len > 0) {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
data = (this->*(status_tab[status_].func))(data, len);
|
|
|
|
|
if (status_ == redis_s_null || status_ == redis_s_finish) {
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return data;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const char* redis_object::parse_object(const char* data, size_t& len) {
|
|
|
|
|
assert(cnt_ > 0);
|
|
|
|
|
assert(obj_);
|
|
|
|
|
|
|
|
|
|
data = obj_->update(data, len);
|
|
|
|
|
if (obj_->failed()) {
|
|
|
|
|
status_ = redis_s_null;
|
|
|
|
|
return data;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (!obj_->finish()) {
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
objs_.emplace_back(obj_);
|
|
|
|
|
|
|
|
|
|
if (objs_.size() == (size_t) cnt_) {
|
|
|
|
|
obj_ = nullptr;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
//cnt_ = 0;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
status_ = redis_s_finish;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
} else if (cache_.empty()) {
|
|
|
|
|
obj_ = new redis_object(cache_, cache_max_);
|
|
|
|
|
obj_->set_parent(this);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
} else {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
obj_ = cache_.back();
|
|
|
|
|
obj_->set_parent(this);
|
|
|
|
|
cache_.pop_back();
|
2023-07-20 19:24:18 +08:00
|
|
|
|
}
|
2023-07-26 15:50:15 +08:00
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_begin(const char* data, size_t& len) {
|
2023-07-19 19:07:53 +08:00
|
|
|
|
if (len == 0) {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
switch (*data) {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
case ':': // INTEGER
|
|
|
|
|
status_ = redis_s_number;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
break;
|
|
|
|
|
case '+': // STATUS
|
|
|
|
|
status_ = redis_s_status;
|
|
|
|
|
break;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
case '-': // ERROR
|
|
|
|
|
status_ = redis_s_error;
|
|
|
|
|
break;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
case '$': // STRING
|
|
|
|
|
status_ = redis_s_strlen;
|
|
|
|
|
break;
|
|
|
|
|
case '*': // ARRAY
|
|
|
|
|
status_ = redis_s_arlen;
|
|
|
|
|
break;
|
|
|
|
|
default: // INVALID
|
|
|
|
|
status_ = redis_s_null;
|
|
|
|
|
break;
|
|
|
|
|
}
|
2023-07-20 19:24:18 +08:00
|
|
|
|
|
|
|
|
|
len--;
|
|
|
|
|
data++;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_status(const char* data, size_t& len) {
|
2023-07-19 19:07:53 +08:00
|
|
|
|
bool found = false;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
data = get_line(data, len, buf_, found);
|
2023-07-19 19:07:53 +08:00
|
|
|
|
if (!found) {
|
|
|
|
|
assert(len == 0);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (buf_.empty()) {
|
|
|
|
|
status_ = redis_s_null;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_STATUS;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
status_ = redis_s_finish;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_error(const char* data, size_t& len) {
|
|
|
|
|
bool found = false;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
data = get_line(data, len, buf_, found);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (!found) {
|
|
|
|
|
assert(len == 0);
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (buf_.empty()) {
|
|
|
|
|
status_ = redis_s_null;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_ERROR;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
status_ = redis_s_finish;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_number(const char* data, size_t& len) {
|
|
|
|
|
bool found = false;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
data = get_line(data, len, buf_, found);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (!found) {
|
|
|
|
|
assert(len == 0);
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (buf_.empty()) {
|
|
|
|
|
status_ = redis_s_null;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
2023-07-20 19:24:18 +08:00
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_INTEGER;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
status_ = redis_s_finish;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_strlen(const char* data, size_t& len) {
|
2023-07-21 14:20:47 +08:00
|
|
|
|
bool found = false;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
cnt_ = 0;
|
2023-07-21 14:20:47 +08:00
|
|
|
|
data = get_length(data, len, cnt_, found);
|
|
|
|
|
if (status_ == redis_s_null || !found) {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (cnt_ <= 0) {
|
|
|
|
|
status_ = redis_s_finish;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_STRING;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
status_ = redis_s_string;
|
|
|
|
|
return data;
|
|
|
|
|
}
|
2023-07-19 19:07:53 +08:00
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_string(const char* data, size_t& len) {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
buf_.reserve((size_t) cnt_);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
data = get_data(data, len, (size_t) cnt_);
|
|
|
|
|
if (buf_.size() == (size_t) cnt_) {
|
|
|
|
|
status_ = redis_s_strend;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_strend(const char* data, size_t& len) {
|
2023-07-19 19:07:53 +08:00
|
|
|
|
bool found = false;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
std::string buf;
|
|
|
|
|
data = get_line(data, len, buf, found);
|
2023-07-19 19:07:53 +08:00
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
// If the buf_ not empty, some data other '\r\n' got.
|
2023-07-26 15:50:15 +08:00
|
|
|
|
if (!buf.empty()) {
|
2023-07-19 19:07:53 +08:00
|
|
|
|
status_ = redis_s_null;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (!found) {
|
|
|
|
|
assert(len == 0);
|
|
|
|
|
return data;
|
|
|
|
|
}
|
2023-07-19 19:07:53 +08:00
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
status_ = redis_s_finish;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_arlen(const char* data, size_t& len) {
|
2023-07-21 14:20:47 +08:00
|
|
|
|
bool found = false;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
cnt_ = 0;
|
2023-07-21 14:20:47 +08:00
|
|
|
|
data = get_length(data, len, cnt_, found);
|
|
|
|
|
if (status_ == redis_s_null || !found) {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (cnt_ <= 0) {
|
|
|
|
|
status_ = redis_s_finish;
|
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_ARRAY;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
status_ = redis_s_array;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
|
|
|
|
|
if (cache_.empty()) {
|
|
|
|
|
obj_ = new redis_object(cache_, cache_max_);
|
|
|
|
|
obj_->set_parent(this);
|
|
|
|
|
} else {
|
|
|
|
|
obj_ = cache_.back();
|
|
|
|
|
obj_->set_parent(this);
|
|
|
|
|
cache_.pop_back();
|
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::parse_array(const char* data, size_t& len) {
|
|
|
|
|
assert(obj_ != nullptr);
|
|
|
|
|
|
|
|
|
|
return parse_object(data, len);
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
const char* redis_object::get_data(const char* data, size_t& len, size_t want) {
|
2023-07-19 19:07:53 +08:00
|
|
|
|
size_t n = buf_.size();
|
|
|
|
|
assert(n < want);
|
|
|
|
|
|
|
|
|
|
want -= n;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
|
|
|
|
|
#if 1
|
|
|
|
|
if (want > len) {
|
|
|
|
|
want = len;
|
|
|
|
|
len = 0;
|
|
|
|
|
} else {
|
|
|
|
|
len -= want;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
buf_.append(data, want);
|
|
|
|
|
data += want;
|
|
|
|
|
#else
|
2023-07-19 19:07:53 +08:00
|
|
|
|
for (size_t i = 0; i < want && len > 0; i++) {
|
|
|
|
|
buf_.push_back(*data++);
|
|
|
|
|
len--;
|
|
|
|
|
}
|
2023-07-26 15:50:15 +08:00
|
|
|
|
#endif
|
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-21 14:20:47 +08:00
|
|
|
|
const char* redis_object::get_length(const char* data, size_t& len,
|
|
|
|
|
int& res, bool& found) {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
data = get_line(data, len, buf_, found);
|
2023-07-19 19:07:53 +08:00
|
|
|
|
if (!found) {
|
|
|
|
|
assert(len == 0);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (buf_.empty()) {
|
|
|
|
|
status_ = redis_s_null;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-21 14:20:47 +08:00
|
|
|
|
// buf_.push_back('\0'); // The c++11 promise the last char is null.
|
|
|
|
|
char* endptr;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
res = (int) strtol(buf_.c_str(), &endptr, 10);
|
2023-07-19 19:07:53 +08:00
|
|
|
|
buf_.clear();
|
2023-07-21 14:20:47 +08:00
|
|
|
|
|
|
|
|
|
if (endptr == buf_.c_str() || *endptr != '\0') {
|
|
|
|
|
status_ = redis_s_null;
|
|
|
|
|
return data;
|
|
|
|
|
}
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
const char* redis_object::get_line(const char* data, size_t& len,
|
|
|
|
|
std::string& buf, bool& found) {
|
2023-07-19 19:07:53 +08:00
|
|
|
|
while (len > 0) {
|
|
|
|
|
switch (*data) {
|
|
|
|
|
case '\r':
|
|
|
|
|
data++;
|
|
|
|
|
len--;
|
|
|
|
|
break;
|
|
|
|
|
case '\n':
|
2023-07-20 19:24:18 +08:00
|
|
|
|
data++;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
len--;
|
|
|
|
|
found = true;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
default:
|
2023-07-26 15:50:15 +08:00
|
|
|
|
buf.push_back(*data++);
|
2023-07-19 19:07:53 +08:00
|
|
|
|
len--;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return data;
|
2023-07-19 19:07:53 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 17:36:06 +08:00
|
|
|
|
bool redis_object::to_string(std::string& out) const {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
#define USE_UNIX_CRLF
|
|
|
|
|
#ifdef USE_UNIX_CRLF
|
|
|
|
|
#define CRLF "\n"
|
|
|
|
|
#else
|
|
|
|
|
#define CRLF "\r\n"
|
|
|
|
|
#endif
|
|
|
|
|
|
|
|
|
|
if (!objs_.empty()) {
|
2023-07-26 17:36:06 +08:00
|
|
|
|
out += objs_.size();
|
|
|
|
|
out += CRLF;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
|
2023-07-20 22:56:34 +08:00
|
|
|
|
for (const auto& obj : objs_) {
|
2023-07-20 19:24:18 +08:00
|
|
|
|
if (!obj->to_string(out)) {
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
//assert(!buf_.empty());
|
2023-07-20 19:24:18 +08:00
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
switch (type_) {
|
|
|
|
|
case REDIS_OBJ_STATUS:
|
2023-07-26 17:36:06 +08:00
|
|
|
|
out += "+";
|
|
|
|
|
out.append(buf_.c_str(), buf_.size());
|
|
|
|
|
out.append(CRLF);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
break;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
case REDIS_OBJ_ERROR:
|
2023-07-26 17:36:06 +08:00
|
|
|
|
out.append("-");
|
|
|
|
|
out.append(buf_.c_str(), buf_.size());
|
|
|
|
|
out.append(CRLF);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
break;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
case REDIS_OBJ_INTEGER:
|
2023-07-26 17:36:06 +08:00
|
|
|
|
out.append(":").append(buf_.c_str(), buf_.size()).append(CRLF);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
break;
|
2023-07-26 15:50:15 +08:00
|
|
|
|
case REDIS_OBJ_STRING:
|
2023-07-26 17:36:06 +08:00
|
|
|
|
out.append("$");
|
|
|
|
|
out += buf_.size();
|
|
|
|
|
out.append(CRLF).append(buf_.c_str(), buf_.size()).append(CRLF);
|
2023-07-20 19:24:18 +08:00
|
|
|
|
break;
|
2023-07-21 14:20:47 +08:00
|
|
|
|
//case acl::REDIS_RESULT_ARRAY:
|
|
|
|
|
// break;
|
2023-07-20 19:24:18 +08:00
|
|
|
|
default:
|
|
|
|
|
break;
|
|
|
|
|
}
|
2023-07-26 15:50:15 +08:00
|
|
|
|
|
2023-07-20 19:24:18 +08:00
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2023-07-21 16:20:04 +08:00
|
|
|
|
redis_object& redis_object::set_status(const std::string& data,
|
|
|
|
|
bool return_parent) {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_STATUS;
|
|
|
|
|
buf_ = data;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
return return_parent ? *parent_ : *this;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
redis_object& redis_object::set_error(const std::string& data,
|
|
|
|
|
bool return_parent) {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_ERROR;
|
|
|
|
|
buf_ = data;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
return return_parent ? *parent_ : *this;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
redis_object& redis_object::set_number(int n, bool return_parent) {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_INTEGER;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
|
|
|
|
|
std::string buf = std::to_string(n);
|
2023-07-26 15:50:15 +08:00
|
|
|
|
buf_ = buf;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
return return_parent ? *parent_ : *this;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
redis_object& redis_object::set_string(const std::string &data,
|
|
|
|
|
bool return_parent) {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_STRING;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
if (!data.empty()) {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
buf_ = data;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
}
|
|
|
|
|
return return_parent ? *parent_ : *this;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
redis_object& redis_object::create_child() {
|
2023-07-26 15:50:15 +08:00
|
|
|
|
redis_object* obj;
|
|
|
|
|
if (cache_.empty()) {
|
|
|
|
|
obj = new redis_object(cache_, cache_max_);
|
|
|
|
|
obj->set_parent(this);
|
|
|
|
|
objs_.emplace_back(obj);
|
|
|
|
|
} else {
|
|
|
|
|
obj = cache_.back();
|
|
|
|
|
obj->set_parent(this);
|
|
|
|
|
cache_.pop_back();
|
|
|
|
|
objs_.emplace_back(obj);
|
|
|
|
|
}
|
2023-07-21 16:20:04 +08:00
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
if (obj_ == nullptr) {
|
2023-07-21 16:20:04 +08:00
|
|
|
|
// The last one is NULL.
|
2023-07-26 15:50:15 +08:00
|
|
|
|
type_ = REDIS_OBJ_ARRAY;
|
2023-07-21 16:20:04 +08:00
|
|
|
|
}
|
|
|
|
|
|
2023-07-26 15:50:15 +08:00
|
|
|
|
cnt_ = objs_.size();
|
2023-07-21 16:20:04 +08:00
|
|
|
|
return *obj;
|
|
|
|
|
}
|
|
|
|
|
|
2023-07-19 19:07:53 +08:00
|
|
|
|
} // namespace pkv
|