1use crate::client::{Client, Data, RequestOptions};
4use crate::error::Error;
5use crate::models::*;
6use crate::multipart::Form;
7use crate::pagination::{iterate, Page};
8
9impl Client {
10 pub fn cameras(&self) -> CamerasService<'_> {
12 CamerasService::new(self)
13 }
14
15 pub fn photos(&self) -> PhotosService<'_> {
17 PhotosService::new(self)
18 }
19
20 pub fn recognitions(&self) -> RecognitionsService<'_> {
22 RecognitionsService::new(self)
23 }
24}
25
26
27#[derive(Debug, Clone)]
31pub struct CamerasService<'a> {
32 client: &'a Client,
33 options: RequestOptions,
34}
35
36impl<'a> CamerasService<'a> {
37 pub(crate) fn new(client: &'a Client) -> Self {
38 Self { client, options: RequestOptions::default() }
39 }
40
41 pub fn api_key(mut self, key: impl Into<String>) -> Self {
43 self.options.api_key = Some(key.into());
44 self
45 }
46
47 pub fn options(mut self, options: RequestOptions) -> Self {
49 self.options = options;
50 self
51 }
52
53 pub fn list(&self) -> Result<Vec<Camera>, Error> {
55 let out: Data<Vec<Camera>> = self.client.request("GET", "/api/v1/cameras", &[], None, &self.options)?;
56 Ok(out.data)
57 }
58}
59
60impl PhotosDetectParams {
61 fn form(&self) -> Form<'_> {
65 let mut form = Form::new();
66 form.file("image", &self.image);
67 if let Some(value) = &self.image_mode {
68 form.text("image_mode", value.to_string());
69 }
70 if let Some(value) = &self.lpr_confidence {
71 form.text("lpr_confidence", value.to_string());
72 }
73 if let Some(value) = &self.min_ocr_confidence {
74 form.text("min_ocr_confidence", value.to_string());
75 }
76 form
77 }
78}
79
80impl PhotosOCRParams {
81 fn form(&self) -> Form<'_> {
85 let mut form = Form::new();
86 form.file("image", &self.image);
87 form
88 }
89}
90
91impl PhotosRecognizeParams {
92 fn form(&self) -> Form<'_> {
96 let mut form = Form::new();
97 form.file("image", &self.image);
98 if let Some(value) = &self.image_mode {
99 form.text("image_mode", value.to_string());
100 }
101 if let Some(value) = &self.lpr_confidence {
102 form.text("lpr_confidence", value.to_string());
103 }
104 if let Some(value) = &self.min_ocr_confidence {
105 form.text("min_ocr_confidence", value.to_string());
106 }
107 form
108 }
109}
110
111#[derive(Debug, Clone)]
115pub struct PhotosService<'a> {
116 client: &'a Client,
117 options: RequestOptions,
118}
119
120impl<'a> PhotosService<'a> {
121 pub(crate) fn new(client: &'a Client) -> Self {
122 Self { client, options: RequestOptions::default() }
123 }
124
125 pub fn api_key(mut self, key: impl Into<String>) -> Self {
127 self.options.api_key = Some(key.into());
128 self
129 }
130
131 pub fn options(mut self, options: RequestOptions) -> Self {
133 self.options = options;
134 self
135 }
136
137 pub fn detect(&self, params: &PhotosDetectParams) -> Result<PhotoDetection, Error> {
139 self.client.request("POST", "/api/v1/detect", &[], Some(params.form()), &self.options)
140 }
141
142 pub fn ocr(&self, params: &PhotosOCRParams) -> Result<PlateReading, Error> {
144 self.client.request("POST", "/api/v1/ocr", &[], Some(params.form()), &self.options)
145 }
146
147 pub fn recognize(&self, params: &PhotosRecognizeParams) -> Result<PhotoRecognition, Error> {
149 self.client.request("POST", "/api/v1/recognize", &[], Some(params.form()), &self.options)
150 }
151}
152
153#[derive(Debug, Clone, Default, PartialEq, Eq)]
155#[non_exhaustive]
156pub struct RecognitionsListParams {
157 pub before: Option<String>,
159 pub plate: Option<String>,
161 pub camera: Option<String>,
163 pub source: Option<String>,
165}
166
167impl RecognitionsListParams {
168 pub fn new() -> Self {
170 Self::default()
171 }
172
173 pub fn before(mut self, before: impl Into<String>) -> Self {
175 self.before = Some(before.into());
176 self
177 }
178
179 pub fn plate(mut self, plate: impl Into<String>) -> Self {
181 self.plate = Some(plate.into());
182 self
183 }
184
185 pub fn camera(mut self, camera: impl Into<String>) -> Self {
187 self.camera = Some(camera.into());
188 self
189 }
190
191 pub fn source(mut self, source: impl Into<String>) -> Self {
193 self.source = Some(source.into());
194 self
195 }
196
197 fn query(&self) -> Vec<(&'static str, String)> {
198 let mut query = Vec::new();
199 if let Some(value) = &self.before {
200 query.push(("before", value.clone()));
201 }
202 if let Some(value) = &self.plate {
203 query.push(("plate", value.clone()));
204 }
205 if let Some(value) = &self.camera {
206 query.push(("camera", value.clone()));
207 }
208 if let Some(value) = &self.source {
209 query.push(("source", value.clone()));
210 }
211 query
212 }
213}
214
215#[derive(Debug, Clone)]
219pub struct RecognitionsService<'a> {
220 client: &'a Client,
221 options: RequestOptions,
222}
223
224impl<'a> RecognitionsService<'a> {
225 pub(crate) fn new(client: &'a Client) -> Self {
226 Self { client, options: RequestOptions::default() }
227 }
228
229 pub fn api_key(mut self, key: impl Into<String>) -> Self {
231 self.options.api_key = Some(key.into());
232 self
233 }
234
235 pub fn options(mut self, options: RequestOptions) -> Self {
237 self.options = options;
238 self
239 }
240
241 pub fn image(&self, id: &str) -> Result<DetectionImageLink, Error> {
243 self.client.request("GET", &format!("/api/v1/detections/{}/image", crate::client::escape(id)), &[], None, &self.options)
244 }
245
246 pub fn list(&self, params: &RecognitionsListParams) -> Result<Page<Recognition>, Error> {
248 self.client.request("GET", "/api/v1/recognitions", ¶ms.query(), None, &self.options)
249 }
250
251 pub fn list_iter(&self, params: RecognitionsListParams) -> impl Iterator<Item = Result<Recognition, Error>> + 'a {
253 let client = self.client;
254 let options = self.options.clone();
255 let path = String::from("/api/v1/recognitions");
256 let first = params.before.clone();
257 iterate(first, move |cursor| {
258 let mut params = params.clone();
259 params.before = cursor.map(str::to_owned);
260 client.request("GET", &path, ¶ms.query(), None, &options)
261 })
262 }
263}
264