From 9136627766b9a2f0c64260999bcf429ea45efba3 Mon Sep 17 00:00:00 2001 From: Yaroslav Dynnikov <yaroslav.dynnikov@gmail.com> Date: Tue, 5 Jul 2022 02:05:02 +0300 Subject: [PATCH] feature: limit number of peers in join response Initially, JoinResponse was supplied with every single peer in cluster. If the cluster is big enough, it results in the "max tuple size limit reached" error. In fact, only voters are needed for the raft to operate normally. --- src/main.rs | 1 + src/traft/node.rs | 12 +++++++++++- src/util.rs | 10 ++++++++++ 3 files changed, 22 insertions(+), 1 deletion(-) diff --git a/src/main.rs b/src/main.rs index 5ab9ec2ecb..a5172dbb1b 100644 --- a/src/main.rs +++ b/src/main.rs @@ -525,6 +525,7 @@ fn start_join(args: &args::Run, leader_address: String) { let raft_id = resp.peer.raft_id; start_transaction(|| -> Result<(), Error> { + traft::Storage::persist_peer(&resp.peer).unwrap(); for peer in resp.raft_group { traft::Storage::persist_peer(&peer).unwrap(); } diff --git a/src/traft/node.rs b/src/traft/node.rs index 2dea124b58..e441cfb4ea 100644 --- a/src/traft/node.rs +++ b/src/traft/node.rs @@ -1000,9 +1000,19 @@ fn raft_join(req: JoinRequest) -> Result<JoinResponse, Box<dyn std::error::Error } let peer = node.handle_topology_request(req.into())?; - let raft_group = Storage::peers()?; let box_replication = Storage::box_replication(&peer.replicaset_id, Some(peer.commit_index))?; + // A joined peer needs to communicate with other nodes. + // Provide it the list of raft voters in response. + let mut raft_group = vec![]; + for raft_id in Storage::voters()?.into_iter() { + if let Some(peer) = Storage::peer_by_raft_id(raft_id)? { + raft_group.push(peer); + } else { + crate::warn_or_panic!("peer missing in storage, raft_id: {}", raft_id); + } + } + Ok(JoinResponse { peer, raft_group, diff --git a/src/util.rs b/src/util.rs index 125de8e64a..b0aa9313ac 100644 --- a/src/util.rs +++ b/src/util.rs @@ -13,3 +13,13 @@ macro_rules! unwrap_ok_or { } } } + +#[macro_export] +macro_rules! warn_or_panic { + ($($arg:tt)*) => { + $crate::tlog!(Warning, $($arg)*); + if cfg!(debug_assertions) { + panic!($($arg)*); + } + }; +} -- GitLab