rama::http::layer

Module catch_panic

Expand description

Convert panics into responses.

Note that using panics for error handling is not recommended. Prefer instead to use Result whenever possible.

§Example

use std::convert::Infallible;

use rama_http::{Request, Response, Body, header::HeaderName};
use rama_http::layer::catch_panic::CatchPanicLayer;
use rama_core::service::service_fn;
use rama_core::{Context, Service, Layer};
use rama_core::error::BoxError;

async fn handle(req: Request) -> Result<Response, Infallible> {
    panic!("something went wrong...")
}

let mut svc = (
    // Catch panics and convert them into responses.
    CatchPanicLayer::new(),
).layer(service_fn(handle));

// Call the service.
let request = Request::new(Body::default());

let response = svc.serve(Context::default(), request).await?;

assert_eq!(response.status(), 500);

Using a custom panic handler:

use std::{any::Any, convert::Infallible};

use rama_http::{Body, Request, StatusCode, Response, header::{self, HeaderName}};
use rama_http::layer::catch_panic::CatchPanicLayer;
use rama_core::service::{Service, service_fn};
use rama_core::Layer;
use rama_core::error::BoxError;

async fn handle(req: Request) -> Result<Response, Infallible> {
    panic!("something went wrong...")
}

fn handle_panic(err: Box<dyn Any + Send + 'static>) -> Response {
    let details = if let Some(s) = err.downcast_ref::<String>() {
        s.clone()
    } else if let Some(s) = err.downcast_ref::<&str>() {
        s.to_string()
    } else {
        "Unknown panic message".to_string()
    };

    let body = serde_json::json!({
        "error": {
            "kind": "panic",
            "details": details,
        }
    });
    let body = serde_json::to_string(&body).unwrap();

    Response::builder()
        .status(StatusCode::INTERNAL_SERVER_ERROR)
        .header(header::CONTENT_TYPE, "application/json")
        .body(Body::from(body))
        .unwrap()
}

let svc = (
    // Use `handle_panic` to create the response.
    CatchPanicLayer::custom(handle_panic),
).layer(service_fn(handle));

Structs§

  • Middleware that catches panics and converts them into 500 Internal Server responses.
  • Layer that applies the CatchPanic middleware that catches panics and converts them into 500 Internal Server responses.
  • The default ResponseForPanic used by CatchPanic.

Traits§