Line data Source code
1 : use axum::response::{IntoResponse, Response};
2 : use http::StatusCode;
3 : use serde::{Deserialize, Serialize};
4 : use tracing::info;
5 : use utils::failpoint_support::apply_failpoint;
6 :
7 : pub type ConfigureFailpointsRequest = Vec<FailpointConfig>;
8 :
9 : /// Information for configuring a single fail point
10 0 : #[derive(Debug, Serialize, Deserialize)]
11 : pub struct FailpointConfig {
12 : /// Name of the fail point
13 : pub name: String,
14 : /// List of actions to take, using the format described in `fail::cfg`
15 : ///
16 : /// We also support `actions = "exit"` to cause the fail point to immediately exit.
17 : pub actions: String,
18 : }
19 :
20 : use crate::http::JsonResponse;
21 : use crate::http::extract::Json;
22 :
23 : /// Configure failpoints for testing purposes.
24 0 : pub(in crate::http) async fn configure_failpoints(
25 0 : failpoints: Json<ConfigureFailpointsRequest>,
26 0 : ) -> Response {
27 0 : if !fail::has_failpoints() {
28 0 : return JsonResponse::error(
29 0 : StatusCode::PRECONDITION_FAILED,
30 0 : "Cannot manage failpoints because neon was compiled without failpoints support",
31 0 : );
32 0 : }
33 :
34 0 : for fp in &*failpoints {
35 0 : info!("cfg failpoint: {} {}", fp.name, fp.actions);
36 :
37 : // We recognize one extra "action" that's not natively recognized
38 : // by the failpoints crate: exit, to immediately kill the process
39 0 : let cfg_result = apply_failpoint(&fp.name, &fp.actions);
40 :
41 0 : if let Err(e) = cfg_result {
42 0 : return JsonResponse::error(
43 0 : StatusCode::BAD_REQUEST,
44 0 : format!("failed to configure failpoints: {e}"),
45 0 : );
46 0 : }
47 : }
48 :
49 0 : StatusCode::OK.into_response()
50 0 : }
|