1use crate::{InternalError, access::AccessError, dto::prelude::*};
2use std::fmt::{self, Display};
3
4#[derive(CandidType, Clone, Debug, Deserialize, Eq, PartialEq)]
12pub struct Error {
13 pub code: ErrorCode,
14 pub message: String,
15}
16
17impl Error {
18 #[must_use]
19 pub const fn new(code: ErrorCode, message: String) -> Self {
20 Self { code, message }
21 }
22
23 pub fn conflict(message: impl Into<String>) -> Self {
25 Self::new(ErrorCode::Conflict, message.into())
26 }
27
28 pub fn policy(code: ErrorCode, message: impl Into<String>) -> Self {
30 Self::new(code, message.into())
31 }
32
33 pub fn forbidden(message: impl Into<String>) -> Self {
35 Self::new(ErrorCode::Forbidden, message.into())
36 }
37
38 pub fn internal(message: impl Into<String>) -> Self {
40 Self::new(ErrorCode::Internal, message.into())
41 }
42
43 pub fn invalid(message: impl Into<String>) -> Self {
45 Self::new(ErrorCode::InvalidInput, message.into())
46 }
47
48 pub fn invariant(message: impl Into<String>) -> Self {
50 Self::new(ErrorCode::InvariantViolation, message.into())
51 }
52
53 pub fn exhausted(message: impl Into<String>) -> Self {
55 Self::new(ErrorCode::ResourceExhausted, message.into())
56 }
57
58 pub fn not_found(message: impl Into<String>) -> Self {
60 Self::new(ErrorCode::NotFound, message.into())
61 }
62
63 pub fn unauthorized(message: impl Into<String>) -> Self {
65 Self::new(ErrorCode::Unauthorized, message.into())
66 }
67
68 pub fn unavailable(message: impl Into<String>) -> Self {
70 Self::new(ErrorCode::Unavailable, message.into())
71 }
72}
73
74impl Display for Error {
75 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
76 write!(f, "[{:?}] {}", self.code, self.message)
77 }
78}
79
80impl From<AccessError> for Error {
81 fn from(err: AccessError) -> Self {
82 Self::from(InternalError::from(err))
83 }
84}
85
86#[derive(CandidType, Clone, Copy, Debug, Deserialize, Eq, PartialEq)]
94#[non_exhaustive]
95#[remain::sorted]
96pub enum ErrorCode {
97 Conflict,
98 Forbidden,
99 Internal,
100 InvalidInput,
101 InvariantViolation,
102 NotFound,
103 PolicyReplicaRequiresSingletonWithScaling,
104 PolicyRoleAlreadyRegistered,
105 PolicyShardRequiresSingletonWithSharding,
106 PolicySingletonAlreadyRegisteredUnderParent,
107 PolicyTenantRequiresSingletonParent,
108 ResourceExhausted,
109 Unauthorized,
110 Unavailable,
111}