mod error;
pub use error::{Error, ErrorKind, ValidateError};
pub use afastdata_macro::*;
#[cfg(feature = "len-u64")]
pub type LenInt = u64;
#[cfg(not(feature = "len-u64"))]
pub type LenInt = u32;
pub const LEN_INT_SIZE: usize = std::mem::size_of::<LenInt>();
pub trait AFastSerialize {
fn to_bytes(&self) -> Vec<u8>;
fn to_bytes_with(&self, _marker: &str) -> Vec<u8> {
self.to_bytes()
}
}
pub trait AFastDeserialize: Sized {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error>;
fn from_bytes_with(data: &[u8], _marker: &str) -> Result<(Self, usize), Error> {
Self::from_bytes(data)
}
}
fn read_exact(data: &[u8], offset: usize, n: usize) -> Result<&[u8], Error> {
if offset + n > data.len() {
Err(Error::deserialize(format!(
"Not enough bytes: need {} at offset {}, have {}",
n,
offset,
data.len()
)))
} else {
Ok(&data[offset..offset + n])
}
}
macro_rules! impl_serialize_int {
($t:ty, $size:expr) => {
impl AFastSerialize for $t {
fn to_bytes(&self) -> Vec<u8> {
self.to_le_bytes().to_vec()
}
}
impl AFastDeserialize for $t {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, $size)?;
let arr: [u8; $size] = bytes.try_into().unwrap();
Ok((Self::from_le_bytes(arr), $size))
}
}
};
}
impl_serialize_int!(i8, 1);
impl_serialize_int!(u8, 1);
impl_serialize_int!(i16, 2);
impl_serialize_int!(u16, 2);
impl_serialize_int!(i32, 4);
impl_serialize_int!(u32, 4);
impl_serialize_int!(i64, 8);
impl_serialize_int!(u64, 8);
impl_serialize_int!(i128, 16);
impl_serialize_int!(u128, 16);
impl_serialize_int!(f32, 4);
impl_serialize_int!(f64, 8);
impl AFastSerialize for usize {
fn to_bytes(&self) -> Vec<u8> {
(*self as u64).to_le_bytes().to_vec()
}
}
impl AFastDeserialize for usize {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 8)?;
let arr: [u8; 8] = bytes.try_into().unwrap();
Ok((u64::from_le_bytes(arr) as usize, 8))
}
}
impl AFastSerialize for bool {
fn to_bytes(&self) -> Vec<u8> {
vec![if *self { 1 } else { 0 }]
}
}
impl AFastDeserialize for bool {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 1)?;
match bytes[0] {
0 => Ok((false, 1)),
1 => Ok((true, 1)),
v => Err(Error::deserialize(format!("Invalid bool value: {}", v))),
}
}
}
fn write_len(buf: &mut Vec<u8>, len: usize) {
let v = len as LenInt;
buf.extend(v.to_le_bytes());
}
fn read_len(data: &[u8], offset: usize) -> Result<(usize, usize), Error> {
let bytes = read_exact(data, offset, LEN_INT_SIZE)?;
let arr: [u8; LEN_INT_SIZE] = bytes.try_into().unwrap();
let len = LenInt::from_le_bytes(arr) as usize;
Ok((len, offset + LEN_INT_SIZE))
}
impl AFastSerialize for String {
fn to_bytes(&self) -> Vec<u8> {
let bytes = self.as_bytes();
let mut result = Vec::with_capacity(LEN_INT_SIZE + bytes.len());
write_len(&mut result, bytes.len());
result.extend_from_slice(bytes);
result
}
}
impl AFastDeserialize for String {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, offset) = read_len(data, 0)?;
let bytes = read_exact(data, offset, len)?;
let s = std::str::from_utf8(bytes)
.map_err(|e| Error::deserialize(format!("Invalid UTF-8: {}", e)))?;
Ok((s.to_owned(), offset + len))
}
}
impl<T: AFastSerialize> AFastSerialize for Vec<T> {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE + self.len());
write_len(&mut result, self.len());
for item in self {
result.extend(item.to_bytes());
}
result
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE + self.len());
write_len(&mut result, self.len());
for item in self {
result.extend(item.to_bytes_with(marker));
}
result
}
}
impl<T: AFastDeserialize> AFastDeserialize for Vec<T> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut vec = Vec::with_capacity(len);
for _ in 0..len {
let (item, new_offset) = T::from_bytes(&data[offset..])?;
vec.push(item);
offset += new_offset;
}
Ok((vec, offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut vec = Vec::with_capacity(len);
for _ in 0..len {
let (item, new_offset) = T::from_bytes_with(&data[offset..], marker)?;
vec.push(item);
offset += new_offset;
}
Ok((vec, offset))
}
}
impl<T: AFastSerialize> AFastSerialize for Option<T> {
fn to_bytes(&self) -> Vec<u8> {
match self {
Some(val) => {
let mut result = vec![1u8];
result.extend(val.to_bytes());
result
}
None => vec![0u8],
}
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
match self {
Some(val) => {
let mut result = vec![1u8];
result.extend(val.to_bytes_with(marker));
result
}
None => vec![0u8],
}
}
}
impl<T: AFastDeserialize> AFastDeserialize for Option<T> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 1)?;
match bytes[0] {
0 => Ok((None, 1)),
1 => {
let (val, new_offset) = T::from_bytes(&data[1..])?;
Ok((Some(val), 1 + new_offset))
}
v => Err(Error::deserialize(format!("Invalid Option tag: {}", v))),
}
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 1)?;
match bytes[0] {
0 => Ok((None, 1)),
1 => {
let (val, new_offset) = T::from_bytes_with(&data[1..], marker)?;
Ok((Some(val), 1 + new_offset))
}
v => Err(Error::deserialize(format!("Invalid Option tag: {}", v))),
}
}
}
impl<T: AFastSerialize, const N: usize> AFastSerialize for [T; N] {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE + N);
for item in self {
result.extend(item.to_bytes());
}
result
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE + N);
for item in self {
result.extend(item.to_bytes_with(marker));
}
result
}
}
impl<T: AFastDeserialize + Default + Copy, const N: usize> AFastDeserialize for [T; N] {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let mut arr = [T::default(); N];
let mut offset = 0;
for item in arr.iter_mut() {
let (val, new_offset) = T::from_bytes(&data[offset..])?;
*item = val;
offset += new_offset;
}
Ok((arr, offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let mut arr = [T::default(); N];
let mut offset = 0;
for item in arr.iter_mut() {
let (val, new_offset) = T::from_bytes_with(&data[offset..], marker)?;
*item = val;
offset += new_offset;
}
Ok((arr, offset))
}
}
impl AFastSerialize for &str {
fn to_bytes(&self) -> Vec<u8> {
let bytes = self.as_bytes();
let len = bytes.len() as LenInt;
let mut result = len.to_le_bytes().to_vec();
result.extend_from_slice(bytes);
result
}
fn to_bytes_with(&self, _marker: &str) -> Vec<u8> {
self.to_bytes()
}
}
impl<K: AFastSerialize, V: AFastSerialize> AFastSerialize for std::collections::HashMap<K, V> {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for (k, v) in self {
result.extend(k.to_bytes());
result.extend(v.to_bytes());
}
result
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for (k, v) in self {
result.extend(k.to_bytes_with(marker));
result.extend(v.to_bytes_with(marker));
}
result
}
}
impl<K: AFastDeserialize + Eq + std::hash::Hash, V: AFastDeserialize> AFastDeserialize
for std::collections::HashMap<K, V>
{
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut map = std::collections::HashMap::with_capacity(len);
for _ in 0..len {
let (key, new_offset) = K::from_bytes(&data[offset..])?;
offset += new_offset;
let (val, new_offset) = V::from_bytes(&data[offset..])?;
offset += new_offset;
map.insert(key, val);
}
Ok((map, offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut map = std::collections::HashMap::with_capacity(len);
for _ in 0..len {
let (key, new_offset) = K::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
let (val, new_offset) = V::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
map.insert(key, val);
}
Ok((map, offset))
}
}
impl<T: AFastSerialize> AFastSerialize for std::collections::HashSet<T> {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for item in self {
result.extend(item.to_bytes());
}
result
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for item in self {
result.extend(item.to_bytes_with(marker));
}
result
}
}
impl<T: AFastDeserialize + Eq + std::hash::Hash> AFastDeserialize for std::collections::HashSet<T> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut set = std::collections::HashSet::with_capacity(len);
for _ in 0..len {
let (item, new_offset) = T::from_bytes(&data[offset..])?;
offset += new_offset;
set.insert(item);
}
Ok((set, offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut set = std::collections::HashSet::with_capacity(len);
for _ in 0..len {
let (item, new_offset) = T::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
set.insert(item);
}
Ok((set, offset))
}
}
impl<K: AFastSerialize, V: AFastSerialize> AFastSerialize for std::collections::BTreeMap<K, V> {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for (k, v) in self {
result.extend(k.to_bytes());
result.extend(v.to_bytes());
}
result
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for (k, v) in self {
result.extend(k.to_bytes_with(marker));
result.extend(v.to_bytes_with(marker));
}
result
}
}
impl<K: AFastDeserialize + Ord, V: AFastDeserialize> AFastDeserialize
for std::collections::BTreeMap<K, V>
{
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut map = std::collections::BTreeMap::new();
for _ in 0..len {
let (key, new_offset) = K::from_bytes(&data[offset..])?;
offset += new_offset;
let (val, new_offset) = V::from_bytes(&data[offset..])?;
offset += new_offset;
map.insert(key, val);
}
Ok((map, offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut map = std::collections::BTreeMap::new();
for _ in 0..len {
let (key, new_offset) = K::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
let (val, new_offset) = V::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
map.insert(key, val);
}
Ok((map, offset))
}
}
impl<T: AFastSerialize> AFastSerialize for std::collections::BTreeSet<T> {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for item in self {
result.extend(item.to_bytes());
}
result
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE);
write_len(&mut result, self.len());
for item in self {
result.extend(item.to_bytes_with(marker));
}
result
}
}
impl<T: AFastDeserialize + Ord> AFastDeserialize for std::collections::BTreeSet<T> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut set = std::collections::BTreeSet::new();
for _ in 0..len {
let (item, new_offset) = T::from_bytes(&data[offset..])?;
offset += new_offset;
set.insert(item);
}
Ok((set, offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let (len, mut offset) = read_len(data, 0)?;
let mut set = std::collections::BTreeSet::new();
for _ in 0..len {
let (item, new_offset) = T::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
set.insert(item);
}
Ok((set, offset))
}
}
macro_rules! impl_tuple {
() => {};
($first:ident $(, $rest:ident)*) => {
#[allow(non_snake_case)]
impl<$first: AFastSerialize $(, $rest: AFastSerialize)*> AFastSerialize for ($first, $($rest,)*) {
fn to_bytes(&self) -> Vec<u8> {
let ($first, $($rest,)*) = self;
let mut result = Vec::new();
result.extend($first.to_bytes());
$(result.extend($rest.to_bytes());)*
result
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
let ($first, $($rest,)*) = self;
let mut result = Vec::new();
result.extend($first.to_bytes_with(marker));
$(result.extend($rest.to_bytes_with(marker));)*
result
}
}
#[allow(non_snake_case)]
impl<$first: AFastDeserialize $(, $rest: AFastDeserialize)*> AFastDeserialize for ($first, $($rest,)*) {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let mut offset = 0;
let ($first, new_offset) = <$first as AFastDeserialize>::from_bytes(&data[offset..])?;
offset += new_offset;
$(
let ($rest, new_offset) = <$rest as AFastDeserialize>::from_bytes(&data[offset..])?;
offset += new_offset;
)*
Ok((($first, $($rest,)*), offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let mut offset = 0;
let ($first, new_offset) = <$first as AFastDeserialize>::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
$(
let ($rest, new_offset) = <$rest as AFastDeserialize>::from_bytes_with(&data[offset..], marker)?;
offset += new_offset;
)*
Ok((($first, $($rest,)*), offset))
}
}
impl_tuple!($($rest),*);
};
}
impl<T: AFastSerialize> AFastSerialize for Box<T> {
fn to_bytes(&self) -> Vec<u8> {
(**self).to_bytes()
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
(**self).to_bytes_with(marker)
}
}
impl<T: AFastDeserialize> AFastDeserialize for Box<T> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (val, offset) = T::from_bytes(data)?;
Ok((Box::new(val), offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let (val, offset) = T::from_bytes_with(data, marker)?;
Ok((Box::new(val), offset))
}
}
#[cfg(all(
feature = "tuple-8",
not(any(feature = "tuple-16", feature = "tuple-32"))
))]
impl_tuple!(A, B, C, D, E, F, G, H);
#[cfg(all(feature = "tuple-16", not(feature = "tuple-32")))]
impl_tuple!(A, B, C, D, E, F, G, H, I, J, K, L, M, N, O, P);
#[cfg(feature = "tuple-32")]
impl_tuple!(
A, B, C, D, E, F, G, H, I, J, K, L, M, N, O, P, Q, R, S, T, U, V, W, X, Y, Z, AA, AB, AC, AD,
AE, AF
);
#[cfg(feature = "serde_json")]
impl AFastSerialize for serde_json::Number {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::new();
if let Some(n) = self.as_i64() {
result.push(0u8);
result.extend(n.to_le_bytes());
} else if let Some(n) = self.as_u64() {
result.push(1u8);
result.extend(n.to_le_bytes());
} else if let Some(n) = self.as_f64() {
result.push(2u8);
result.extend(n.to_le_bytes());
}
result
}
}
#[cfg(feature = "serde_json")]
impl AFastDeserialize for serde_json::Number {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 1)?;
match bytes[0] {
0 => {
let bytes = read_exact(data, 1, 8)?;
let arr: [u8; 8] = bytes.try_into().unwrap();
let n = i64::from_le_bytes(arr);
Ok((serde_json::Number::from(n), 9))
}
1 => {
let bytes = read_exact(data, 1, 8)?;
let arr: [u8; 8] = bytes.try_into().unwrap();
let n = u64::from_le_bytes(arr);
Ok((serde_json::Number::from(n), 9))
}
2 => {
let bytes = read_exact(data, 1, 8)?;
let arr: [u8; 8] = bytes.try_into().unwrap();
let n = f64::from_le_bytes(arr);
Ok((
serde_json::Number::from_f64(n).ok_or_else(|| {
Error::deserialize("Invalid f64 for serde_json::Number".to_string())
})?,
9,
))
}
v => Err(Error::deserialize(format!(
"Invalid serde_json::Number tag: {}",
v
))),
}
}
}
#[cfg(feature = "serde_json")]
impl AFastSerialize for serde_json::Value {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::new();
match self {
serde_json::Value::Null => {
result.push(0u8);
}
serde_json::Value::Bool(b) => {
result.push(1u8);
result.extend(b.to_bytes());
}
serde_json::Value::Number(n) => {
result.push(2u8);
result.extend(n.to_bytes());
}
serde_json::Value::String(s) => {
result.push(3u8);
result.extend(s.to_bytes());
}
serde_json::Value::Array(arr) => {
result.push(4u8);
write_len(&mut result, arr.len());
for item in arr {
result.extend(item.to_bytes());
}
}
serde_json::Value::Object(map) => {
result.push(5u8);
write_len(&mut result, map.len());
for (k, v) in map {
result.extend(k.to_bytes());
result.extend(v.to_bytes());
}
}
}
result
}
}
#[cfg(feature = "serde_json")]
impl AFastDeserialize for serde_json::Value {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 1)?;
let mut offset = 1usize;
match bytes[0] {
0 => Ok((serde_json::Value::Null, offset)),
1 => {
let (val, consumed) = bool::from_bytes(&data[offset..])?;
offset += consumed;
Ok((serde_json::Value::Bool(val), offset))
}
2 => {
let (val, consumed) = serde_json::Number::from_bytes(&data[offset..])?;
offset += consumed;
Ok((serde_json::Value::Number(val), offset))
}
3 => {
let (val, consumed) = String::from_bytes(&data[offset..])?;
offset += consumed;
Ok((serde_json::Value::String(val), offset))
}
4 => {
let (len, new_offset) = read_len(data, offset)?;
offset = new_offset;
let mut arr = Vec::with_capacity(len);
for _ in 0..len {
let (val, consumed) = serde_json::Value::from_bytes(&data[offset..])?;
arr.push(val);
offset += consumed;
}
Ok((serde_json::Value::Array(arr), offset))
}
5 => {
let (len, new_offset) = read_len(data, offset)?;
offset = new_offset;
let mut map = serde_json::Map::with_capacity(len);
for _ in 0..len {
let (key, consumed) = String::from_bytes(&data[offset..])?;
offset += consumed;
let (val, consumed) = serde_json::Value::from_bytes(&data[offset..])?;
offset += consumed;
map.insert(key, val);
}
Ok((serde_json::Value::Object(map), offset))
}
v => Err(Error::deserialize(format!(
"Invalid serde_json::Value tag: {}",
v
))),
}
}
}
impl AFastSerialize for std::net::Ipv4Addr {
fn to_bytes(&self) -> Vec<u8> {
self.octets().to_vec()
}
}
impl AFastDeserialize for std::net::Ipv4Addr {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 4)?;
Ok((
std::net::Ipv4Addr::new(bytes[0], bytes[1], bytes[2], bytes[3]),
4,
))
}
}
impl AFastSerialize for std::net::Ipv6Addr {
fn to_bytes(&self) -> Vec<u8> {
self.octets().to_vec()
}
}
impl AFastDeserialize for std::net::Ipv6Addr {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 16)?;
let arr: [u8; 16] = bytes.try_into().unwrap();
Ok((std::net::Ipv6Addr::from(arr), 16))
}
}
impl AFastSerialize for std::net::IpAddr {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::new();
match self {
std::net::IpAddr::V4(addr) => {
result.push(0u8);
result.extend(addr.to_bytes());
}
std::net::IpAddr::V6(addr) => {
result.push(1u8);
result.extend(addr.to_bytes());
}
}
result
}
}
impl AFastDeserialize for std::net::IpAddr {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 1)?;
let mut offset = 1usize;
match bytes[0] {
0 => {
let (addr, consumed) = std::net::Ipv4Addr::from_bytes(&data[offset..])?;
offset += consumed;
Ok((std::net::IpAddr::V4(addr), offset))
}
1 => {
let (addr, consumed) = std::net::Ipv6Addr::from_bytes(&data[offset..])?;
offset += consumed;
Ok((std::net::IpAddr::V6(addr), offset))
}
v => Err(Error::deserialize(format!("Invalid IpAddr tag: {}", v))),
}
}
}
#[cfg(feature = "uuid")]
impl AFastSerialize for uuid::Uuid {
fn to_bytes(&self) -> Vec<u8> {
self.as_bytes().to_vec()
}
}
#[cfg(feature = "uuid")]
impl AFastDeserialize for uuid::Uuid {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 16)?;
let arr: [u8; 16] = bytes.try_into().unwrap();
Ok((uuid::Uuid::from_bytes(arr), 16))
}
}
#[cfg(feature = "chrono")]
impl AFastSerialize for chrono::NaiveDate {
fn to_bytes(&self) -> Vec<u8> {
use chrono::Datelike;
let mut result = Vec::with_capacity(6);
result.extend((self.year()).to_le_bytes());
result.push(self.month() as u8);
result.push(self.day() as u8);
result
}
}
#[cfg(feature = "chrono")]
impl AFastDeserialize for chrono::NaiveDate {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 6)?;
let year = i32::from_le_bytes([bytes[0], bytes[1], bytes[2], bytes[3]]);
let month = bytes[4] as u32;
let day = bytes[5] as u32;
let date = chrono::NaiveDate::from_ymd_opt(year, month, day).ok_or_else(|| {
Error::deserialize(format!("Invalid NaiveDate: {}-{}-{}", year, month, day))
})?;
Ok((date, 6))
}
}
#[cfg(feature = "chrono")]
impl AFastSerialize for chrono::NaiveTime {
fn to_bytes(&self) -> Vec<u8> {
use chrono::Timelike;
let nanos =
self.num_seconds_from_midnight() as u64 * 1_000_000_000 + self.nanosecond() as u64;
nanos.to_le_bytes().to_vec()
}
}
#[cfg(feature = "chrono")]
impl AFastDeserialize for chrono::NaiveTime {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 8)?;
let arr: [u8; 8] = bytes.try_into().unwrap();
let total_nanos = u64::from_le_bytes(arr);
let secs = (total_nanos / 1_000_000_000) as u32;
let nanos = (total_nanos % 1_000_000_000) as u32;
let time = chrono::NaiveTime::from_num_seconds_from_midnight_opt(secs, nanos).ok_or_else(
|| Error::deserialize(format!("Invalid NaiveTime: {}s {}ns", secs, nanos)),
)?;
Ok((time, 8))
}
}
#[cfg(feature = "chrono")]
impl AFastSerialize for chrono::NaiveDateTime {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(14);
result.extend(self.date().to_bytes());
result.extend(self.time().to_bytes());
result
}
}
#[cfg(feature = "chrono")]
impl AFastDeserialize for chrono::NaiveDateTime {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let mut offset = 0;
let (date, consumed) = chrono::NaiveDate::from_bytes(&data[offset..])?;
offset += consumed;
let (time, consumed) = chrono::NaiveTime::from_bytes(&data[offset..])?;
offset += consumed;
Ok((date.and_time(time), offset))
}
}
#[cfg(feature = "chrono")]
impl AFastSerialize for chrono::DateTime<chrono::Utc> {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(12);
result.extend(self.timestamp().to_le_bytes());
result.extend(self.timestamp_subsec_nanos().to_le_bytes());
result
}
}
#[cfg(feature = "chrono")]
impl AFastDeserialize for chrono::DateTime<chrono::Utc> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 12)?;
let secs = i64::from_le_bytes([
bytes[0], bytes[1], bytes[2], bytes[3], bytes[4], bytes[5], bytes[6], bytes[7],
]);
let nanos = u32::from_le_bytes([bytes[8], bytes[9], bytes[10], bytes[11]]);
let dt = chrono::DateTime::from_timestamp(secs, nanos).ok_or_else(|| {
Error::deserialize(format!("Invalid DateTime<Utc>: {}s {}ns", secs, nanos))
})?;
Ok((dt, 12))
}
}
#[cfg(feature = "chrono")]
impl AFastSerialize for chrono::DateTime<chrono::Local> {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(12);
result.extend(self.timestamp().to_le_bytes());
result.extend(self.timestamp_subsec_nanos().to_le_bytes());
result
}
}
#[cfg(feature = "chrono")]
impl AFastDeserialize for chrono::DateTime<chrono::Local> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 12)?;
let secs = i64::from_le_bytes([
bytes[0], bytes[1], bytes[2], bytes[3], bytes[4], bytes[5], bytes[6], bytes[7],
]);
let nanos = u32::from_le_bytes([bytes[8], bytes[9], bytes[10], bytes[11]]);
let dt = chrono::DateTime::from_timestamp(secs, nanos).ok_or_else(|| {
Error::deserialize(format!("Invalid DateTime<Local>: {}s {}ns", secs, nanos))
})?;
Ok((dt.with_timezone(&chrono::Local), 12))
}
}
#[cfg(feature = "rust_decimal")]
impl AFastSerialize for rust_decimal::Decimal {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(20);
result.extend(self.mantissa().to_le_bytes());
result.extend(self.scale().to_le_bytes());
result
}
}
#[cfg(feature = "rust_decimal")]
impl AFastDeserialize for rust_decimal::Decimal {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 20)?;
let mantissa = i128::from_le_bytes(bytes[0..16].try_into().unwrap());
let scale = u32::from_le_bytes(bytes[16..20].try_into().unwrap());
Ok((
rust_decimal::Decimal::from_i128_with_scale(mantissa, scale),
20,
))
}
}
#[cfg(feature = "url")]
impl AFastSerialize for url::Url {
fn to_bytes(&self) -> Vec<u8> {
let s = self.as_str();
let bytes = s.as_bytes();
let mut result = Vec::with_capacity(LEN_INT_SIZE + bytes.len());
write_len(&mut result, bytes.len());
result.extend_from_slice(bytes);
result
}
}
#[cfg(feature = "url")]
impl AFastDeserialize for url::Url {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, offset) = read_len(data, 0)?;
let bytes = read_exact(data, offset, len)?;
let s = std::str::from_utf8(bytes)
.map_err(|e| Error::deserialize(format!("Invalid UTF-8 for Url: {}", e)))?;
let url = s
.parse::<url::Url>()
.map_err(|e| Error::deserialize(format!("Invalid Url: {}", e)))?;
Ok((url, offset + len))
}
}
#[cfg(feature = "bytes")]
impl AFastSerialize for bytes::Bytes {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE + self.len());
write_len(&mut result, self.len());
result.extend_from_slice(self);
result
}
}
#[cfg(feature = "bytes")]
impl AFastDeserialize for bytes::Bytes {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, offset) = read_len(data, 0)?;
let bytes = read_exact(data, offset, len)?;
Ok((bytes::Bytes::copy_from_slice(bytes), offset + len))
}
}
#[cfg(feature = "bytes")]
impl AFastSerialize for bytes::BytesMut {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(LEN_INT_SIZE + self.len());
write_len(&mut result, self.len());
result.extend_from_slice(self);
result
}
}
#[cfg(feature = "bytes")]
impl AFastDeserialize for bytes::BytesMut {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (len, offset) = read_len(data, 0)?;
let bytes_slice = read_exact(data, offset, len)?;
let mut buf = bytes::BytesMut::with_capacity(len);
buf.extend_from_slice(bytes_slice);
Ok((buf, offset + len))
}
}
#[cfg(feature = "bigdecimal")]
impl AFastSerialize for bigdecimal::BigDecimal {
fn to_bytes(&self) -> Vec<u8> {
use bigdecimal::num_bigint::Sign;
let (bigint, exp) = self.as_bigint_and_exponent();
let (sign, bytes) = bigint.to_bytes_be();
let mut result = Vec::new();
result.push(match sign {
Sign::NoSign => 0u8,
Sign::Minus => 1u8,
Sign::Plus => 2u8,
});
write_len(&mut result, bytes.len());
result.extend_from_slice(&bytes);
result.extend(exp.to_le_bytes());
result
}
}
#[cfg(feature = "bigdecimal")]
impl AFastDeserialize for bigdecimal::BigDecimal {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
use bigdecimal::num_bigint::{BigInt, Sign};
let bytes = read_exact(data, 0, 1)?;
let sign = match bytes[0] {
0 => Sign::NoSign,
1 => Sign::Minus,
2 => Sign::Plus,
v => {
return Err(Error::deserialize(format!(
"Invalid BigDecimal sign: {}",
v
)));
}
};
let mut offset = 1;
let (len, new_offset) = read_len(data, offset)?;
offset = new_offset;
let bigint_bytes = read_exact(data, offset, len)?;
offset += len;
let bigint = BigInt::from_bytes_be(sign, bigint_bytes);
let exp_bytes = read_exact(data, offset, 8)?;
offset += 8;
let exp = i64::from_le_bytes(exp_bytes.try_into().unwrap());
let bd = bigdecimal::BigDecimal::new(bigint, exp);
Ok((bd, offset))
}
}
#[cfg(feature = "ipnetwork")]
impl AFastSerialize for ipnetwork::Ipv4Network {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(5);
result.extend(self.ip().octets());
result.push(self.prefix());
result
}
}
#[cfg(feature = "ipnetwork")]
impl AFastDeserialize for ipnetwork::Ipv4Network {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 5)?;
let ip = std::net::Ipv4Addr::new(bytes[0], bytes[1], bytes[2], bytes[3]);
let prefix = bytes[4];
let net = ipnetwork::Ipv4Network::new(ip, prefix)
.map_err(|e| Error::deserialize(format!("Invalid Ipv4Network: {}", e)))?;
Ok((net, 5))
}
}
#[cfg(feature = "ipnetwork")]
impl AFastSerialize for ipnetwork::Ipv6Network {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::with_capacity(17);
result.extend(self.ip().octets());
result.push(self.prefix());
result
}
}
#[cfg(feature = "ipnetwork")]
impl AFastDeserialize for ipnetwork::Ipv6Network {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 17)?;
let arr: [u8; 16] = bytes[..16].try_into().unwrap();
let ip = std::net::Ipv6Addr::from(arr);
let prefix = bytes[16];
let net = ipnetwork::Ipv6Network::new(ip, prefix)
.map_err(|e| Error::deserialize(format!("Invalid Ipv6Network: {}", e)))?;
Ok((net, 17))
}
}
#[cfg(feature = "ipnetwork")]
impl AFastSerialize for ipnetwork::IpNetwork {
fn to_bytes(&self) -> Vec<u8> {
let mut result = Vec::new();
match self {
ipnetwork::IpNetwork::V4(net) => {
result.push(0u8);
result.extend(net.to_bytes());
}
ipnetwork::IpNetwork::V6(net) => {
result.push(1u8);
result.extend(net.to_bytes());
}
}
result
}
}
#[cfg(feature = "ipnetwork")]
impl AFastDeserialize for ipnetwork::IpNetwork {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 1)?;
let mut offset = 1usize;
match bytes[0] {
0 => {
let (net, consumed) = ipnetwork::Ipv4Network::from_bytes(&data[offset..])?;
offset += consumed;
Ok((ipnetwork::IpNetwork::V4(net), offset))
}
1 => {
let (net, consumed) = ipnetwork::Ipv6Network::from_bytes(&data[offset..])?;
offset += consumed;
Ok((ipnetwork::IpNetwork::V6(net), offset))
}
v => Err(Error::deserialize(format!("Invalid IpNetwork tag: {}", v))),
}
}
}
#[cfg(feature = "mac_address")]
impl AFastSerialize for mac_address::MacAddress {
fn to_bytes(&self) -> Vec<u8> {
self.bytes().to_vec()
}
}
#[cfg(feature = "mac_address")]
impl AFastDeserialize for mac_address::MacAddress {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let bytes = read_exact(data, 0, 6)?;
let arr: [u8; 6] = bytes.try_into().unwrap();
Ok((mac_address::MacAddress::new(arr), 6))
}
}
#[cfg(feature = "sqlx")]
impl<T: AFastSerialize> AFastSerialize for sqlx::types::Json<T> {
fn to_bytes(&self) -> Vec<u8> {
(**self).to_bytes()
}
fn to_bytes_with(&self, marker: &str) -> Vec<u8> {
(**self).to_bytes_with(marker)
}
}
#[cfg(feature = "sqlx")]
impl<T: AFastDeserialize> AFastDeserialize for sqlx::types::Json<T> {
fn from_bytes(data: &[u8]) -> Result<(Self, usize), Error> {
let (val, offset) = T::from_bytes(data)?;
Ok((sqlx::types::Json(val), offset))
}
fn from_bytes_with(data: &[u8], marker: &str) -> Result<(Self, usize), Error> {
let (val, offset) = T::from_bytes_with(data, marker)?;
Ok((sqlx::types::Json(val), offset))
}
}