1 use std::error::Error; 2 use std::io::Write; 3 4 use backend::Backend; 5 use deserialize::{self, FromSql, FromSqlRow, Queryable}; 6 use serialize::{self, IsNull, Output, ToSql}; 7 use sql_types::{self, BigInt, Binary, Bool, Double, Float, Integer, NotNull, SmallInt, Text}; 8 9 #[allow(dead_code)] 10 mod foreign_impls { 11 use super::*; 12 13 #[derive(FromSqlRow, AsExpression)] 14 #[diesel(foreign_derive)] 15 #[sql_type = "Bool"] 16 struct BoolProxy(bool); 17 18 #[derive(FromSqlRow, AsExpression)] 19 #[diesel(foreign_derive)] 20 #[cfg_attr(feature = "mysql", sql_type = "::sql_types::TinyInt")] 21 struct I8Proxy(i8); 22 23 #[derive(FromSqlRow, AsExpression)] 24 #[diesel(foreign_derive)] 25 #[sql_type = "SmallInt"] 26 struct I16Proxy(i16); 27 28 #[derive(FromSqlRow, AsExpression)] 29 #[diesel(foreign_derive)] 30 #[sql_type = "Integer"] 31 struct I32Proxy(i32); 32 33 #[derive(FromSqlRow, AsExpression)] 34 #[diesel(foreign_derive)] 35 #[sql_type = "BigInt"] 36 struct I64Proxy(i64); 37 38 #[derive(FromSqlRow, AsExpression)] 39 #[diesel(foreign_derive)] 40 #[cfg_attr( 41 feature = "mysql", 42 sql_type = "::sql_types::Unsigned<::sql_types::TinyInt>" 43 )] 44 struct U8Proxy(u8); 45 46 #[derive(FromSqlRow, AsExpression)] 47 #[diesel(foreign_derive)] 48 #[cfg_attr(feature = "mysql", sql_type = "::sql_types::Unsigned<SmallInt>")] 49 struct U16Proxy(u16); 50 51 #[derive(FromSqlRow, AsExpression)] 52 #[diesel(foreign_derive)] 53 #[cfg_attr(feature = "mysql", sql_type = "::sql_types::Unsigned<Integer>")] 54 #[cfg_attr(feature = "postgres", sql_type = "::sql_types::Oid")] 55 struct U32Proxy(u32); 56 57 #[derive(FromSqlRow, AsExpression)] 58 #[diesel(foreign_derive)] 59 #[cfg_attr(feature = "mysql", sql_type = "::sql_types::Unsigned<BigInt>")] 60 struct U64Proxy(u64); 61 62 #[derive(FromSqlRow, AsExpression)] 63 #[diesel(foreign_derive)] 64 #[sql_type = "Float"] 65 struct F32Proxy(f32); 66 67 #[derive(FromSqlRow, AsExpression)] 68 #[diesel(foreign_derive)] 69 #[sql_type = "Double"] 70 struct F64Proxy(f64); 71 72 #[derive(FromSqlRow, AsExpression)] 73 #[diesel(foreign_derive)] 74 #[sql_type = "Text"] 75 #[cfg_attr(feature = "sqlite", sql_type = "::sql_types::Date")] 76 #[cfg_attr(feature = "sqlite", sql_type = "::sql_types::Time")] 77 #[cfg_attr(feature = "sqlite", sql_type = "::sql_types::Timestamp")] 78 struct StringProxy(String); 79 80 #[derive(AsExpression)] 81 #[diesel(foreign_derive, not_sized)] 82 #[sql_type = "Text"] 83 #[cfg_attr(feature = "sqlite", sql_type = "::sql_types::Date")] 84 #[cfg_attr(feature = "sqlite", sql_type = "::sql_types::Time")] 85 #[cfg_attr(feature = "sqlite", sql_type = "::sql_types::Timestamp")] 86 struct StrProxy(str); 87 88 #[derive(FromSqlRow)] 89 #[diesel(foreign_derive)] 90 struct VecProxy<T>(Vec<T>); 91 92 #[derive(AsExpression)] 93 #[diesel(foreign_derive)] 94 #[sql_type = "Binary"] 95 struct BinaryVecProxy(Vec<u8>); 96 97 #[derive(AsExpression)] 98 #[diesel(foreign_derive, not_sized)] 99 #[sql_type = "Binary"] 100 struct BinarySliceProxy([u8]); 101 } 102 103 impl NotNull for () {} 104 105 impl<ST, DB> FromSql<ST, DB> for String 106 where 107 DB: Backend, 108 *const str: FromSql<ST, DB>, 109 { from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self>110 fn from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self> { 111 let str_ptr = <*const str as FromSql<ST, DB>>::from_sql(bytes)?; 112 // We know that the pointer impl will never return null 113 let string = unsafe { &*str_ptr }; 114 Ok(string.to_owned()) 115 } 116 } 117 118 /// The returned pointer is *only* valid for the lifetime to the argument of 119 /// `from_sql`. This impl is intended for uses where you want to write a new 120 /// impl in terms of `String`, but don't want to allocate. We have to return a 121 /// raw pointer instead of a reference with a lifetime due to the structure of 122 /// `FromSql` 123 impl<DB: Backend<RawValue = [u8]>> FromSql<sql_types::Text, DB> for *const str { from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self>124 fn from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self> { 125 use std::str; 126 let string = str::from_utf8(not_none!(bytes))?; 127 Ok(string as *const _) 128 } 129 } 130 131 impl<DB: Backend> ToSql<sql_types::Text, DB> for str { to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result132 fn to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result { 133 out.write_all(self.as_bytes()) 134 .map(|_| IsNull::No) 135 .map_err(|e| Box::new(e) as Box<dyn Error + Send + Sync>) 136 } 137 } 138 139 impl<DB> ToSql<sql_types::Text, DB> for String 140 where 141 DB: Backend, 142 str: ToSql<sql_types::Text, DB>, 143 { to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result144 fn to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result { 145 (self as &str).to_sql(out) 146 } 147 } 148 149 impl<ST, DB> FromSql<ST, DB> for Vec<u8> 150 where 151 DB: Backend, 152 *const [u8]: FromSql<ST, DB>, 153 { from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self>154 fn from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self> { 155 let slice_ptr = <*const [u8] as FromSql<ST, DB>>::from_sql(bytes)?; 156 // We know that the pointer impl will never return null 157 let bytes = unsafe { &*slice_ptr }; 158 Ok(bytes.to_owned()) 159 } 160 } 161 162 /// The returned pointer is *only* valid for the lifetime to the argument of 163 /// `from_sql`. This impl is intended for uses where you want to write a new 164 /// impl in terms of `Vec<u8>`, but don't want to allocate. We have to return a 165 /// raw pointer instead of a reference with a lifetime due to the structure of 166 /// `FromSql` 167 impl<DB: Backend<RawValue = [u8]>> FromSql<sql_types::Binary, DB> for *const [u8] { from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self>168 fn from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self> { 169 Ok(not_none!(bytes) as *const _) 170 } 171 } 172 173 impl<DB> ToSql<sql_types::Binary, DB> for Vec<u8> 174 where 175 DB: Backend, 176 [u8]: ToSql<sql_types::Binary, DB>, 177 { to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result178 fn to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result { 179 (self as &[u8]).to_sql(out) 180 } 181 } 182 183 impl<DB: Backend> ToSql<sql_types::Binary, DB> for [u8] { to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result184 fn to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result { 185 out.write_all(self) 186 .map(|_| IsNull::No) 187 .map_err(|e| Box::new(e) as Box<dyn Error + Send + Sync>) 188 } 189 } 190 191 use std::borrow::{Cow, ToOwned}; 192 use std::fmt; 193 impl<'a, T: ?Sized, ST, DB> ToSql<ST, DB> for Cow<'a, T> 194 where 195 T: 'a + ToOwned + ToSql<ST, DB>, 196 DB: Backend, 197 Self: fmt::Debug, 198 { to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result199 fn to_sql<W: Write>(&self, out: &mut Output<W, DB>) -> serialize::Result { 200 ToSql::<ST, DB>::to_sql(&**self, out) 201 } 202 } 203 204 impl<'a, T: ?Sized, ST, DB> FromSql<ST, DB> for Cow<'a, T> 205 where 206 T: 'a + ToOwned, 207 DB: Backend, 208 T::Owned: FromSql<ST, DB>, 209 { from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self>210 fn from_sql(bytes: Option<&DB::RawValue>) -> deserialize::Result<Self> { 211 T::Owned::from_sql(bytes).map(Cow::Owned) 212 } 213 } 214 215 impl<'a, T: ?Sized, ST, DB> FromSqlRow<ST, DB> for Cow<'a, T> 216 where 217 T: 'a + ToOwned, 218 DB: Backend, 219 Cow<'a, T>: FromSql<ST, DB>, 220 { build_from_row<R: ::row::Row<DB>>(row: &mut R) -> deserialize::Result<Self>221 fn build_from_row<R: ::row::Row<DB>>(row: &mut R) -> deserialize::Result<Self> { 222 FromSql::<ST, DB>::from_sql(row.take()) 223 } 224 } 225 226 impl<'a, T: ?Sized, ST, DB> Queryable<ST, DB> for Cow<'a, T> 227 where 228 T: 'a + ToOwned, 229 DB: Backend, 230 Self: FromSqlRow<ST, DB>, 231 { 232 type Row = Self; 233 build(row: Self::Row) -> Self234 fn build(row: Self::Row) -> Self { 235 row 236 } 237 } 238 239 use expression::bound::Bound; 240 use expression::{AsExpression, Expression}; 241 242 impl<'a, T: ?Sized, ST> AsExpression<ST> for Cow<'a, T> 243 where 244 T: 'a + ToOwned, 245 Bound<ST, Cow<'a, T>>: Expression<SqlType = ST>, 246 { 247 type Expression = Bound<ST, Self>; 248 as_expression(self) -> Self::Expression249 fn as_expression(self) -> Self::Expression { 250 Bound::new(self) 251 } 252 } 253 254 impl<'a, 'b, T: ?Sized, ST> AsExpression<ST> for &'b Cow<'a, T> 255 where 256 T: 'a + ToOwned, 257 Bound<ST, &'b T>: Expression<SqlType = ST>, 258 { 259 type Expression = Bound<ST, &'b T>; 260 as_expression(self) -> Self::Expression261 fn as_expression(self) -> Self::Expression { 262 Bound::new(&**self) 263 } 264 } 265