loco_rs/model/
mod.rs

1//! # Model Error Handling
2//!
3//! Useful when using `sea_orm` and want to propagate errors
4
5pub mod query;
6use async_trait::async_trait;
7use sea_orm::DatabaseConnection;
8
9use crate::validation::ModelValidationErrors;
10
11#[derive(thiserror::Error, Debug)]
12#[allow(clippy::module_name_repetitions)]
13pub enum ModelError {
14    #[error("Entity already exists")]
15    EntityAlreadyExists,
16
17    #[error("Entity not found")]
18    EntityNotFound,
19
20    #[error(transparent)]
21    Validation(#[from] ModelValidationErrors),
22
23    #[cfg(feature = "auth_jwt")]
24    #[error("jwt error")]
25    Jwt(#[from] jsonwebtoken::errors::Error),
26
27    #[error(transparent)]
28    DbErr(#[from] sea_orm::DbErr),
29
30    #[error(transparent)]
31    Any(#[from] Box<dyn std::error::Error + Send + Sync>),
32
33    #[error("{0}")]
34    Message(String),
35}
36
37#[allow(clippy::module_name_repetitions)]
38pub type ModelResult<T, E = ModelError> = std::result::Result<T, E>;
39
40impl ModelError {
41    #[must_use]
42    pub fn wrap(err: impl std::error::Error + Send + Sync + 'static) -> Self {
43        Self::Any(Box::new(err))
44    }
45
46    #[must_use]
47    pub fn to_msg(err: impl std::error::Error + Send + Sync + 'static) -> Self {
48        Self::Message(err.to_string())
49    }
50
51    #[must_use]
52    pub fn msg(s: &str) -> Self {
53        Self::Message(s.to_string())
54    }
55}
56#[async_trait]
57pub trait Authenticable: Clone {
58    async fn find_by_api_key(db: &DatabaseConnection, api_key: &str) -> ModelResult<Self>;
59    async fn find_by_claims_key(db: &DatabaseConnection, claims_key: &str) -> ModelResult<Self>;
60}