mybatis_core/mssql/
sqlx_value.rs

1use rbson::{bson, Bson};
2use sqlx_core::column::Column;
3use sqlx_core::decode::Decode;
4use sqlx_core::error::BoxDynError;
5use sqlx_core::mssql::{Mssql, MssqlRow, MssqlValue, MssqlValueRef};
6use sqlx_core::row::Row;
7use sqlx_core::type_info::TypeInfo;
8use sqlx_core::types::BigDecimal;
9use sqlx_core::value::ValueRef;
10
11use crate::convert::{JsonCodec, RefJsonCodec, ResultCodec};
12
13use crate::db::db_adapter::DataDecoder;
14use crate::to_bson_macro;
15use crate::types::Decimal;
16
17impl<'r> JsonCodec for sqlx_core::mssql::MssqlValueRef<'r> {
18    fn try_to_bson(self) -> crate::Result<Bson> {
19        //TODO batter way to match type replace use string match
20        match self.type_info().name() {
21            "NULL" => {
22                return Ok(Bson::Null);
23            }
24            "TINYINT" => {
25                let r: Option<i8> = Decode::<'_, Mssql>::decode(self)?;
26                if let Some(r) = r {
27                    return Ok(bson!(r as i32));
28                }
29                return Ok(Bson::Null);
30            }
31            "SMALLINT" => {
32                let r: Option<i16> = Decode::<'_, Mssql>::decode(self)?;
33                if let Some(r) = r {
34                    return Ok(bson!(r as i32));
35                }
36                return Ok(Bson::Null);
37            }
38            "INT" => {
39                let r: Option<i32> = Decode::<'_, Mssql>::decode(self)?;
40                return Ok(to_bson_macro!(r));
41            }
42            "BIGINT" => {
43                let r: Option<i64> = Decode::<'_, Mssql>::decode(self)?;
44                return Ok(to_bson_macro!(r));
45            }
46            "REAL" => {
47                let r: Option<f32> = Decode::<'_, Mssql>::decode(self)?;
48                return Ok(to_bson_macro!(r));
49            }
50            "FLOAT" => {
51                let r: Option<f64> = Decode::<'_, Mssql>::decode(self)?;
52                return Ok(to_bson_macro!(r));
53            }
54
55            "VARCHAR" | "NVARCHAR" | "BIGVARCHAR" | "CHAR" | "BIGCHAR" | "NCHAR" => {
56                let r: Option<String> = Decode::<'_, Mssql>::decode(self)?;
57                return Ok(to_bson_macro!(r));
58            }
59
60            "NEWDECIMAL" => {
61                let r: Option<String> = Decode::<'_, Mssql>::decode(self)?;
62                return Ok(to_bson_macro!(r));
63            }
64
65            //TODO "DATE" | "TIME" | "DATETIME" | "TIMESTAMP" => {}
66            // you can use types package to save date to string
67            _ => {
68                return Err(crate::Error::from(format!(
69                    "un support database type for:{:?}!",
70                    self.type_info().name()
71                )));
72            }
73        }
74    }
75}
76
77impl RefJsonCodec for Vec<MssqlRow> {
78    fn try_to_bson(&self, decoder: &dyn DataDecoder) -> crate::Result<Bson> {
79        let mut arr = Vec::with_capacity(self.len());
80        for row in self {
81            let mut m = rbson::Document::new();
82            let columns = row.columns();
83            for x in columns {
84                let key = x.name();
85                let v: MssqlValueRef = row.try_get_raw(key)?;
86                let mut bson = v.try_to_bson()?;
87                decoder.decode(key, &mut bson)?;
88                m.insert(key.to_owned(), bson);
89            }
90            arr.push(Bson::Document(m));
91        }
92        Ok(Bson::from(arr))
93    }
94}