nullnet_libdatastore/
client.rs

1use crate::datastore::store_service_client::StoreServiceClient;
2#[allow(clippy::wildcard_imports)]
3use crate::datastore::*;
4use crate::utils::{authorize_request, validate_response_and_convert_to_reponse_data};
5use crate::{DatastoreConfig, ResponseData};
6use nullnet_liberror::{Error, ErrorHandler, Location, location};
7use tonic::transport::Channel;
8
9/// A client for interacting with the datastore service.
10#[derive(Debug, Clone)]
11pub struct DatastoreClient {
12    /// Datastore gRPC endpoint
13    client: StoreServiceClient<Channel>,
14}
15
16impl DatastoreClient {
17    /// Creates a new instance of `DatastoreClient`.
18    ///
19    /// # Arguments
20    /// * `config` - The configuration settings for connecting to the datastore.
21    #[allow(clippy::missing_errors_doc)]
22    pub async fn new(config: DatastoreConfig) -> Result<Self, Error> {
23        let channel = config.connect().await?;
24        let client = StoreServiceClient::new(channel).max_decoding_message_size(50 * 1024 * 1024);
25        Ok(Self { client })
26    }
27
28    /// Logs in to the datastore service with the provided request.
29    ///
30    /// # Arguments
31    /// * `request` - The login request containing the necessary credentials.
32    ///
33    /// # Returns
34    /// * `Ok(LoginResponse)` - The response received after a successful login.
35    /// * `Err(Error)` - If the login fails or if an error occurs during the process.
36    #[allow(clippy::missing_errors_doc)]
37    pub async fn login(&mut self, request: LoginRequest) -> Result<LoginResponse, Error> {
38        let response = self.client.login(request).await.handle_err(location!())?;
39
40        Ok(response.into_inner())
41    }
42
43    /// Creates multiple records in the datastore with the provided request.
44    ///
45    /// # Arguments
46    /// * `request` - The batch create request containing the records to be created.
47    /// * `token` - The authorization token to authorize the request.
48    ///
49    /// # Returns
50    /// * `Ok(ResponseData)` - The response data containing the result of the operation.
51    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
52    #[allow(clippy::missing_errors_doc)]
53    pub async fn batch_create(
54        &mut self,
55        request: BatchCreateRequest,
56        token: &str,
57    ) -> Result<ResponseData, Error> {
58        let request = authorize_request(request, token)?;
59
60        let response = self
61            .client
62            .batch_create(request)
63            .await
64            .handle_err(location!())?;
65
66        validate_response_and_convert_to_reponse_data(response.get_ref())
67    }
68
69    /// Creates a single record in the datastore with the provided request.
70    ///
71    /// # Arguments
72    /// * `request` - The create request containing the record to be created.
73    /// * `token` - The authorization token to authorize the request.
74    ///
75    /// # Returns
76    /// * `Ok(ResponseData)` - The response data containing the result of the operation.
77    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
78    #[allow(clippy::missing_errors_doc)]
79    pub async fn create(
80        &mut self,
81        request: CreateRequest,
82        token: &str,
83    ) -> Result<ResponseData, Error> {
84        let request = authorize_request(request, token)?;
85
86        let response = self.client.create(request).await.handle_err(location!())?;
87
88        validate_response_and_convert_to_reponse_data(response.get_ref())
89    }
90
91    /// Deletes a record from the datastore with the provided request.
92    ///
93    /// # Arguments
94    /// * `request` - The delete request containing the identifier of the record to be deleted.
95    /// * `token` - The authorization token to authorize the request.
96    ///
97    /// # Returns
98    /// * `Ok(ResponseData)` - The response data containing the result of the operation.
99    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
100    #[allow(clippy::missing_errors_doc)]
101    pub async fn delete(
102        &mut self,
103        request: DeleteRequest,
104        token: &str,
105    ) -> Result<ResponseData, Error> {
106        let request = authorize_request(request, token)?;
107
108        let response = self.client.delete(request).await.handle_err(location!())?;
109
110        validate_response_and_convert_to_reponse_data(response.get_ref())
111    }
112
113    /// Deletes multiple records from the datastore with the provided request.
114    ///
115    /// # Arguments
116    /// * `request` - The batch delete request containing the identifiers of the records to be deleted.
117    /// * `token` - The authorization token to authorize the request.
118    ///
119    /// # Returns
120    /// * `Ok(ResponseData)` - The response data containing the result of the operation.
121    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
122    #[allow(clippy::missing_errors_doc)]
123    pub async fn batch_delete(
124        &mut self,
125        request: BatchDeleteRequest,
126        token: &str,
127    ) -> Result<ResponseData, Error> {
128        let request = authorize_request(request, token)?;
129
130        let response = self
131            .client
132            .batch_delete(request)
133            .await
134            .handle_err(location!())?;
135
136        validate_response_and_convert_to_reponse_data(response.get_ref())
137    }
138
139    /// Updates a record in the datastore with the provided request.
140    ///
141    /// # Arguments
142    /// * `request` - The update request containing the record's updated data.
143    /// * `token` - The authorization token to authorize the request.
144    ///
145    /// # Returns
146    /// * `Ok(ResponseData)` - The response data containing the result of the operation.
147    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
148    #[allow(clippy::missing_errors_doc)]
149    pub async fn update(
150        &mut self,
151        request: UpdateRequest,
152        token: &str,
153    ) -> Result<ResponseData, Error> {
154        let request = authorize_request(request, token)?;
155
156        let response = self.client.update(request).await.handle_err(location!())?;
157
158        validate_response_and_convert_to_reponse_data(response.get_ref())
159    }
160
161    /// Updates multiple records in the datastore with the provided request.
162    ///
163    /// # Arguments
164    /// * `request` - The batch update request containing the updated data for multiple records.
165    /// * `token` - The authorization token to authorize the request.
166    ///
167    /// # Returns
168    /// * `Ok(ResponseData)` - The response data containing the result of the operation.
169    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
170    #[allow(clippy::missing_errors_doc)]
171    pub async fn batch_update(
172        &mut self,
173        request: BatchUpdateRequest,
174        token: &str,
175    ) -> Result<ResponseData, Error> {
176        let request = authorize_request(request, token)?;
177
178        let response = self
179            .client
180            .batch_update(request)
181            .await
182            .handle_err(location!())?;
183
184        validate_response_and_convert_to_reponse_data(response.get_ref())
185    }
186
187    /// Retrieves records from the datastore based on the specified filter.
188    ///
189    /// # Arguments
190    /// * `request` - The request containing the filter criteria.
191    /// * `token` - The authorization token to authorize the request.
192    ///
193    /// # Returns
194    /// * `Ok(ResponseData)` - The response data containing the records that match the filter.
195    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
196    #[allow(clippy::missing_errors_doc)]
197    pub async fn get_by_filter(
198        &mut self,
199        request: GetByFilterRequest,
200        token: &str,
201    ) -> Result<ResponseData, Error> {
202        let request = authorize_request(request, token)?;
203
204        let response = self
205            .client
206            .get_by_filter(request)
207            .await
208            .handle_err(location!())?;
209
210        validate_response_and_convert_to_reponse_data(response.get_ref())
211    }
212
213    /// Performs aggregation on records in the datastore based on the provided request.
214    ///
215    /// # Arguments
216    /// * `request` - The aggregation request specifying the criteria for aggregation.
217    /// * `token` - The authorization token to authorize the request.
218    ///
219    /// # Returns
220    /// * `Ok(ResponseData)` - The response data containing the result of the aggregation.
221    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
222    #[allow(clippy::missing_errors_doc)]
223    pub async fn aggregate(
224        &mut self,
225        request: AggregateRequest,
226        token: &str,
227    ) -> Result<ResponseData, Error> {
228        let request = authorize_request(request, token)?;
229
230        let response = self
231            .client
232            .aggregate(request)
233            .await
234            .handle_err(location!())?;
235
236        validate_response_and_convert_to_reponse_data(response.get_ref())
237    }
238
239    /// Retrieves a record from the datastore by its identifier.
240    ///
241    /// # Arguments
242    /// * `request` - The request containing the identifier of the record to be retrieved.
243    /// * `token` - The authorization token to authorize the request.
244    ///
245    /// # Returns
246    /// * `Ok(ResponseData)` - The response data containing the requested record.
247    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
248    #[allow(clippy::missing_errors_doc)]
249    pub async fn get_by_id(
250        &mut self,
251        request: GetByIdRequest,
252        token: &str,
253    ) -> Result<ResponseData, Error> {
254        let request = authorize_request(request, token)?;
255
256        let response = self
257            .client
258            .get_by_id(request)
259            .await
260            .handle_err(location!())?;
261
262        validate_response_and_convert_to_reponse_data(response.get_ref())
263    }
264
265    /// Updates (if already present) or creates (if not) a record in the datastore.
266    ///
267    /// # Arguments
268    /// * `request` - The request containing the record to be updated or created (based on a list of conflict columns).
269    /// * `token` - The authorization token to authorize the request.
270    ///
271    /// # Returns
272    /// * `Ok(ResponseData)` - The response data containing the result of the operation.
273    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
274    #[allow(clippy::missing_errors_doc)]
275    pub async fn upsert(
276        &mut self,
277        request: UpsertRequest,
278        token: &str,
279    ) -> Result<ResponseData, Error> {
280        let request = authorize_request(request, token)?;
281
282        let response = self.client.upsert(request).await.handle_err(location!())?;
283
284        validate_response_and_convert_to_reponse_data(response.get_ref())
285    }
286
287    /// Registeres a new account
288    ///
289    /// # Arguments
290    /// * `request` - The request containing the account info.
291    /// * `token` - The authorization token to authorize the request.
292    ///
293    /// # Returns
294    /// * `Ok(RegisterResponse)` - The response data containing the result of the operation.
295    /// * `Err(Error)` - If the operation fails or if an error occurs during the process.
296    #[allow(clippy::missing_errors_doc)]
297    pub async fn register_device(
298        &mut self,
299        request: RegisterDeviceRequest,
300        token: &str,
301    ) -> Result<ResponseData, Error> {
302        let request = authorize_request(request, token)?;
303
304        let response = self
305            .client
306            .register_device(request)
307            .await
308            .handle_err(location!())?;
309
310        validate_response_and_convert_to_reponse_data(response.get_ref())
311    }
312}