use axum::{
extract::{
FromRequestParts as AxumFromRequestParts, Path as AxumPath,
rejection::PathRejection as AxumPathRejection,
},
response::IntoResponse as _,
};
use http::request::Parts;
use crate::{
Registry,
adapters::SerdeAdapter,
openapi::{Operation, ParameterIn, Responses},
request::{FromRequestParts, utils::add_parameters_to_operation},
response::IntoResponse,
schema::SchemaDeserialize,
};
pub struct Path<T>(pub T);
pub struct PathRejection(AxumPathRejection);
impl<T, S> FromRequestParts<S> for Path<T>
where
T: SchemaDeserialize + Send,
S: Send + Sync + 'static,
{
type Rejection = PathRejection;
fn openapi(operation: &mut Operation, registry: &mut Registry) {
add_parameters_to_operation::<T>(operation, registry, ParameterIn::Path, "path");
}
async fn from_request_parts(parts: &mut Parts, state: &S) -> Result<Self, Self::Rejection> {
<AxumPath<SerdeAdapter<T>> as AxumFromRequestParts<S>>::from_request_parts(parts, state)
.await
.map(|query| Self(query.0.0))
.map_err(PathRejection)
}
}
impl IntoResponse for PathRejection {
fn openapi(_: &mut Registry) -> Responses {
Responses::default()
}
fn into_response(self) -> crate::response::Response {
self.0.into_response()
}
}