diff --git a/crates/axum-utils/src/jwt.rs b/crates/axum-utils/src/jwt.rs new file mode 100644 index 00000000..eea1c90d --- /dev/null +++ b/crates/axum-utils/src/jwt.rs @@ -0,0 +1,31 @@ +// Copyright 2022 The Matrix.org Foundation C.I.C. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +use axum::{ + response::{IntoResponse, Response}, + TypedHeader, +}; +use headers::ContentType; +use mas_jose::jwt::Jwt; +use mime::Mime; + +pub struct JwtResponse(pub Jwt<'static, T>); + +impl IntoResponse for JwtResponse { + fn into_response(self) -> Response { + let application_jwt: Mime = "application/jwt".parse().unwrap(); + let content_type = ContentType::from(application_jwt); + (TypedHeader(content_type), self.0.into_string()).into_response() + } +} diff --git a/crates/axum-utils/src/lib.rs b/crates/axum-utils/src/lib.rs index de6f79c4..fca100e6 100644 --- a/crates/axum-utils/src/lib.rs +++ b/crates/axum-utils/src/lib.rs @@ -21,6 +21,7 @@ pub mod client_authorization; pub mod cookies; pub mod csrf; pub mod fancy_error; +pub mod jwt; pub mod session; pub mod user_authorization; diff --git a/crates/handlers/src/oauth2/userinfo.rs b/crates/handlers/src/oauth2/userinfo.rs index c77151b6..6ec88daa 100644 --- a/crates/handlers/src/oauth2/userinfo.rs +++ b/crates/handlers/src/oauth2/userinfo.rs @@ -16,17 +16,15 @@ use anyhow::Context; use axum::{ extract::Extension, response::{IntoResponse, Response}, - Json, TypedHeader, + Json, }; -use headers::ContentType; -use mas_axum_utils::{user_authorization::UserAuthorization, FancyError}; +use mas_axum_utils::{jwt::JwtResponse, user_authorization::UserAuthorization, FancyError}; use mas_jose::{ constraints::Constrainable, jwt::{JsonWebSignatureHeader, Jwt}, }; use mas_keystore::Keystore; use mas_router::UrlBuilder; -use mime::Mime; use oauth2_types::scope; use serde::Serialize; use serde_with::skip_serializing_none; @@ -91,9 +89,7 @@ pub async fn get( }; let token = Jwt::sign(header, user_info, &signer)?; - let application_jwt: Mime = "application/jwt".parse().unwrap(); - let content_type = ContentType::from(application_jwt); - Ok((TypedHeader(content_type), token.as_str().to_owned()).into_response()) + Ok(JwtResponse(token).into_response()) } else { Ok(Json(user_info).into_response()) } diff --git a/crates/jose/src/jwt/raw.rs b/crates/jose/src/jwt/raw.rs index 45289a64..150cc0c7 100644 --- a/crates/jose/src/jwt/raw.rs +++ b/crates/jose/src/jwt/raw.rs @@ -85,6 +85,12 @@ pub enum DecodeError { TooManyDots, } +impl<'a> From> for String { + fn from(val: RawJwt<'a>) -> Self { + val.inner.into() + } +} + impl<'a> TryFrom<&'a str> for RawJwt<'a> { type Error = DecodeError; fn try_from(value: &'a str) -> Result { diff --git a/crates/jose/src/jwt/signed.rs b/crates/jose/src/jwt/signed.rs index 130531ff..447e7c2b 100644 --- a/crates/jose/src/jwt/signed.rs +++ b/crates/jose/src/jwt/signed.rs @@ -256,6 +256,10 @@ impl<'a, T> Jwt<'a, T> { pub fn as_str(&'a self) -> &'a str { &self.raw } + + pub fn into_string(self) -> String { + self.raw.into() + } } #[derive(Debug, Error)]