From 4f31000cf40b5ff512e3bf7f3c0504054410b37e Mon Sep 17 00:00:00 2001 From: Tao He Date: Fri, 12 Feb 2021 15:56:09 +0800 Subject: [PATCH] Set a proper upper bound for `ls` request, and remove the default sort options. (#46) Signed-off-by: Tao He --- src/v3/AsyncGetAction.cpp | 37 +++++++++++++++++++++++++++++-------- 1 file changed, 29 insertions(+), 8 deletions(-) diff --git a/src/v3/AsyncGetAction.cpp b/src/v3/AsyncGetAction.cpp index c89c812..957d863 100644 --- a/src/v3/AsyncGetAction.cpp +++ b/src/v3/AsyncGetAction.cpp @@ -1,23 +1,44 @@ #include "etcd/v3/AsyncGetAction.hpp" + +#include + #include "etcd/v3/action_constants.hpp" using etcdserverpb::RangeRequest; +static std::string string_plus_one(std::string const &value) { + char *s = static_cast(calloc(value.size() + 1, sizeof(char))); + std::memcpy(s, value.c_str(), value.size()); + for (int i = value.size() - 1; i >= 0; --i) { + if (static_cast(s[i]) < 0xff) { + s[i] = s[i] + 1; + std::string ret = std::string(s, i + 1); + free(s); + return ret; + } + } + // see: noPrefixEnd in etcd + return {"\0"}; +} + etcdv3::AsyncGetAction::AsyncGetAction(etcdv3::ActionParameters param) : etcdv3::Action(param) { RangeRequest get_request; - get_request.set_key(parameters.key); + if (parameters.key.empty()) { + get_request.set_key("\0"); + } else { + get_request.set_key(parameters.key); + } get_request.set_limit(param.limit); if(parameters.withPrefix) { - std::string range_end(parameters.key); - int ascii = (int)range_end[range_end.length()-1]; - range_end.back() = ascii+1; - - get_request.set_range_end(range_end); - get_request.set_sort_target(RangeRequest::SortTarget::RangeRequest_SortTarget_KEY); - get_request.set_sort_order(RangeRequest::SortOrder::RangeRequest_SortOrder_ASCEND); + if (parameters.key.empty()) { + get_request.set_range_end(string_plus_one("\0")); + } else { + get_request.set_range_end(string_plus_one(parameters.key)); + } + get_request.set_sort_order(RangeRequest::SortOrder::RangeRequest_SortOrder_NONE); } response_reader = parameters.kv_stub->AsyncRange(&context,get_request,&cq_); response_reader->Finish(&reply, &status, (void*)this);