diff --git a/sqlx-mysql/src/types/inet.rs b/sqlx-mysql/src/types/inet.rs new file mode 100644 index 0000000000..385ca4a61a --- /dev/null +++ b/sqlx-mysql/src/types/inet.rs @@ -0,0 +1,92 @@ +use std::net::{IpAddr, Ipv4Addr, Ipv6Addr}; + +use crate::decode::Decode; +use crate::encode::{Encode, IsNull}; +use crate::error::BoxDynError; +use crate::io::MySqlBufMutExt; +use crate::types::Type; +use crate::{MySql, MySqlTypeInfo, MySqlValueRef}; + +impl Type for Ipv4Addr { + fn type_info() -> MySqlTypeInfo { + <&str as Type>::type_info() + } + + fn compatible(ty: &MySqlTypeInfo) -> bool { + <&str as Type>::compatible(ty) + } +} + +impl Encode<'_, MySql> for Ipv4Addr { + fn encode_by_ref(&self, buf: &mut Vec) -> IsNull { + buf.put_str_lenenc(&self.to_string()); + + IsNull::No + } +} + +impl Decode<'_, MySql> for Ipv4Addr { + fn decode(value: MySqlValueRef<'_>) -> Result { + // delegate to the &str type to decode from MySQL + let text = <&str as Decode>::decode(value)?; + + // parse a Ipv4Addr from the text + text.parse().map_err(Into::into) + } +} + +impl Type for Ipv6Addr { + fn type_info() -> MySqlTypeInfo { + <&str as Type>::type_info() + } + + fn compatible(ty: &MySqlTypeInfo) -> bool { + <&str as Type>::compatible(ty) + } +} + +impl Encode<'_, MySql> for Ipv6Addr { + fn encode_by_ref(&self, buf: &mut Vec) -> IsNull { + buf.put_str_lenenc(&self.to_string()); + + IsNull::No + } +} + +impl Decode<'_, MySql> for Ipv6Addr { + fn decode(value: MySqlValueRef<'_>) -> Result { + // delegate to the &str type to decode from MySQL + let text = <&str as Decode>::decode(value)?; + + // parse a Ipv6Addr from the text + text.parse().map_err(Into::into) + } +} + +impl Type for IpAddr { + fn type_info() -> MySqlTypeInfo { + <&str as Type>::type_info() + } + + fn compatible(ty: &MySqlTypeInfo) -> bool { + <&str as Type>::compatible(ty) + } +} + +impl Encode<'_, MySql> for IpAddr { + fn encode_by_ref(&self, buf: &mut Vec) -> IsNull { + buf.put_str_lenenc(&self.to_string()); + + IsNull::No + } +} + +impl Decode<'_, MySql> for IpAddr { + fn decode(value: MySqlValueRef<'_>) -> Result { + // delegate to the &str type to decode from MySQL + let text = <&str as Decode>::decode(value)?; + + // parse a IpAddr from the text + text.parse().map_err(Into::into) + } +} diff --git a/sqlx-mysql/src/types/mod.rs b/sqlx-mysql/src/types/mod.rs index 6cbbde7166..be35111401 100644 --- a/sqlx-mysql/src/types/mod.rs +++ b/sqlx-mysql/src/types/mod.rs @@ -17,6 +17,7 @@ //! | `f64` | DOUBLE | //! | `&str`, [`String`] | VARCHAR, CHAR, TEXT | //! | `&[u8]`, `Vec` | VARBINARY, BINARY, BLOB | +//! | `IpAddr`, `Ipv4Addr`, `Ipv6Addr` | VARCHAR, TEXT | //! //! ##### Note: `BOOLEAN`/`BOOL` Type //! MySQL and MariaDB treat `BOOLEAN` as an alias of the `TINYINT` type: @@ -102,6 +103,7 @@ pub(crate) use sqlx_core::types::*; mod bool; mod bytes; mod float; +mod inet; mod int; mod str; mod text;