diff --git a/Cargo.lock b/Cargo.lock index 07f2c40..79283d8 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -169,6 +169,12 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "349a06037c7bf932dd7e7d1f653678b2038b9ad46a74102f1fc7bd7872678cce" +[[package]] +name = "base64" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8" + [[package]] name = "base64ct" version = "1.5.2" @@ -1229,6 +1235,7 @@ version = "0.2.0" dependencies = [ "async-std", "async-trait", + "base64", "clap", "configparser", "json", diff --git a/Cargo.toml b/Cargo.toml index 0514ec3..bc542d0 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -14,6 +14,7 @@ async-trait = "0.1.57" jwt-simple = "0.11.1" simple_logger = "4.0.0" log = "0.4.17" +base64 = "0.13.1" # useful for tests (embedded files should be delete in release ?) #rust-embed="6.4.1" diff --git a/src/http/router.rs b/src/http/router.rs index 1c41b40..57b0070 100644 --- a/src/http/router.rs +++ b/src/http/router.rs @@ -1,6 +1,7 @@ //! router aims to handle correctly the request corresponding to the target //! it implements all the logic to build an `HTTPResponse` +use base64; use json; use super::{HTTPMessage, HTTPRequest, HTTPResponse}; @@ -11,6 +12,7 @@ use crate::stores::{FileStore, Store}; // TODO: must be mapped with corresponding handler const GET_ROUTE: &'static str = "/get/"; const VALIDATE_ROUTE: &'static str = "/validate/"; +const PUBKEY_ROUTE: &'static str = "/pubkey/"; async fn handle_get(request: HTTPRequest, config: Config) -> HTTPResponse { let mut store = FileStore::new(config.filestore_path.clone()); @@ -87,6 +89,28 @@ async fn handle_validate(request: HTTPRequest, config: Config) -> HTTPResponse { HTTPResponse::as_200(Some(json)) } +/// returns the JWT public key in base64 encoded +async fn handle_public_key(_request: HTTPRequest, config: Config) -> HTTPResponse { + let jwt_signer = { + match JWTSigner::new(config).await { + Ok(s) => s, + Err(e) => { + let message = HTTPMessage::error(&e); + let json = message.try_into().unwrap(); + return HTTPResponse::as_500(Some(json)); + } + } + }; + + let public_key = jwt_signer.get_public_key(); + + let mut message = HTTPMessage::default(); + message.put("pubkey", &base64::encode(public_key)); + + let json = message.try_into().unwrap(); + HTTPResponse::as_200(Some(json)) +} + pub struct Router; impl Router { @@ -99,6 +123,7 @@ impl Router { match target.as_str() { GET_ROUTE => handle_get(request, config).await, VALIDATE_ROUTE => handle_validate(request, config).await, + PUBKEY_ROUTE => handle_public_key(request, config).await, _ => HTTPResponse::as_404(), } } diff --git a/src/jwt/jwt.rs b/src/jwt/jwt.rs index ddcba72..8772517 100644 --- a/src/jwt/jwt.rs +++ b/src/jwt/jwt.rs @@ -90,6 +90,10 @@ impl JWTSigner { )), } } + + pub fn get_public_key(&self) -> String { + self.public_key.clone() + } } #[tokio::test]