1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138
use std::{fmt, rc}; use std::marker; use serde_json; use chrono; use uuid; use super::from; use super::sql; use super::expression; pub trait Field { fn name(&self) -> &str; fn table_name(&self) -> &str; fn qual(&self) -> Option<&String>; fn upcast_field(&self) -> SharedField; } impl fmt::Debug for Field { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { write!(f, "Field: {}", self.name()) } } pub type BoxedField = Box<Field + 'static>; pub type SharedField = rc::Rc<BoxedField>; #[derive(Clone, Debug)] pub struct NamedField<T> { pub name: String, pub table_name: String, pub qual: Option<String>, _marker: marker::PhantomData<T>, } impl<T: Clone> NamedField<T> { pub fn new(name: &str, table_name: &str) -> NamedField<T> { NamedField { name: name.to_string(), table_name: table_name.to_string(), qual: None, _marker: marker::PhantomData, } } pub fn new_qual(name: &str, table_name: &str, qual: &str) -> NamedField<T> { NamedField { name: name.to_string(), table_name: table_name.to_string(), qual: Some(qual.to_string()), _marker: marker::PhantomData, } } pub fn field_of(name: &str, table: &from::Table) -> NamedField<T> { NamedField { name: name.to_string(), table_name: table.get_table_name().to_string(), qual: table.get_table_alias().as_ref().map(|v| v.to_string()), _marker: marker::PhantomData, } } pub fn qual(&self) -> NamedField<T> { let mut field = self.clone(); field.qual = Some(self.table_name.to_string()); field } pub fn qual_with(&self, qual: &str) -> NamedField<T> { let mut field = self.clone(); field.qual = Some(qual.to_string()); field } pub fn qual_for(&self, table: &from::Table) -> NamedField<T> { let mut field = self.clone(); field.qual = table.get_table_alias().as_ref().map(|v| v.to_string()); field } } impl<T: Clone + 'static + fmt::Debug> expression::UntypedExpression for NamedField<T> { fn expression_as_sql(&self) -> &sql::ToSql { self } fn upcast_expression(&self) -> expression::SharedExpression { rc::Rc::new(Box::new(self.clone()) as expression::BoxedExpression) } } impl<T: Clone + 'static> Field for NamedField<T> { fn name(&self) -> &str { &self.name } fn table_name(&self) -> &str { &self.table_name } fn qual(&self) -> Option<&String> { self.qual.as_ref() } fn upcast_field(&self) -> SharedField { rc::Rc::new(Box::new(self.clone())) } } pub type BoolField = NamedField<bool>; pub type I8Field = NamedField<i8>; pub type I16Field = NamedField<i16>; pub type I32Field = NamedField<i32>; pub type I64Field = NamedField<i64>; pub type F32Field = NamedField<f32>; pub type F64Field = NamedField<f64>; pub type StringField = NamedField<String>; pub type ByteListField = NamedField<Vec<u8>>; pub type JsonField = NamedField<serde_json::Value>; pub type TimespecField = NamedField<chrono::NaiveDateTime>; pub type UuidField = NamedField<uuid::Uuid>; pub type OptionalBoolField = NamedField<Option<bool>>; pub type OptionalI8Field = NamedField<Option<i8>>; pub type OptionalI16Field = NamedField<Option<i16>>; pub type OptionalI32Field = NamedField<Option<i32>>; pub type OptionalI64Field = NamedField<Option<i64>>; pub type OptionalF32Field = NamedField<Option<f32>>; pub type OptionalF64Field = NamedField<Option<f64>>; pub type OptionalStringField = NamedField<Option<String>>; pub type OptionalByteListField = NamedField<Option<Vec<u8>>>; pub type OptionalJsonField = NamedField<Option<serde_json::Value>>; pub type OptionalTimespecField = NamedField<Option<chrono::NaiveDateTime>>; pub type OptionalUuidField = NamedField<Option<uuid::Uuid>>;