b453d5d
use axum::Json;
use axum::http::StatusCode;
use axum::response::{IntoResponse, Response};
use serde::{Deserialize, Serialize};
use std::fmt;
use utoipa::ToSchema;
#[derive(Debug, Serialize, Deserialize, ToSchema)]
pub struct NoData;
#[derive(Serialize, Deserialize, Debug, ToSchema)]
pub struct AppResponseData<T> {
pub code: i32,
pub message: String,
pub data: Option<T>,
pub error: Option<String>,
pub error_code: Option<String>,
pub request_id: String,
pub log_id: String,
}
impl<T> AppResponseData<T>
where
T: Serialize,
{
pub fn ok(data: T) -> Self {
AppResponseData {
code: 200,
message: "success".to_string(),
data: Some(data),
error: None,
error_code: None,
request_id: String::new(),
log_id: String::new(),
}
}
pub fn err(code: i32, message: impl Into<String>) -> Self {
AppResponseData {
code,
message: message.into(),
data: None,
error: None,
error_code: None,
request_id: String::new(),
log_id: String::new(),
}
}
pub fn err_with_detail(
code: i32,
message: impl Into<String>,
detail: impl Into<String>,
) -> Self {
AppResponseData {
code,
message: message.into(),
data: None,
error: Some(detail.into()),
error_code: None,
request_id: String::new(),
log_id: String::new(),
}
}
pub fn with_code(mut self, code: i32) -> Self {
self.code = code;
self
}
pub fn with_message(mut self, message: impl Into<String>) -> Self {
self.message = message.into();
self
}
pub fn with_error(mut self, error: impl Into<String>) -> Self {
self.error = Some(error.into());
self
}
pub fn with_error_code(mut self, code: impl Into<String>) -> Self {
self.error_code = Some(code.into());
self
}
pub fn with_request_id(mut self, request_id: impl Into<String>) -> Self {
self.request_id = request_id.into();
self
}
pub fn with_log_id(mut self, log_id: impl Into<String>) -> Self {
self.log_id = log_id.into();
self
}
}
impl AppResponseData<NoData> {
pub fn empty() -> Self {
AppResponseData {
code: 200,
message: "success".to_string(),
data: None,
error: None,
error_code: None,
request_id: String::new(),
log_id: String::new(),
}
}
}
impl fmt::Display for AppResponseData<()> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "API error: code={}, message={}", self.code, self.message)
}
}
impl<T: Serialize> IntoResponse for AppResponseData<T> {
fn into_response(self) -> Response {
let status =
StatusCode::from_u16(self.code as u16).unwrap_or(StatusCode::INTERNAL_SERVER_ERROR);
(status, Json(self)).into_response()
}
}