Files
continuwuity/src/core/error/response.rs
T

Ignoring revisions in .git-blame-ignore-revs. Click here to bypass and see the normal blame view.

136 lines
3.1 KiB
Rust
Raw Normal View History

2024-07-13 02:15:15 +00:00
use bytes::BytesMut;
use http::StatusCode;
use http_body_util::Full;
use ruma::api::{
OutgoingResponse,
client::{
error::{ErrorBody, ErrorKind},
uiaa::UiaaResponse,
},
};
2024-07-13 02:15:15 +00:00
use super::Error;
use crate::error;
impl axum::response::IntoResponse for Error {
fn into_response(self) -> axum::response::Response {
2026-02-05 21:08:08 +00:00
let status = self.status_code();
if status.is_server_error() {
error!(
error = %self,
error_debug = ?self,
kind = ?self.kind(),
status = %status,
"Server error"
);
} else if status.is_client_error() {
use crate::debug_error;
debug_error!(
error = %self,
kind = ?self.kind(),
status = %status,
"Client error"
);
}
2024-07-13 02:15:15 +00:00
let response: UiaaResponse = self.into();
response
.try_into_http_response::<BytesMut>()
.inspect_err(|e| error!("error response error: {e}"))
.map_or_else(
|_| StatusCode::INTERNAL_SERVER_ERROR.into_response(),
|r| r.map(BytesMut::freeze).map(Full::new).into_response(),
)
}
}
impl From<Error> for UiaaResponse {
#[inline]
2024-07-13 02:15:15 +00:00
fn from(error: Error) -> Self {
if let Error::Uiaa(uiaainfo) = error {
return Self::AuthResponse(uiaainfo);
}
let body = ErrorBody::Standard {
2024-07-13 02:15:15 +00:00
kind: error.kind(),
message: error.message(),
};
Self::MatrixError(ruma::api::client::error::Error {
status_code: error.status_code(),
body,
})
}
}
pub(super) fn status_code(kind: &ErrorKind, hint: StatusCode) -> StatusCode {
if hint == StatusCode::BAD_REQUEST {
bad_request_code(kind)
} else {
hint
}
}
pub(super) fn bad_request_code(kind: &ErrorKind) -> StatusCode {
use ErrorKind::*;
2024-07-13 02:15:15 +00:00
match kind {
// 429
| LimitExceeded { .. } => StatusCode::TOO_MANY_REQUESTS,
// 413
| TooLarge => StatusCode::PAYLOAD_TOO_LARGE,
// 405
| Unrecognized => StatusCode::METHOD_NOT_ALLOWED,
// 404
| NotFound | NotImplemented | FeatureDisabled | SenderIgnored { .. } =>
StatusCode::NOT_FOUND,
// 403
| GuestAccessForbidden
2024-07-13 02:15:15 +00:00
| ThreepidAuthFailed
| UserDeactivated
| ThreepidDenied
2025-09-21 17:03:40 +00:00
| InviteBlocked
| WrongRoomKeysVersion { .. }
| UserSuspended
| Forbidden { .. } => StatusCode::FORBIDDEN,
2024-07-13 02:15:15 +00:00
// 401
| UnknownToken { .. } | MissingToken | Unauthorized | UserLocked =>
StatusCode::UNAUTHORIZED,
2024-07-13 02:15:15 +00:00
// 400
| _ => StatusCode::BAD_REQUEST,
2024-07-13 02:15:15 +00:00
}
}
pub(super) fn ruma_error_message(error: &ruma::api::client::error::Error) -> String {
if let ErrorBody::Standard { message, .. } = &error.body {
2025-03-22 07:09:11 +00:00
return message.clone();
2024-07-13 02:15:15 +00:00
}
format!("{error}")
}
pub(super) fn ruma_error_kind(e: &ruma::api::client::error::Error) -> &ErrorKind {
e.error_kind().unwrap_or(&ErrorKind::Unknown)
2024-07-13 02:15:15 +00:00
}
pub(super) fn io_error_code(kind: std::io::ErrorKind) -> StatusCode {
use std::io::ErrorKind;
match kind {
| ErrorKind::InvalidInput => StatusCode::BAD_REQUEST,
| ErrorKind::PermissionDenied => StatusCode::FORBIDDEN,
| ErrorKind::NotFound => StatusCode::NOT_FOUND,
| ErrorKind::TimedOut => StatusCode::GATEWAY_TIMEOUT,
| ErrorKind::FileTooLarge => StatusCode::PAYLOAD_TOO_LARGE,
| ErrorKind::StorageFull => StatusCode::INSUFFICIENT_STORAGE,
| ErrorKind::Interrupted => StatusCode::SERVICE_UNAVAILABLE,
| _ => StatusCode::INTERNAL_SERVER_ERROR,
}
}