From ddd994278bea8e1209cd42b15c7cdb14d01f0269 Mon Sep 17 00:00:00 2001 From: Marco Napetti Date: Wed, 25 Aug 2021 19:57:32 +0200 Subject: [PATCH 1/5] Introduce Nullable trait to permit custom Option --- src/value.rs | 40 ++++++++++++++++++++++------------------ 1 file changed, 22 insertions(+), 18 deletions(-) diff --git a/src/value.rs b/src/value.rs index 65da098f3..0424a6918 100644 --- a/src/value.rs +++ b/src/value.rs @@ -96,6 +96,10 @@ pub trait IntoValueTuple { fn into_value_tuple(self) -> ValueTuple; } +pub trait Nullable { + fn null() -> Value; +} + impl Value { pub fn unwrap(self) -> T where @@ -113,9 +117,9 @@ macro_rules! type_to_value { } } - impl From> for Value { - fn from(x: Option<$type>) -> Value { - Value::$name(x) + impl Nullable for $type { + fn null() -> Value { + Value::$name(None) } } @@ -170,12 +174,9 @@ macro_rules! type_to_box_value { } } - impl From> for Value { - fn from(x: Option<$type>) -> Value { - match x { - Some(v) => Value::$name(Some(Box::new(v))), - None => Value::$name(None), - } + impl Nullable for $type { + fn null() -> Value { + Value::$name(None) } } @@ -249,6 +250,15 @@ impl<'a> From<&'a str> for Value { } } +impl + Nullable> From> for Value { + fn from(x: Option) -> Value { + match x { + Some(v) => v.into(), + None => T::null(), + } + } +} + type_to_box_value!(Vec, Bytes); impl_value_type_default!(Vec); type_to_box_value!(String, String); @@ -313,15 +323,9 @@ mod with_chrono { } } - impl From>> for Value - where - Tz: TimeZone, - { - fn from(x: Option>) -> Value { - match x { - Some(v) => From::>::from(v), - None => Value::DateTimeWithTimeZone(None), - } + impl Nullable for DateTime { + fn null() -> Value { + Value::DateTimeWithTimeZone(None) } } From d75965aa47ce3beb84263372e83f9f73c8e57b59 Mon Sep 17 00:00:00 2001 From: Marco Napetti Date: Thu, 26 Aug 2021 09:42:44 +0200 Subject: [PATCH 2/5] Add nullability for &str --- src/value.rs | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/value.rs b/src/value.rs index 0424a6918..1f849caff 100644 --- a/src/value.rs +++ b/src/value.rs @@ -250,6 +250,12 @@ impl<'a> From<&'a str> for Value { } } +impl<'a> Nullable for &'a str { + fn null() -> Value { + Value::String(None) + } +} + impl + Nullable> From> for Value { fn from(x: Option) -> Value { match x { From c5b4bdde3838abf0f7b3a3855234a5faf5c70611 Mon Sep 17 00:00:00 2001 From: Marco Napetti Date: Thu, 26 Aug 2021 13:57:38 +0200 Subject: [PATCH 3/5] Remove last direct Option implementations --- src/value.rs | 80 +++++++++++++++------------------------------------- 1 file changed, 22 insertions(+), 58 deletions(-) diff --git a/src/value.rs b/src/value.rs index 1f849caff..208553e34 100644 --- a/src/value.rs +++ b/src/value.rs @@ -144,25 +144,6 @@ macro_rules! type_to_value { Default::default() } } - - impl ValueType for Option<$type> { - fn unwrap(v: Value) -> Self { - match v { - Value::$name(x) => x, - _ => panic!("type error"), - } - } - - fn type_name() -> &'static str { - concat!("Option<", stringify!($type), ">") - } - } - - impl ValueTypeDefault for Option<$type> { - fn default() -> Self { - Default::default() - } - } }; } @@ -192,26 +173,6 @@ macro_rules! type_to_box_value { stringify!($type) } } - - impl ValueType for Option<$type> { - fn unwrap(v: Value) -> Self { - match v { - Value::$name(Some(x)) => Some(*x), - Value::$name(None) => None, - _ => panic!("type error"), - } - } - - fn type_name() -> &'static str { - concat!("Option<", stringify!($type), ">") - } - } - - impl ValueTypeDefault for Option<$type> { - fn default() -> Self { - Default::default() - } - } }; } @@ -265,6 +226,28 @@ impl + Nullable> From> for Value { } } +impl ValueType for Option { + fn unwrap(v: Value) -> Self { + if v == T::null() { + None + } + else { + Some(v.unwrap()) + } + } + + fn type_name() -> &'static str { + //concat!("Option<", T::type_name(), ">") + T::type_name() + } +} + +impl ValueTypeDefault for Option { + fn default() -> Self { + Default::default() + } +} + type_to_box_value!(Vec, Bytes); impl_value_type_default!(Vec); type_to_box_value!(String, String); @@ -313,12 +296,6 @@ mod with_chrono { } } - impl ValueTypeDefault for Option> { - fn default() -> Self { - Default::default() - } - } - impl From> for Value where Tz: TimeZone, @@ -347,19 +324,6 @@ mod with_chrono { stringify!(DateTime) } } - - impl ValueType for Option> { - fn unwrap(v: Value) -> Self { - match v { - Value::DateTimeWithTimeZone(Some(x)) => Some(*x), - _ => panic!("type error"), - } - } - - fn type_name() -> &'static str { - stringify!(Option>) - } - } } #[cfg(feature = "with-rust_decimal")] From 17129dc9a3b24e4f90ab9ab3c37d76aec29b4923 Mon Sep 17 00:00:00 2001 From: Marco Napetti Date: Thu, 26 Aug 2021 17:42:11 +0200 Subject: [PATCH 4/5] Expand generics --- src/value.rs | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/value.rs b/src/value.rs index 208553e34..631d4b93e 100644 --- a/src/value.rs +++ b/src/value.rs @@ -217,7 +217,8 @@ impl<'a> Nullable for &'a str { } } -impl + Nullable> From> for Value { +impl From> for Value +where T: Into + Nullable { fn from(x: Option) -> Value { match x { Some(v) => v.into(), @@ -226,7 +227,8 @@ impl + Nullable> From> for Value { } } -impl ValueType for Option { +impl ValueType for Option +where T: ValueType + Nullable { fn unwrap(v: Value) -> Self { if v == T::null() { None @@ -242,7 +244,8 @@ impl ValueType for Option { } } -impl ValueTypeDefault for Option { +impl ValueTypeDefault for Option +where T: ValueType + Nullable { fn default() -> Self { Default::default() } From fabae549bf44d8a7bcd528645d00d8fc38a4cfda Mon Sep 17 00:00:00 2001 From: Billy Chan Date: Fri, 27 Aug 2021 14:54:10 +0800 Subject: [PATCH 5/5] Use bigdecimal version "^0.2" --- Cargo.toml | 2 +- examples/sqlx_mysql/Cargo.toml | 2 +- examples/sqlx_postgres/Cargo.toml | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index e8048f611..f7a0b7998 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -42,7 +42,7 @@ bytes = { version = "^1", optional = true } chrono = { version = "^0", optional = true } postgres-types = { version = "^0", optional = true } rust_decimal = { version = "^1", optional = true } -bigdecimal = { version = "^0", optional = true } +bigdecimal = { version = "^0.2", optional = true } uuid = { version = "^0", optional = true } thiserror = { version = "^1" } diff --git a/examples/sqlx_mysql/Cargo.toml b/examples/sqlx_mysql/Cargo.toml index 7bbf036b3..f0e2d845d 100644 --- a/examples/sqlx_mysql/Cargo.toml +++ b/examples/sqlx_mysql/Cargo.toml @@ -8,7 +8,7 @@ chrono = "^0" uuid = { version = "^0", features = ["serde", "v4"] } serde_json = "^1" rust_decimal = { version = "^1" } -bigdecimal = { version = "^0" } +bigdecimal = { version = "^0.2" } async-std = { version = "1.8", features = [ "attributes" ] } sea-query = { path = "../../", features = [ "sqlx-mysql", diff --git a/examples/sqlx_postgres/Cargo.toml b/examples/sqlx_postgres/Cargo.toml index bc7355d86..1aaa981ff 100644 --- a/examples/sqlx_postgres/Cargo.toml +++ b/examples/sqlx_postgres/Cargo.toml @@ -8,7 +8,7 @@ chrono = "^0" uuid = { version = "^0", features = ["serde", "v4"] } serde_json = "^1" rust_decimal = { version = "^1" } -bigdecimal = { version = "^0" } +bigdecimal = { version = "^0.2" } async-std = { version = "1.8", features = [ "attributes" ] } sea-query = { path = "../../", features = [ "sqlx-postgres",