An open API service indexing awesome lists of open source software.

https://github.com/conradludgate/pasta-tokens

A correct, fast and ergonomic PASETO library for Rust
https://github.com/conradludgate/pasta-tokens

authentication paserk paseto rust tokens

Last synced: 3 months ago
JSON representation

A correct, fast and ergonomic PASETO library for Rust

Awesome Lists containing this project

README

          

# pasta_tokens

PASETO implementation for Rust.

## Examples

```rust
use pasta_tokens::{v4, paserk::k4, purpose::public::Public, Json};

#[derive(serde::Serialize, serde::Deserialize)]
struct Footer {
/// The ID of the key used to sign the PASETO.
/// A footer should only contain types that are `SafeForFooter`
kid: k4::KeyId,
}

#[derive(serde::Serialize, serde::Deserialize)]
struct Payload {
/// The expiration date of the token
#[serde(with = "time::serde::rfc3339", rename = "exp")]
expiration: time::OffsetDateTime,
/// The subject of the token
#[serde(rename = "sub")]
user_id: uuid::Uuid,
}

// load your secret key
let secret_key = hex::decode("407796f4bc4b8184e9fe0c54b336822d34823092ad873d87ba14c3efb9db8c1d").unwrap();
let secret_key = v4::SecretKey::from_secret_key(secret_key.try_into().unwrap());

let user_id = uuid::Uuid::new_v4();

// create the token payload and footer.
let token = v4::UnsignedToken::new_v4_public(Payload {
// expires in 1 hour
expiration: time::OffsetDateTime::now_utc() + time::Duration::hours(1),
user_id,
})
.with_footer(Json(Footer {
kid: secret_key.public_key().to_id(),
}))
// sign with the secret key
.sign(&secret_key)
.unwrap()
.to_string();

// Send off the token to the client
println!("{token}");
// "v4.public.eyJleHAiOiIyMDIzLTEwLTAxVDE0OjQ4OjI2LjM0NjA5MloiLCJzdWIiOiIxOTBhZjFmYS1lZGVlLTRiNGUtOGQxMC05ZmUwZjQ1ZGQ5OTQifXo-Vsr45NroJZ9pLkuN3xcxgFncGF3eject5GdZH7WwTEfCgmo6hD-zNh0txsLvZi1vC601oNCgXq_2cK4XKQw.eyJraWQiOiJrNC5waWQuQUdQQ09CUkI4UHowQ3dNOFFfQnNVUEw0OF8zZjRUbE0yc2Z0R3Y0ejkzVFkifQ"

// load your public keys
let public_key = hex::decode("b7715bd661458d928654d3e832f53ff5c9480542e0e3d4c9b032c768c7ce6023").unwrap();
let public_key = v4::PublicKey::from_public_key(&public_key).unwrap();

// keep a key cache of key IDs to public keys.
// this will let you securely rotate your secret keys
// and still validate multiple public keys safely
let keys = std::collections::HashMap::from([
(public_key.to_id(), public_key)
]);

// Parse the token from the client
let token: v4::SignedToken> = token.parse().expect("should be a valid token format");

// using the key ID, search for the public key
let key = &keys[&token.unverified_footer().0.kid];

// verify the token signature
let token: v4::VerifiedToken = token.verify(key).expect("token should be signed by us");

// check if the token has expired
assert!(token.message.expiration > time::OffsetDateTime::now_utc());

// proceed to use the payload as you wish!
assert_eq!(token.message.user_id, user_id);
```