rs_zero/rest/middleware/
auth.rs1use axum::{
2 body::Body,
3 extract::Request,
4 http::header::AUTHORIZATION,
5 middleware::Next,
6 response::{IntoResponse, Response},
7};
8use jsonwebtoken::{Algorithm, DecodingKey, Validation, decode};
9use serde::Deserialize;
10
11use crate::rest::{AuthConfig, RestError};
12
13#[derive(Debug, Deserialize)]
14struct Claims {
15 exp: usize,
16}
17
18pub async fn auth_middleware(auth: AuthConfig, request: Request<Body>, next: Next) -> Response {
20 if auth.is_public(request.uri().path()) {
21 return next.run(request).await;
22 }
23
24 let token = request
25 .headers()
26 .get(AUTHORIZATION)
27 .and_then(|value| value.to_str().ok())
28 .and_then(|value| value.strip_prefix("Bearer "))
29 .map(str::trim);
30
31 let Some(token) = token else {
32 return RestError::Unauthorized.into_response();
33 };
34
35 let mut validation = Validation::new(Algorithm::HS256);
36 validation.validate_exp = true;
37
38 match decode::<Claims>(
39 token,
40 &DecodingKey::from_secret(auth.secret.as_bytes()),
41 &validation,
42 ) {
43 Ok(data) => {
44 let _ = data.claims.exp;
45 next.run(request).await
46 }
47 Err(_) => RestError::Unauthorized.into_response(),
48 }
49}