Skip to content

Commit 1ecdb44

Browse files
committed
Merge branch 'unstable' into fix-hash-rename
2 parents 90dbfb6 + 04b5c06 commit 1ecdb44

File tree

205 files changed

+1513
-998
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

205 files changed

+1513
-998
lines changed

.github/workflows/kiwidb.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ jobs:
7171
working-directory: ${{ github.workspace }}/${{ env.BUILD_DIR }}
7272
# Execute tests defined by the CMake configuration.
7373
# See https://cmake.org/cmake/help/latest/manual/ctest.1.html for more detail
74-
run: ctest
74+
run: ctest --output-on-failure --timeout 600
7575

7676
- name: Run TCL E2e Tests
7777
working-directory: ${{ github.workspace }}
@@ -113,7 +113,7 @@ jobs:
113113
working-directory: ${{ github.workspace }}/${{ env.BUILD_DIR }}
114114
# Execute tests defined by the CMake configuration.
115115
# See https://cmake.org/cmake/help/latest/manual/ctest.1.html for more detail
116-
run: ctest
116+
run: ctest --output-on-failure --timeout 600
117117

118118
- name: Run TCL E2e Tests
119119
working-directory: ${{ github.workspace }}

.gitmodules

Lines changed: 0 additions & 3 deletions
This file was deleted.

CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# Copyright (c) 2023-present, Arana/Kiwi Community. All rights reserved.
1+
# Copyright (c) 2023-present, arana-db Community. All rights reserved.
22
# This source code is licensed under the BSD-style license found in the
33
# LICENSE file in the root directory of this source tree. An additional grant
44
# of patent rights can be found in the PATENTS file in the same directory.

LICENSE.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
Copyright (c) 2015-2023, OpenAtom Foundation
1+
Copyright (c) 2015-2023, arana-db Foundation
22
All rights reserved.
33

44
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:

