1use crate::connection::config::DatabaseResult;
4use wae_types::WaeError;
5
6pub trait FromDatabaseValue: Sized {
8 #[cfg(feature = "turso")]
10 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self>;
11
12 #[cfg(feature = "postgres")]
14 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self>;
15
16 #[cfg(feature = "mysql")]
18 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self>;
19}
20
21#[cfg(all(feature = "turso", not(feature = "postgres"), not(feature = "mysql")))]
22mod database_value_impl {
23 use super::*;
24
25 macro_rules! impl_from_value {
26 ($type:ty, $pattern:pat => $expr:expr) => {
27 impl FromDatabaseValue for $type {
28 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
29 match value {
30 $pattern => Ok($expr),
31 _ => Err(WaeError::invalid_format(stringify!($type), format!("{:?}", value))),
32 }
33 }
34 }
35 };
36 }
37
38 impl_from_value!(i64, turso::Value::Integer(i) => i);
39 impl_from_value!(i32, turso::Value::Integer(i) => i as i32);
40 impl_from_value!(i16, turso::Value::Integer(i) => i as i16);
41 impl_from_value!(u64, turso::Value::Integer(i) => i as u64);
42 impl_from_value!(u32, turso::Value::Integer(i) => i as u32);
43 impl_from_value!(Vec<u8>, turso::Value::Blob(b) => b);
44
45 impl FromDatabaseValue for f64 {
46 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
47 match value {
48 turso::Value::Integer(i) => Ok(i as f64),
49 turso::Value::Text(s) => {
50 s.parse().map_err(|_| WaeError::invalid_format("f64", format!("Cannot parse '{}' as float", s)))
51 }
52 _ => Err(WaeError::invalid_format("f64", format!("{:?}", value))),
53 }
54 }
55 }
56
57 impl FromDatabaseValue for String {
58 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
59 match value {
60 turso::Value::Text(s) => Ok(s),
61 turso::Value::Integer(i) => Ok(i.to_string()),
62 _ => Err(WaeError::invalid_format("String", format!("{:?}", value))),
63 }
64 }
65 }
66
67 impl FromDatabaseValue for bool {
68 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
69 match value {
70 turso::Value::Integer(i) => Ok(i != 0),
71 _ => Err(WaeError::invalid_format("bool", format!("{:?}", value))),
72 }
73 }
74 }
75
76 impl<T: FromDatabaseValue> FromDatabaseValue for Option<T> {
77 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
78 match value {
79 turso::Value::Null => Ok(None),
80 v => T::from_turso_value(v).map(Some),
81 }
82 }
83 }
84}
85
86#[cfg(all(feature = "postgres", not(feature = "turso"), not(feature = "mysql")))]
87mod database_value_impl {
88 use super::*;
89
90 macro_rules! impl_from_value {
91 ($type:ty) => {
92 impl FromDatabaseValue for $type {
93 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
94 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
95 }
96 }
97 };
98 }
99
100 impl_from_value!(i64);
101 impl_from_value!(i32);
102 impl_from_value!(i16);
103 impl_from_value!(f64);
104 impl_from_value!(String);
105 impl_from_value!(Vec<u8>);
106 impl_from_value!(bool);
107
108 impl FromDatabaseValue for u64 {
109 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
110 let i: i64 =
111 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
112 Ok(i as u64)
113 }
114 }
115
116 impl FromDatabaseValue for u32 {
117 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
118 let i: i32 =
119 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
120 Ok(i as u32)
121 }
122 }
123
124 impl FromDatabaseValue for Option<i64> {
125 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
126 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
127 }
128 }
129
130 impl FromDatabaseValue for Option<i32> {
131 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
132 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
133 }
134 }
135
136 impl FromDatabaseValue for Option<i16> {
137 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
138 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
139 }
140 }
141
142 impl FromDatabaseValue for Option<u64> {
143 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
144 let opt: Option<i64> =
145 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
146 Ok(opt.map(|i| i as u64))
147 }
148 }
149
150 impl FromDatabaseValue for Option<u32> {
151 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
152 let opt: Option<i32> =
153 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
154 Ok(opt.map(|i| i as u32))
155 }
156 }
157
158 impl FromDatabaseValue for Option<f64> {
159 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
160 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
161 }
162 }
163
164 impl FromDatabaseValue for Option<String> {
165 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
166 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
167 }
168 }
169
170 impl FromDatabaseValue for Option<Vec<u8>> {
171 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
172 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
173 }
174 }
175
176 impl FromDatabaseValue for Option<bool> {
177 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
178 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
179 }
180 }
181}
182
183#[cfg(all(feature = "mysql", not(feature = "turso"), not(feature = "postgres")))]
184mod database_value_impl {
185 use super::*;
186 use mysql_async::prelude::FromValue;
187
188 macro_rules! impl_from_value {
189 ($type:ty) => {
190 impl FromDatabaseValue for $type {
191 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
192 row.get_opt(index)
193 .transpose()
194 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
195 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))
196 }
197 }
198 };
199 }
200
201 impl_from_value!(i64);
202 impl_from_value!(i32);
203 impl_from_value!(i16);
204 impl_from_value!(f64);
205 impl_from_value!(String);
206 impl_from_value!(Vec<u8>);
207 impl_from_value!(bool);
208
209 impl FromDatabaseValue for u64 {
210 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
211 let i: i64 = row
212 .get_opt(index)
213 .transpose()
214 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
215 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))?;
216 Ok(i as u64)
217 }
218 }
219
220 impl FromDatabaseValue for u32 {
221 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
222 let i: i32 = row
223 .get_opt(index)
224 .transpose()
225 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
226 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))?;
227 Ok(i as u32)
228 }
229 }
230
231 impl<T: FromDatabaseValue + FromValue> FromDatabaseValue for Option<T> {
232 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
233 match row.get_opt::<Option<T>, usize>(index) {
234 Some(Ok(val)) => Ok(val),
235 Some(Err(e)) => Err(WaeError::internal(format!("Failed to get column {}: {:?}", index, e))),
236 None => Ok(None),
237 }
238 }
239 }
240}
241
242#[cfg(any(
243 all(feature = "turso", feature = "postgres"),
244 all(feature = "turso", feature = "mysql"),
245 all(feature = "postgres", feature = "mysql"),
246 all(feature = "turso", feature = "postgres", feature = "mysql")
247))]
248mod database_value_impl {
249 use super::*;
250
251 macro_rules! impl_from_value_multi {
252 ($type:ty) => {
253 impl FromDatabaseValue for $type {
254 #[cfg(feature = "turso")]
255 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
256 match value {
257 turso::Value::Integer(i) => Ok(i as $type),
258 turso::Value::Text(s) => s.parse().map_err(|_| {
259 WaeError::invalid_format(stringify!($type), format!("Cannot parse as {}", stringify!($type)))
260 }),
261 _ => Err(WaeError::invalid_format(stringify!($type), format!("{:?}", value))),
262 }
263 }
264
265 #[cfg(feature = "postgres")]
266 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
267 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
268 }
269
270 #[cfg(feature = "mysql")]
271 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
272 row.get_opt(index)
273 .transpose()
274 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
275 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))
276 }
277 }
278 };
279 }
280
281 impl_from_value_multi!(i64);
282 impl_from_value_multi!(i32);
283 impl_from_value_multi!(i16);
284 impl_from_value_multi!(f64);
285
286 impl FromDatabaseValue for String {
287 #[cfg(feature = "turso")]
288 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
289 match value {
290 turso::Value::Text(s) => Ok(s),
291 turso::Value::Integer(i) => Ok(i.to_string()),
292 _ => Err(WaeError::invalid_format("String", format!("{:?}", value))),
293 }
294 }
295
296 #[cfg(feature = "postgres")]
297 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
298 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
299 }
300
301 #[cfg(feature = "mysql")]
302 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
303 row.get_opt(index)
304 .transpose()
305 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
306 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))
307 }
308 }
309
310 impl FromDatabaseValue for Vec<u8> {
311 #[cfg(feature = "turso")]
312 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
313 match value {
314 turso::Value::Blob(b) => Ok(b),
315 _ => Err(WaeError::invalid_format("Vec<u8>", format!("{:?}", value))),
316 }
317 }
318
319 #[cfg(feature = "postgres")]
320 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
321 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
322 }
323
324 #[cfg(feature = "mysql")]
325 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
326 row.get_opt(index)
327 .transpose()
328 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
329 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))
330 }
331 }
332
333 impl FromDatabaseValue for bool {
334 #[cfg(feature = "turso")]
335 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
336 match value {
337 turso::Value::Integer(i) => Ok(i != 0),
338 _ => Err(WaeError::invalid_format("bool", format!("{:?}", value))),
339 }
340 }
341
342 #[cfg(feature = "postgres")]
343 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
344 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
345 }
346
347 #[cfg(feature = "mysql")]
348 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
349 row.get_opt(index)
350 .transpose()
351 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
352 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))
353 }
354 }
355
356 impl FromDatabaseValue for u64 {
357 #[cfg(feature = "turso")]
358 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
359 match value {
360 turso::Value::Integer(i) => Ok(i as u64),
361 _ => Err(WaeError::invalid_format("u64", format!("{:?}", value))),
362 }
363 }
364
365 #[cfg(feature = "postgres")]
366 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
367 let i: i64 =
368 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
369 Ok(i as u64)
370 }
371
372 #[cfg(feature = "mysql")]
373 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
374 let i: i64 = row
375 .get_opt(index)
376 .transpose()
377 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
378 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))?;
379 Ok(i as u64)
380 }
381 }
382
383 impl FromDatabaseValue for u32 {
384 #[cfg(feature = "turso")]
385 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
386 match value {
387 turso::Value::Integer(i) => Ok(i as u32),
388 _ => Err(WaeError::invalid_format("u32", format!("{:?}", value))),
389 }
390 }
391
392 #[cfg(feature = "postgres")]
393 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
394 let i: i32 =
395 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
396 Ok(i as u32)
397 }
398
399 #[cfg(feature = "mysql")]
400 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
401 let i: i32 = row
402 .get_opt(index)
403 .transpose()
404 .map_err(|e| WaeError::internal(format!("Failed to get column {}: {:?}", index, e)))?
405 .ok_or_else(|| WaeError::internal(format!("Column {} is NULL", index)))?;
406 Ok(i as u32)
407 }
408 }
409
410 impl FromDatabaseValue for Option<i64> {
411 #[cfg(feature = "turso")]
412 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
413 match value {
414 turso::Value::Null => Ok(None),
415 v => i64::from_turso_value(v).map(Some),
416 }
417 }
418
419 #[cfg(feature = "postgres")]
420 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
421 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
422 }
423
424 #[cfg(feature = "mysql")]
425 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
426 match row.get_opt::<Option<i64>, usize>(index) {
427 Some(Ok(val)) => Ok(val),
428 Some(Err(_)) => Ok(None),
429 None => Ok(None),
430 }
431 }
432 }
433
434 impl FromDatabaseValue for Option<i32> {
435 #[cfg(feature = "turso")]
436 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
437 match value {
438 turso::Value::Null => Ok(None),
439 v => i32::from_turso_value(v).map(Some),
440 }
441 }
442
443 #[cfg(feature = "postgres")]
444 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
445 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
446 }
447
448 #[cfg(feature = "mysql")]
449 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
450 match row.get_opt::<Option<i32>, usize>(index) {
451 Some(Ok(val)) => Ok(val),
452 Some(Err(_)) => Ok(None),
453 None => Ok(None),
454 }
455 }
456 }
457
458 impl FromDatabaseValue for Option<i16> {
459 #[cfg(feature = "turso")]
460 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
461 match value {
462 turso::Value::Null => Ok(None),
463 v => i16::from_turso_value(v).map(Some),
464 }
465 }
466
467 #[cfg(feature = "postgres")]
468 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
469 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
470 }
471
472 #[cfg(feature = "mysql")]
473 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
474 match row.get_opt::<Option<i16>, usize>(index) {
475 Some(Ok(val)) => Ok(val),
476 Some(Err(_)) => Ok(None),
477 None => Ok(None),
478 }
479 }
480 }
481
482 impl FromDatabaseValue for Option<u64> {
483 #[cfg(feature = "turso")]
484 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
485 match value {
486 turso::Value::Null => Ok(None),
487 v => u64::from_turso_value(v).map(Some),
488 }
489 }
490
491 #[cfg(feature = "postgres")]
492 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
493 let opt: Option<i64> =
494 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
495 Ok(opt.map(|i| i as u64))
496 }
497
498 #[cfg(feature = "mysql")]
499 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
500 match row.get_opt::<Option<i64>, usize>(index) {
501 Some(Ok(val)) => Ok(val.map(|i| i as u64)),
502 Some(Err(_)) => Ok(None),
503 None => Ok(None),
504 }
505 }
506 }
507
508 impl FromDatabaseValue for Option<u32> {
509 #[cfg(feature = "turso")]
510 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
511 match value {
512 turso::Value::Null => Ok(None),
513 v => u32::from_turso_value(v).map(Some),
514 }
515 }
516
517 #[cfg(feature = "postgres")]
518 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
519 let opt: Option<i32> =
520 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))?;
521 Ok(opt.map(|i| i as u32))
522 }
523
524 #[cfg(feature = "mysql")]
525 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
526 match row.get_opt::<Option<i32>, usize>(index) {
527 Some(Ok(val)) => Ok(val.map(|i| i as u32)),
528 Some(Err(_)) => Ok(None),
529 None => Ok(None),
530 }
531 }
532 }
533
534 impl FromDatabaseValue for Option<f64> {
535 #[cfg(feature = "turso")]
536 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
537 match value {
538 turso::Value::Null => Ok(None),
539 v => f64::from_turso_value(v).map(Some),
540 }
541 }
542
543 #[cfg(feature = "postgres")]
544 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
545 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
546 }
547
548 #[cfg(feature = "mysql")]
549 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
550 match row.get_opt::<Option<f64>, usize>(index) {
551 Some(Ok(val)) => Ok(val),
552 Some(Err(_)) => Ok(None),
553 None => Ok(None),
554 }
555 }
556 }
557
558 impl FromDatabaseValue for Option<String> {
559 #[cfg(feature = "turso")]
560 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
561 match value {
562 turso::Value::Null => Ok(None),
563 v => String::from_turso_value(v).map(Some),
564 }
565 }
566
567 #[cfg(feature = "postgres")]
568 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
569 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
570 }
571
572 #[cfg(feature = "mysql")]
573 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
574 match row.get_opt::<Option<String>, usize>(index) {
575 Some(Ok(val)) => Ok(val),
576 Some(Err(_)) => Ok(None),
577 None => Ok(None),
578 }
579 }
580 }
581
582 impl FromDatabaseValue for Option<Vec<u8>> {
583 #[cfg(feature = "turso")]
584 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
585 match value {
586 turso::Value::Null => Ok(None),
587 v => Vec::<u8>::from_turso_value(v).map(Some),
588 }
589 }
590
591 #[cfg(feature = "postgres")]
592 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
593 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
594 }
595
596 #[cfg(feature = "mysql")]
597 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
598 match row.get_opt::<Option<Vec<u8>>, usize>(index) {
599 Some(Ok(val)) => Ok(val),
600 Some(Err(_)) => Ok(None),
601 None => Ok(None),
602 }
603 }
604 }
605
606 impl FromDatabaseValue for Option<bool> {
607 #[cfg(feature = "turso")]
608 fn from_turso_value(value: turso::Value) -> DatabaseResult<Self> {
609 match value {
610 turso::Value::Null => Ok(None),
611 v => bool::from_turso_value(v).map(Some),
612 }
613 }
614
615 #[cfg(feature = "postgres")]
616 fn from_postgres_row(row: &tokio_postgres::Row, index: usize) -> DatabaseResult<Self> {
617 row.try_get(index).map_err(|e| WaeError::internal(format!("Failed to get column {}: {}", index, e)))
618 }
619
620 #[cfg(feature = "mysql")]
621 fn from_mysql_row(row: &mysql_async::Row, index: usize) -> DatabaseResult<Self> {
622 match row.get_opt::<Option<bool>, usize>(index) {
623 Some(Ok(val)) => Ok(val),
624 Some(Err(_)) => Ok(None),
625 None => Ok(None),
626 }
627 }
628 }
629}