meta_srv/service/admin/
leader.rs

1// Copyright 2023 Greptime Team
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7//     http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15use std::collections::HashMap;
16
17use axum::extract::State;
18use axum::response::{IntoResponse, Response};
19use snafu::ResultExt;
20use tonic::codegen::http;
21
22use crate::error::{self, Result};
23use crate::metasrv::ElectionRef;
24use crate::service::admin::util::ErrorHandler;
25use crate::service::admin::HttpHandler;
26
27#[derive(Clone)]
28pub struct LeaderHandler {
29    pub election: Option<ElectionRef>,
30}
31
32impl LeaderHandler {
33    async fn get_leader(&self) -> Result<Option<String>> {
34        if let Some(election) = &self.election {
35            let leader_addr = election.leader().await?.0;
36            return Ok(Some(leader_addr));
37        }
38        Ok(None)
39    }
40}
41
42/// Get the leader handler.
43#[axum_macros::debug_handler]
44pub(crate) async fn get(State(handler): State<LeaderHandler>) -> Response {
45    handler
46        .get_leader()
47        .await
48        .map_err(ErrorHandler::new)
49        .map(|leader| leader.unwrap_or("election info is None".to_string()))
50        .into_response()
51}
52
53#[async_trait::async_trait]
54impl HttpHandler for LeaderHandler {
55    async fn handle(
56        &self,
57        _: &str,
58        _: http::Method,
59        _: &HashMap<String, String>,
60    ) -> Result<http::Response<String>> {
61        if let Some(leader_addr) = self.get_leader().await? {
62            return http::Response::builder()
63                .status(http::StatusCode::OK)
64                .body(leader_addr)
65                .context(error::InvalidHttpBodySnafu);
66        }
67        http::Response::builder()
68            .status(http::StatusCode::OK)
69            .body("election info is None".to_string())
70            .context(error::InvalidHttpBodySnafu)
71    }
72}