110 lines
2.9 KiB
Rust
110 lines
2.9 KiB
Rust
use actix::Message;
|
|
use model::{AccountId, Audience, Token};
|
|
use sqlx::PgPool;
|
|
|
|
use crate::{db_async_handler, Result};
|
|
|
|
#[derive(Debug, thiserror::Error)]
|
|
pub enum Error {
|
|
#[error("Failed to save new token")]
|
|
Create,
|
|
#[error("Failed to find token by jti")]
|
|
Jti,
|
|
}
|
|
|
|
#[derive(Message)]
|
|
#[rtype(result = "Result<Token>")]
|
|
pub struct TokenByJti {
|
|
pub jti: uuid::Uuid,
|
|
}
|
|
|
|
db_async_handler!(TokenByJti, token_by_jti, Token);
|
|
|
|
pub(crate) async fn token_by_jti(msg: TokenByJti, pool: PgPool) -> Result<Token> {
|
|
sqlx::query_as(r#"
|
|
SELECT id, customer_id, role, issuer, subject, audience, expiration_time, not_before_time, issued_at_time, jwt_id
|
|
FROM tokens
|
|
WHERE jwt_id = $1 AND expiration_time > now()
|
|
"#)
|
|
.bind(msg.jti)
|
|
.fetch_one(&pool)
|
|
.await
|
|
.map_err(|e| {
|
|
log::error!("{e:?}");
|
|
crate::Error::Token(Error::Jti)
|
|
})
|
|
}
|
|
|
|
#[derive(Message)]
|
|
#[rtype(result = "Result<Token>")]
|
|
pub struct CreateToken {
|
|
pub customer_id: uuid::Uuid,
|
|
pub role: model::Role,
|
|
pub subject: AccountId,
|
|
pub audience: Audience,
|
|
}
|
|
|
|
db_async_handler!(CreateToken, create_token, Token);
|
|
|
|
pub(crate) async fn create_token(msg: CreateToken, pool: PgPool) -> Result<Token> {
|
|
let CreateToken {
|
|
customer_id,
|
|
role,
|
|
subject,
|
|
audience,
|
|
} = msg;
|
|
sqlx::query_as(r#"
|
|
INSERT INTO tokens (customer_id, role, subject, audience)
|
|
VALUES ($1, $2, $3, $4)
|
|
RETURNING id, customer_id, role, issuer, subject, audience, expiration_time, not_before_time, issued_at_time, jwt_id
|
|
"#)
|
|
.bind(customer_id)
|
|
.bind(role)
|
|
.bind(subject)
|
|
.bind(audience)
|
|
.fetch_one(&pool)
|
|
.await
|
|
.map_err(|e| {
|
|
log::error!("{e:?}");
|
|
crate::Error::Token(Error::Create)
|
|
})
|
|
}
|
|
|
|
#[derive(Message)]
|
|
#[rtype(result = "Result<Token>")]
|
|
pub struct CreateExtendedToken {
|
|
pub customer_id: uuid::Uuid,
|
|
pub role: model::Role,
|
|
pub subject: AccountId,
|
|
pub audience: Audience,
|
|
pub expiration_time: chrono::NaiveDateTime,
|
|
}
|
|
|
|
db_async_handler!(CreateExtendedToken, create_extended_token, Token);
|
|
|
|
pub(crate) async fn create_extended_token(msg: CreateExtendedToken, pool: PgPool) -> Result<Token> {
|
|
let CreateExtendedToken {
|
|
customer_id,
|
|
role,
|
|
subject,
|
|
audience,
|
|
expiration_time,
|
|
} = msg;
|
|
sqlx::query_as(r#"
|
|
INSERT INTO tokens (customer_id, role, subject, audience, expiration_time)
|
|
VALUES ($1, $2, $3, $4, $5)
|
|
RETURNING id, customer_id, role, issuer, subject, audience, expiration_time, not_before_time, issued_at_time, jwt_id
|
|
"#)
|
|
.bind(customer_id)
|
|
.bind(role)
|
|
.bind(subject)
|
|
.bind(audience)
|
|
.bind(expiration_time)
|
|
.fetch_one(&pool)
|
|
.await
|
|
.map_err(|e| {
|
|
log::error!("{e:?}");
|
|
crate::Error::Token(Error::Create)
|
|
})
|
|
}
|