cmake/rocksdb.cmake

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ ExternalProject_Add(
1212
${EXTERNAL_PROJECT_LOG_ARGS}
1313
DEPENDS gflags snappy zlib lz4 zstd
1414
GIT_REPOSITORY https://github.com/facebook/rocksdb.git
15-
GIT_TAG v9.4.0
15+
GIT_TAG v9.11.1
1616
GIT_SHALLOW true
1717
SOURCE_DIR ${ROCKSDB_SOURCES_DIR}
1818
CMAKE_ARGS

etc/script/check_format.sh

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,9 +43,9 @@ main() {
4343
echo "Starting code format check..."
4444

4545
# Find all C/C++ source files
46-
while IFS= read -r -d '' file; do
46+
find ./src -type f \( -name "*.cpp" -o -name "*.hpp" -o -name "*.c" -o -name "*.h" -o -name "*.cc" \) -print0 | while IFS= read -r -d '' file; do
4747
check_file "$file"
48-
done < <(find ./src -type f \( -name "*.cpp" -o -name "*.hpp" -o -name "*.c" -o -name "*.h" -o -name "*.cc" \) -print0)
48+
done
4949

5050
# Output summary
5151
echo "----------------------------------------"

src/CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# Copyright (c) 2023-present, Arana/Kiwi Community. All rights reserved.
1+
# Copyright (c) 2023-present, arana-db Community. All rights reserved.
22
# This source code is licensed under the BSD-style license found in the
33
# LICENSE file in the root directory of this source tree. An additional grant
44
# of patent rights can be found in the PATENTS file in the same directory.

src/base_cmd.cc

Lines changed: 85 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// Copyright (c) 2023-present, Arana/Kiwi Community. All rights reserved.
1+
// Copyright (c) 2023-present, arana-db Community. All rights reserved.
22
// This source code is licensed under the BSD-style license found in the
33
// LICENSE file in the root directory of this source tree. An additional grant
44
// of patent rights can be found in the PATENTS file in the same directory
@@ -9,15 +9,12 @@
99

1010
#include "base_cmd.h"
1111

12-
#include "fmt/core.h"
13-
1412
#include "raft/raft.h"
1513

1614
#include "common.h"
1715
#include "config.h"
1816
#include "kiwi.h"
1917
#include "log.h"
20-
#include "raft/raft.h"
2118

2219
namespace kiwi {
2320

@@ -44,16 +41,19 @@ void BaseCmd::Execute(PClient* client) {
4441
// read consistency (lease read) / write redirection
4542
if (g_config.use_raft && (HasFlag(kCmdFlagsReadonly) || HasFlag(kCmdFlagsWrite))) {
4643
if (!RAFT_INST.IsInitialized()) {
47-
return client->SetRes(CmdRes::kErrOther, "RAFT_INST is not initialized");
44+
client->SetRes(CmdRes::kErrOther, "RAFT_INST is not initialized");
45+
return;
4846
}
4947

5048
if (!RAFT_INST.IsLeader()) {
5149
auto leader_addr = RAFT_INST.GetLeaderAddress();
5250
if (leader_addr.empty()) {
53-
return client->SetRes(CmdRes::kErrOther, std::string("-CLUSTERDOWN No Raft leader"));
51+
client->SetRes(CmdRes::kErrClusterDown, "No raft leader");
52+
return;
5453
}
5554

56-
return client->SetRes(CmdRes::kErrOther, fmt::format("-MOVED {}", leader_addr));
55+
client->SetRes(CmdRes::kErrMoved, leader_addr);
56+
return;
5757
}
5858
}
5959

@@ -106,6 +106,84 @@ BaseCmd* BaseCmdGroup::GetSubCmd(const std::string& cmdName) {
106106
return subCmd->second.get();
107107
}
108108

109+
void BaseCmd::BlockThisClientToWaitLRPush(std::vector<std::string>& keys, int64_t expire_time,
110+
std::shared_ptr<PClient> client, BlockedConnNode::Type type) {
111+
std::lock_guard<std::shared_mutex> map_lock(g_kiwi->GetBlockMtx());
112+
auto& key_to_conns = g_kiwi->GetMapFromKeyToConns();
113+
for (const auto& key : keys) {
114+
kiwi::BlockKey blpop_key{client->GetCurrentDB(), key};
115+
116+
auto it = key_to_conns.find(blpop_key);
117+
if (it == key_to_conns.end()) {
118+
key_to_conns.emplace(blpop_key, std::make_unique<std::list<BlockedConnNode>>());
119+
it = key_to_conns.find(blpop_key);
120+
}
121+
it->second->emplace_back(expire_time, client, type);
122+
}
123+
}
124+
125+
void BaseCmd::ServeAndUnblockConns(PClient* client) {
126+
kiwi::BlockKey key{client->GetCurrentDB(), client->Key()};
127+
128+
std::lock_guard<std::shared_mutex> map_lock(g_kiwi->GetBlockMtx());
129+
auto& key_to_conns = g_kiwi->GetMapFromKeyToConns();
130+
auto it = key_to_conns.find(key);
131+
if (it == key_to_conns.end()) {
132+
// no client is waitting for this key
133+
return;
134+
}
135+
136+
auto& waitting_list = it->second;
137+
std::vector<std::string> elements;
138+
storage::Status s;
139+
140+
// traverse this list from head to tail(in the order of adding sequence) ,means "first blocked, first get served“
141+
for (auto conn_blocked = waitting_list->begin(); conn_blocked != waitting_list->end();) {
142+
auto BlockedClient = conn_blocked->GetBlockedClient();
143+
144+
if (BlockedClient->State() == ClientState::kClosed) {
145+
conn_blocked = waitting_list->erase(conn_blocked);
146+
g_kiwi->CleanBlockedNodes(BlockedClient);
147+
continue;
148+
}
149+
150+
switch (conn_blocked->GetCmdType()) {
151+
case BlockedConnNode::Type::BLPop:
152+
s = STORE_INST.GetBackend(client->GetCurrentDB())->GetStorage()->LPop(client->Key(), 1, &elements);
153+
break;
154+
case BlockedConnNode::Type::BRPop:
155+
s = STORE_INST.GetBackend(client->GetCurrentDB())->GetStorage()->RPop(client->Key(), 1, &elements);
156+
break;
157+
case BlockedConnNode::Type::NotAny:
158+
//! DOING NOTHING?
159+
break;
160+
}
161+
162+
if (s.ok()) {
163+
BlockedClient->AppendArrayLen(2);
164+
BlockedClient->AppendString(client->Key());
165+
BlockedClient->AppendString(elements[0]);
166+
} else if (s.IsNotFound()) {
167+
// this key has no more elements to serve more blocked conn.
168+
break;
169+
} else {
170+
BlockedClient->SetRes(CmdRes::kErrOther, s.ToString());
171+
}
172+
BlockedClient->SendPacket();
173+
// remove this conn from current waiting list
174+
conn_blocked = waitting_list->erase(conn_blocked);
175+
g_kiwi->CleanBlockedNodes(BlockedClient);
176+
}
177+
}
178+
179+
bool BlockedConnNode::IsExpired(std::chrono::system_clock::time_point now) {
180+
if (expire_time_ == 0) {
181+
return false;
182+
}
183+
int64_t now_in_ms = std::chrono::time_point_cast<std::chrono::milliseconds>(now).time_since_epoch().count();
184+
return expire_time_ <= now_in_ms;
185+
}
186+
109187
bool BaseCmdGroup::DoInitial(PClient* client) {
110188
client->SetSubCmdName(client->argv_[1]);
111189
if (!subCmds_.contains(client->SubCmdName())) {

src/base_cmd.h

Lines changed: 39 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// Copyright (c) 2023-present, Arana/Kiwi Community. All rights reserved.
1+
// Copyright (c) 2023-present, arana-db Community. All rights reserved.
22
// This source code is licensed under the BSD-style license found in the
33
// LICENSE file in the root directory of this source tree. An additional grant
44
// of patent rights can be found in the PATENTS file in the same directory
@@ -144,6 +144,8 @@ const std::string kCmdNameRPush = "rpush";
144144
const std::string kCmdNameRPushx = "rpushx";
145145
const std::string kCmdNameLPop = "lpop";
146146
const std::string kCmdNameRPop = "rpop";
147+
const std::string kCmdNameBLPop = "blpop";
148+
const std::string kCmdNameBRPop = "brpop";
147149
const std::string kCmdNameLRem = "lrem";
148150
const std::string kCmdNameLRange = "lrange";
149151
const std::string kCmdNameLTrim = "ltrim";
@@ -190,7 +192,7 @@ enum CmdFlags {
190192
kCmdFlagsProtected = (1 << 12), // Don't accept in scripts
191193
kCmdFlagsModuleNoCluster = (1 << 13), // No cluster mode support
192194
kCmdFlagsNoMulti = (1 << 14), // Cannot be pipelined
193-
kCmdFlagsExclusive = (1 << 15), // May change Storage pointer, like Arana/Kiwi's kCmdFlagsSuspend
195+
kCmdFlagsExclusive = (1 << 15), // May change Storage pointer, like pika's kCmdFlagsSuspend
194196
kCmdFlagsRaft = (1 << 16), // raft
195197
};
196198

@@ -219,6 +221,22 @@ enum AclCategory {
219221
kAclCategoryRaft = (1 << 21),
220222
};
221223

224+
class BlockedConnNode {
225+
public:
226+
enum Type { NotAny = 0, BLPop, BRPop };
227+
virtual ~BlockedConnNode() = default;
228+
BlockedConnNode(int64_t expire_time, std::shared_ptr<PClient> client, Type type)
229+
: expire_time_(expire_time), client_(client), type_(type) {}
230+
bool IsExpired(std::chrono::system_clock::time_point now = std::chrono::system_clock::now());
231+
std::shared_ptr<PClient> GetBlockedClient() { return client_; }
232+
Type GetCmdType() { return type_; }
233+
234+
private:
235+
Type type_ = NotAny;
236+
int64_t expire_time_ = 0;
237+
std::shared_ptr<PClient> client_;
238+
};
239+
222240
/**
223241
* @brief Base class for all commands
224242
* BaseCmd, as the base class for all commands, mainly implements some common functions
@@ -282,6 +300,11 @@ class BaseCmd : public std::enable_shared_from_this<BaseCmd> {
282300

283301
uint32_t GetCmdID() const;
284302

303+
void ServeAndUnblockConns(PClient* client);
304+
305+
void BlockThisClientToWaitLRPush(std::vector<std::string>& keys, int64_t expire_time, std::shared_ptr<PClient> client,
306+
BlockedConnNode::Type type);
307+
285308
protected:
286309
// Execute a specific command
287310
virtual void DoCmd(PClient* client) = 0;
@@ -321,4 +344,18 @@ class BaseCmdGroup : public BaseCmd {
321344
private:
322345
std::map<std::string, std::unique_ptr<BaseCmd>> subCmds_;
323346
};
347+
348+
struct BlockKey { // this data struct is made for the scenario of multi dbs in kiwi.
349+
BlockKey(int db_id, std::string key) : db_id_(db_id), key_(std::move(key)) {}
350+
351+
int db_id_ = -1;
352+
std::string key_;
353+
bool operator==(const BlockKey& p) const { return p.db_id_ == db_id_ && p.key_ == key_; }
354+
};
355+
struct BlockKeyHash {
356+
std::size_t operator()(const BlockKey& k) const {
357+
return std::hash<int>{}(k.db_id_) ^ std::hash<std::string>{}(k.key_);
358+
}
359+
};
360+
324361
} // namespace kiwi

src/client.cc

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// Copyright (c) 2023-present, Arana/Kiwi Community. All rights reserved.
1+
// Copyright (c) 2023-present, arana-db Community. All rights reserved.
22
// This source code is licensed under the BSD-style license found in the
33
// LICENSE file in the root directory of this source tree. An additional grant
44
// of patent rights can be found in the PATENTS file in the same directory
@@ -14,12 +14,9 @@
1414
#include "base_cmd.h"
1515
#include "client.h"
1616
#include "config.h"
17-
#include "env.h"
1817
#include "kiwi.h"
1918
#include "raft/raft.h"
20-
#include "slow_log.h"
2119
#include "std/log.h"
22-
#include "std/std_string.h"
2320

2421
namespace kiwi {
2522

@@ -303,6 +300,7 @@ bool PClient::isPeerMaster() const {
303300
return repl_addr.GetIP() == PeerIP() && repl_addr.GetPort() == PeerPort();
304301
}
305302

303+
// check if the client is the target of the cluster command
306304
bool PClient::isClusterCmdTarget() const {
307305
return RAFT_INST.GetClusterCmdCtx().GetPeerIp() == PeerIP() && RAFT_INST.GetClusterCmdCtx().GetPort() == PeerPort();
308306
}

0 commit comments

Comments
 (0)