open_lark/service/cloud_docs/bitable/v1/app/
copy.rs1use reqwest::Method;
2use serde::{Deserialize, Serialize};
3
4use crate::{
5 core::{
6 api_req::ApiRequest,
7 api_resp::{ApiResponseTrait, BaseResponse, ResponseFormat},
8 constants::AccessTokenType,
9 endpoints::cloud_docs::*,
10 http::Transport,
11 req_option::RequestOption,
12 SDKResult,
13 },
14 impl_executable_builder_owned,
15};
16
17use super::AppService;
18
19impl AppService {
20 pub async fn copy(
22 &self,
23 request: CopyAppRequest,
24 option: Option<RequestOption>,
25 ) -> SDKResult<BaseResponse<CopyAppResponse>> {
26 let mut api_req = request.api_request;
27 api_req.http_method = Method::POST;
28 api_req.api_path = BITABLE_V1_APP_COPY.replace("{app_token}", &request.app_token);
29 api_req.supported_access_token_types = vec![AccessTokenType::Tenant, AccessTokenType::User];
30 api_req.body = serde_json::to_vec(&CopyAppRequestBody {
31 name: request.name,
32 folder_token: request.folder_token,
33 time_zone: request.time_zone,
34 })?;
35
36 let api_resp = Transport::request(api_req, &self.config, option).await?;
37 Ok(api_resp)
38 }
39}
40
41#[derive(Debug, Default)]
43pub struct CopyAppRequest {
44 api_request: ApiRequest,
45 app_token: String,
47 name: Option<String>,
49 folder_token: Option<String>,
51 time_zone: Option<String>,
53}
54
55impl CopyAppRequest {
56 pub fn builder() -> CopyAppRequestBuilder {
57 CopyAppRequestBuilder::default()
58 }
59}
60
61#[derive(Default)]
62pub struct CopyAppRequestBuilder {
63 request: CopyAppRequest,
64}
65
66impl CopyAppRequestBuilder {
67 pub fn app_token(mut self, app_token: impl ToString) -> Self {
69 self.request.app_token = app_token.to_string();
70 self
71 }
72
73 pub fn name(mut self, name: impl ToString) -> Self {
75 self.request.name = Some(name.to_string());
76 self
77 }
78
79 pub fn folder_token(mut self, folder_token: impl ToString) -> Self {
81 self.request.folder_token = Some(folder_token.to_string());
82 self
83 }
84
85 pub fn time_zone(mut self, time_zone: impl ToString) -> Self {
87 self.request.time_zone = Some(time_zone.to_string());
88 self
89 }
90
91 pub fn build(self) -> CopyAppRequest {
92 self.request
93 }
94}
95
96impl_executable_builder_owned!(
97 CopyAppRequestBuilder,
98 AppService,
99 CopyAppRequest,
100 BaseResponse<CopyAppResponse>,
101 copy
102);
103
104#[derive(Serialize)]
105struct CopyAppRequestBody {
106 #[serde(skip_serializing_if = "Option::is_none")]
107 name: Option<String>,
108 #[serde(skip_serializing_if = "Option::is_none")]
109 folder_token: Option<String>,
110 #[serde(skip_serializing_if = "Option::is_none")]
111 time_zone: Option<String>,
112}
113
114#[derive(Deserialize, Debug)]
115pub struct CopyAppResponse {
116 pub app: CopyAppResponseData,
118}
119
120#[derive(Deserialize, Debug)]
121pub struct CopyAppResponseData {
122 pub app_token: String,
124 pub name: String,
126 pub revision: i32,
128 pub url: String,
130}
131
132impl ApiResponseTrait for CopyAppResponse {
133 fn data_format() -> ResponseFormat {
134 ResponseFormat::Data
135 }
136}
137
138#[cfg(test)]
139#[allow(unused_variables, unused_unsafe)]
140mod tests {
141 use super::*;
142 use serde_json::json;
143
144 #[test]
145 fn test_copy_app_request() {
146 let request = CopyAppRequest::builder()
147 .app_token("bascnmBA*****yGehy8")
148 .name("复制的多维表格")
149 .folder_token("fldcnmBA*****yGehy8")
150 .time_zone("Asia/Shanghai")
151 .build();
152
153 assert_eq!(request.app_token, "bascnmBA*****yGehy8");
154 assert_eq!(request.name, Some("复制的多维表格".to_string()));
155 assert_eq!(
156 request.folder_token,
157 Some("fldcnmBA*****yGehy8".to_string())
158 );
159 assert_eq!(request.time_zone, Some("Asia/Shanghai".to_string()));
160 }
161
162 #[test]
163 fn test_copy_app_request_body_serialization() {
164 let body = CopyAppRequestBody {
165 name: Some("复制的多维表格".to_string()),
166 folder_token: Some("fldcnmBA*****yGehy8".to_string()),
167 time_zone: Some("Asia/Shanghai".to_string()),
168 };
169
170 let serialized = serde_json::to_value(&body).unwrap();
171 let expected = json!({
172 "name": "复制的多维表格",
173 "folder_token": "fldcnmBA*****yGehy8",
174 "time_zone": "Asia/Shanghai"
175 });
176
177 assert_eq!(serialized, expected);
178 }
179}