1use crate::constants::*;
2use crate::utils::{deserialize_option_u32_from_str_or_num, deserialize_u32_from_str_or_num};
3use serde::{Deserialize, Serialize};
4
5#[derive(Debug, Serialize, Deserialize)]
6pub struct R<T> {
7 pub success: bool,
8 pub code: i32,
9 pub msg: Option<String>,
10 pub data: Option<T>,
11 #[serde(skip)]
12 pub def_exec: bool,
13 #[serde(default, skip_serializing_if = "String::is_empty")]
14 pub path: String,
15 #[serde(default, skip_serializing_if = "String::is_empty")]
16 pub version: String,
17 #[serde(default, skip_serializing_if = "String::is_empty")]
18 pub base_version: String,
19 pub timestamp: i64,
20}
21
22impl<T> R<T> {
23 pub fn new(code: i32, msg: Option<String>, data: Option<T>) -> Self {
24 Self {
25 success: code == SUCCESS_CODE,
26 code,
27 msg,
28 data,
29 def_exec: false,
30 path: String::new(),
31 version: String::new(),
32 base_version: String::new(),
33 timestamp: chrono::Local::now().timestamp_millis(),
34 }
35 }
36
37 pub fn ok() -> Self {
38 Self::new(SUCCESS_CODE, Some(SUCCESS_MESSAGE.into()), None)
39 }
40
41 pub fn ok_with_data(data: T) -> Self {
42 Self::new(SUCCESS_CODE, Some(SUCCESS_MESSAGE.into()), Some(data))
43 }
44
45 pub fn fail() -> Self {
46 Self::new(OPERATION_EX_CODE, None, None)
47 }
48
49 pub fn fail_with_code(code: i32, msg: String) -> Self {
50 Self::new(code, Some(msg.into()), None)
51 }
52
53 pub fn fail_with_message(msg: String) -> Self {
54 Self::new(FAIL_CODE, Some(msg.into()), None)
55 }
56}
57
58#[derive(Debug, Clone, Serialize, Deserialize)]
60pub struct CursorPageBaseResp<T> {
61 #[serde(skip_serializing_if = "Option::is_none")]
63 pub cursor: Option<u32>,
64 pub is_last: bool,
66 pub list: Vec<T>,
68 pub total: i64,
70}
71
72impl<T> CursorPageBaseResp<T> {
73 pub fn init(cursor: Option<u32>, is_last: bool, list: Vec<T>, total: i64) -> Self {
80 Self {
81 cursor,
82 is_last,
83 list,
84 total,
85 }
86 }
87
88 pub fn is_empty(&self) -> bool {
90 self.list.is_empty()
91 }
92
93 pub fn empty() -> Self {
95 Self {
96 cursor: None,
97 is_last: true,
98 list: Vec::new(),
99 total: 0,
100 }
101 }
102}
103
104impl<T> Default for CursorPageBaseResp<T> {
105 fn default() -> Self {
106 Self {
107 cursor: None,
108 is_last: false,
109 list: Vec::new(),
110 total: 0,
111 }
112 }
113}
114
115#[derive(Debug, Clone, Serialize, Deserialize)]
117pub struct CursorPageBaseReq {
118 #[serde(
120 default = "CursorPageBaseReq::default_page_size",
121 deserialize_with = "deserialize_u32_from_str_or_num"
122 )]
123 pub page_size: u32,
124 #[serde(
126 default,
127 skip_serializing_if = "Option::is_none",
128 deserialize_with = "deserialize_option_u32_from_str_or_num"
129 )]
130 pub cursor: Option<u32>,
131}
132
133impl CursorPageBaseReq {
134 fn default_page_size() -> u32 {
135 10
136 }
137
138 pub fn is_first_page(&self) -> bool {
140 self.cursor
141 .as_ref()
142 .map(|s| *s == 0 || *s < self.page_size)
143 .unwrap_or(true)
144 }
145
146 pub fn plus_page(&self) -> (u32, u32) {
150 (1, self.page_size)
151 }
152}
153
154impl Default for CursorPageBaseReq {
155 fn default() -> Self {
156 Self {
157 page_size: Self::default_page_size(),
158 cursor: None,
159 }
160 }
161}