mirror of
https://github.com/GreptimeTeam/greptimedb.git
synced 2026-10-29 23:16:57 +00:00
feat(operator): retry failed writes with refreshed partitions (#9542)
* feat(operator): retry failed writes with refreshed partitions Signed-off-by: WenyXu <wenymedia@gmail.com> * style(operator): simplify retry test type references Signed-off-by: WenyXu <wenymedia@gmail.com> * refactor(operator): clarify write request rebuilding names Signed-off-by: WenyXu <wenymedia@gmail.com> * refactor(operator): encapsulate write retry attempts Signed-off-by: WenyXu <wenymedia@gmail.com> * style(operator): group inserter configuration methods Signed-off-by: WenyXu <wenymedia@gmail.com> * refactor(operator): share routed peers and separate retry decisions Signed-off-by: WenyXu <wenymedia@gmail.com> * refactor(operator): avoid temporary write routing allocations Signed-off-by: WenyXu <wenymedia@gmail.com> --------- Signed-off-by: WenyXu <wenymedia@gmail.com>
This commit is contained in:
@@ -22,6 +22,9 @@ use crate::cluster::NodeInfo;
|
||||
use crate::error::Error;
|
||||
use crate::{DatanodeId, FlownodeId};
|
||||
|
||||
/// Shared reference to a [`Peer`].
|
||||
pub type PeerRef = Arc<Peer>;
|
||||
|
||||
/// [`PeerResolver`] provides methods to look up peer information by node ID.
|
||||
///
|
||||
/// This trait allows resolving both datanode and flownode peers, regardless of their current activity status.
|
||||
|
||||
@@ -114,15 +114,25 @@ pub fn convert_to_region_leader_map(region_routes: &[RegionRoute]) -> HashMap<Re
|
||||
.collect::<HashMap<_, _>>()
|
||||
}
|
||||
|
||||
/// Returns the leader of the first route matching the region number.
|
||||
pub fn find_region_leader(
|
||||
region_routes: &[RegionRoute],
|
||||
region_number: RegionNumber,
|
||||
) -> Option<Peer> {
|
||||
find_region_leader_ref(region_routes, region_number).cloned()
|
||||
}
|
||||
|
||||
/// Borrows the leader of the first route matching the region number.
|
||||
///
|
||||
/// Returns `None` if no route matches or the first matching route has no leader.
|
||||
pub fn find_region_leader_ref(
|
||||
region_routes: &[RegionRoute],
|
||||
region_number: RegionNumber,
|
||||
) -> Option<&Peer> {
|
||||
region_routes
|
||||
.iter()
|
||||
.find(|x| x.region.id.region_number() == region_number)
|
||||
.and_then(|r| r.leader_peer.as_ref())
|
||||
.cloned()
|
||||
}
|
||||
|
||||
/// Returns the region numbers of the leader regions on the target datanode.
|
||||
@@ -442,6 +452,27 @@ mod tests {
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_find_region_leader() {
|
||||
let mut routes = vec![
|
||||
new_test_region_route(RegionId::new(1, 1)),
|
||||
new_test_region_route(RegionId::new(1, 1)),
|
||||
];
|
||||
routes[1].leader_peer = Some(Peer::new(2, "a2"));
|
||||
|
||||
assert_eq!(
|
||||
find_region_leader_ref(&routes, 1),
|
||||
routes[0].leader_peer.as_ref()
|
||||
);
|
||||
assert_eq!(find_region_leader(&routes, 1), routes[0].leader_peer);
|
||||
assert_eq!(find_region_leader_ref(&routes, 2), None);
|
||||
assert_eq!(find_region_leader(&routes, 2), None);
|
||||
|
||||
routes[0].leader_peer = None;
|
||||
assert_eq!(find_region_leader_ref(&routes, 1), None);
|
||||
assert_eq!(find_region_leader(&routes, 1), None);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_leader_is_downgraded() {
|
||||
let mut region_route = RegionRoute {
|
||||
|
||||
Reference in New Issue
Block a user