linkrs_server/web/
error.rs1use axum::{
4 http::StatusCode,
5 response::{IntoResponse, Json},
6};
7use serde_json::json;
8use thiserror::Error;
9
10#[derive(Error, Debug)]
12pub enum WebError {
13 #[error("Storage error: {0}")]
14 Storage(String),
15
16 #[error("Invalid request: {0}")]
17 BadRequest(String),
18
19 #[error("Not found: {0}")]
20 NotFound(String),
21
22 #[error("Unauthorized: {0}")]
23 Unauthorized(String),
24
25 #[error("Internal error: {0}")]
26 Internal(String),
27
28 #[error("Query error: {0}")]
29 Query(String),
30}
31
32impl IntoResponse for WebError {
33 fn into_response(self) -> axum::response::Response {
34 let (status, error_code, message) = match &self {
35 WebError::Storage(msg) => (
36 StatusCode::INTERNAL_SERVER_ERROR,
37 "STORAGE_ERROR",
38 msg.clone(),
39 ),
40 WebError::BadRequest(msg) => (StatusCode::BAD_REQUEST, "BAD_REQUEST", msg.clone()),
41 WebError::NotFound(msg) => (StatusCode::NOT_FOUND, "NOT_FOUND", msg.clone()),
42 WebError::Unauthorized(msg) => (StatusCode::UNAUTHORIZED, "UNAUTHORIZED", msg.clone()),
43 WebError::Internal(msg) => (
44 StatusCode::INTERNAL_SERVER_ERROR,
45 "INTERNAL_ERROR",
46 msg.clone(),
47 ),
48 WebError::Query(msg) => (StatusCode::BAD_REQUEST, "QUERY_ERROR", msg.clone()),
49 };
50
51 let body = Json(json!({
52 "success": false,
53 "error": {
54 "code": error_code,
55 "message": message
56 }
57 }));
58
59 (status, body).into_response()
60 }
61}
62
63impl From<sqlx::Error> for WebError {
64 fn from(err: sqlx::Error) -> Self {
65 match err {
66 sqlx::Error::RowNotFound => WebError::NotFound("Record not found".to_string()),
67 _ => WebError::Storage(err.to_string()),
68 }
69 }
70}
71
72pub type WebResult<T> = Result<T, WebError>;