error.rs
1 use std::process::ExitStatus; 2 3 use axum::http; 4 use axum::response::{IntoResponse, Response}; 5 6 /// Errors relating to the Git backend. 7 #[derive(Debug, thiserror::Error)] 8 pub enum GitError { 9 /// The entity was not found. 10 #[error("not found")] 11 NotFound, 12 13 /// I/O error. 14 #[error("i/o error: {0}")] 15 Io(#[from] std::io::Error), 16 17 /// The service is not available. 18 #[error("service '{0}' not available")] 19 ServiceUnavailable(&'static str), 20 21 /// Invalid identifier. 22 #[error("invalid radicle identifier: {0}")] 23 Id(#[from] radicle::identity::IdError), 24 25 /// Git backend error. 26 #[error("git-http-backend: exited with code {0}")] 27 BackendExited(ExitStatus), 28 29 /// Git backend error. 30 #[error("git-http-backend: invalid header returned: {0:?}")] 31 BackendHeader(String), 32 33 /// HeaderName error. 34 #[error(transparent)] 35 InvalidHeaderName(#[from] axum::http::header::InvalidHeaderName), 36 37 /// HeaderValue error. 38 #[error(transparent)] 39 InvalidHeaderValue(#[from] axum::http::header::InvalidHeaderValue), 40 } 41 42 impl GitError { 43 pub fn status(&self) -> http::StatusCode { 44 match self { 45 GitError::ServiceUnavailable(_) => http::StatusCode::SERVICE_UNAVAILABLE, 46 GitError::Id(_) => http::StatusCode::NOT_FOUND, 47 GitError::NotFound => http::StatusCode::NOT_FOUND, 48 _ => http::StatusCode::INTERNAL_SERVER_ERROR, 49 } 50 } 51 } 52 53 impl IntoResponse for GitError { 54 fn into_response(self) -> Response { 55 tracing::error!("{}", self); 56 57 self.status().into_response() 58 } 59 } 60 61 /// Errors relating to the `/raw` route. 62 #[derive(Debug, thiserror::Error)] 63 pub enum RawError { 64 /// Surf error. 65 #[error(transparent)] 66 Surf(#[from] radicle_surf::Error), 67 68 /// Git error. 69 #[error(transparent)] 70 Git(#[from] radicle::git::ext::Error), 71 72 /// Radicle Storage error. 73 #[error(transparent)] 74 Storage(#[from] radicle::storage::Error), 75 76 /// Http Headers error. 77 #[error(transparent)] 78 Headers(#[from] http::header::InvalidHeaderValue), 79 80 /// Surf file error. 81 #[error(transparent)] 82 SurfFile(#[from] radicle_surf::fs::error::File), 83 } 84 85 impl RawError { 86 pub fn status(&self) -> http::StatusCode { 87 match self { 88 RawError::SurfFile(_) => http::StatusCode::NOT_FOUND, 89 _ => http::StatusCode::INTERNAL_SERVER_ERROR, 90 } 91 } 92 } 93 94 impl IntoResponse for RawError { 95 fn into_response(self) -> Response { 96 tracing::error!("{}", self); 97 98 self.status().into_response() 99 } 100 }