Created
July 20, 2020 14:53
-
-
Save bionicbrian/a40d513fa2ed3a5550b923232cd6847d to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#![feature(proc_macro_hygiene, decl_macro)] | |
#[macro_use] | |
extern crate rocket; | |
use jsonwebtoken::{decode, encode, Algorithm, DecodingKey, EncodingKey, Header, Validation}; | |
use rocket::request::{self, FromRequest, Request}; | |
use rocket::Outcome; | |
use serde::{Deserialize, Serialize}; | |
/// Our claims struct, it needs to derive `Serialize` and/or `Deserialize` | |
#[derive(Debug, Serialize, Deserialize)] | |
struct Claims { | |
sub: String, | |
company: String, | |
exp: usize, | |
} | |
struct ApiToken { | |
token: jsonwebtoken::TokenData<Claims>, | |
} | |
impl ApiToken { | |
fn token_from_request<'a>(request: &Request) -> Option<jsonwebtoken::TokenData<Claims>> { | |
let token = match request.headers().get_one("Authorization") { | |
Some(auth) => { | |
let parts: Vec<&str> = auth.split(' ').collect(); | |
match parts[..] { | |
["jwt", jwt] => Some(String::from(jwt)), | |
_ => None, | |
} | |
} | |
None => None, | |
}; | |
let api_token = match token { | |
Some(token) => match decode::<Claims>( | |
&token, | |
&DecodingKey::from_secret("secret".as_ref()), | |
&Validation::default(), | |
) { | |
Ok(t) => Some(t), | |
Err(_) => None, | |
}, | |
_ => None, | |
}; | |
api_token | |
} | |
} | |
impl<'a, 'r> FromRequest<'a, 'r> for ApiToken { | |
type Error = String; | |
fn from_request(request: &'a Request<'r>) -> request::Outcome<Self, Self::Error> { | |
let token = ApiToken::token_from_request(request); | |
match token { | |
Some(t) => Outcome::Success(ApiToken { token: t }), | |
None => Outcome::Failure((rocket::http::Status::Unauthorized, "No bueno".to_string())), | |
} | |
} | |
} | |
#[get("/")] | |
fn index(token: ApiToken) -> String { | |
token.token.claims.sub | |
} | |
#[get("/token/<name>")] | |
fn token(name: String) -> String { | |
let my_claims = Claims { | |
sub: name, | |
company: "Cool Things".to_string(), | |
exp: 1595217600, | |
}; | |
let api_token = encode( | |
&Header::default(), | |
&my_claims, | |
&EncodingKey::from_secret("secret".as_ref()), | |
); | |
match api_token { | |
Ok(t) => t, | |
Err(_) => "Oops, nothin'".to_string(), | |
} | |
} | |
fn main() { | |
rocket::ignite().mount("/", routes![index, token]).launch(); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment