Skip to content

Commit

Permalink
Attempt to finish serialize, but.. macros :(
Browse files Browse the repository at this point in the history
  • Loading branch information
fasterthanlime committed Nov 4, 2024
1 parent 447dd72 commit dabf786
Show file tree
Hide file tree
Showing 6 changed files with 65 additions and 12 deletions.
2 changes: 1 addition & 1 deletion merde/examples/enums.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ fn main() {
];

for event in events {
let json = event.to_json_string();
let json = event.to_json_string().unwrap();
println!("JSON: {}", json);
let deserialized: ExampleEvent = merde::json::from_str(&json).unwrap();
println!("Deserialized: {:?}", deserialized);
Expand Down
2 changes: 1 addition & 1 deletion merde/examples/return-deserialize.rs
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ fn main() {
let person: Person = merde_json::from_str(input).unwrap();
println!("{:?}", person);

let serialized = person.to_json_string();
let serialized = person.to_json_string().unwrap();
let person2: Person = merde_json::from_str(&serialized).unwrap();
println!("{:?}", person2);

Expand Down
2 changes: 1 addition & 1 deletion merde/examples/simple.rs
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ fn main() {
// Round-trip! Again, every binding borrows from the previous one, and
// everything can be converted from `F<'a>` to `F<'static>` via the
// `IntoStatic` trait.
let serialized = person.to_json_string();
let serialized = person.to_json_string().unwrap();
let person2: Person = merde_json::from_str(&serialized).unwrap();
println!("{:#?}", person2);

Expand Down
27 changes: 18 additions & 9 deletions merde/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -453,15 +453,15 @@ macro_rules! impl_with_lifetime {

#[doc(hidden)]
#[macro_export]
#[cfg(all(feature = "core"))]
#[cfg(feature = "core")]
macro_rules! impl_serialize {
// owned tuple struct (transparent)
(struct $struct_name:ident transparent) => {
#[automatically_derived]
impl $crate::Serialize for $struct_name {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
S: $crate::Serializer + ?Sized,
{
self.0.serialize(serializer).await
}
Expand All @@ -474,7 +474,7 @@ macro_rules! impl_serialize {
impl<$lifetime> $crate::Serialize for $struct_name<$lifetime> {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
S: $crate::Serializer + ?Sized,
{
self.0.serialize(serializer).await
}
Expand All @@ -487,13 +487,13 @@ macro_rules! impl_serialize {
impl<$lifetime> $crate::Serialize for $struct_name<$lifetime> {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
S: $crate::Serializer + ?Sized,
{
#[allow(unused_imports)]
use $crate::Event;

serializer
.write(Event::MapStart(MapStart {
.write(Event::MapStart($crate::MapStart {
size_hint: Some($crate::count_ident_tokens!($($field)*)),
}))
.await?;
Expand All @@ -512,7 +512,7 @@ macro_rules! impl_serialize {
impl $crate::Serialize for $struct_name {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
S: $crate::Serializer + ?Sized,
{
#[allow(unused_imports)]
use $crate::Event;
Expand All @@ -539,7 +539,7 @@ macro_rules! impl_serialize {
impl $crate::Serialize for $enum_name {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
S: $crate::Serializer + ?Sized,
{
#[allow(unused_imports)]
use $crate::Event;
Expand Down Expand Up @@ -572,7 +572,7 @@ macro_rules! impl_serialize {
impl<$lifetime> $crate::Serialize for $enum_name<$lifetime> {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
S: $crate::Serializer + ?Sized,
{
#[allow(unused_imports)]
use $crate::Event;
Expand Down Expand Up @@ -605,7 +605,7 @@ macro_rules! impl_serialize {
impl $crate::Serialize for $enum_name {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
S: $crate::Serializer + ?Sized,
{
#[allow(unused_imports)]
use $crate::Event;
Expand Down Expand Up @@ -745,6 +745,15 @@ pub fn none_of<I, T>(_f: impl FnOnce(I) -> T) -> Option<T> {
None
}

#[doc(hidden)]
#[macro_export]
macro_rules! count_ident_tokens {
() => { 0 };
($first:ident) => { 1 };
($first:ident $($rest:ident)*) => {
1 + $crate::count_ident_tokens!($($rest)*)
};
}
#[cfg(test)]
#[cfg(feature = "json")]
mod json_tests {
Expand Down
42 changes: 42 additions & 0 deletions merde_core/src/serialize.rs
Original file line number Diff line number Diff line change
Expand Up @@ -243,5 +243,47 @@ impl<'s> Serialize for Value<'s> {
}
}

macro_rules! impl_serialize_for_tuple {
($($type_arg:ident),*) => {
impl<$($type_arg: Serialize),*> Serialize for ($($type_arg),*,) {
async fn serialize<S>(&self, serializer: &mut S) -> Result<(), S::Error>
where
S: Serializer + ?Sized,
{
serializer.write(Event::ArrayStart(ArrayStart {
size_hint: Some(count_tup!($($type_arg)*))
})).await?;

impl_serialize_for_tuple!(@inner self serializer () ($($type_arg)*));
serializer.write(Event::ArrayEnd).await
}
}
};

(@inner $self:ident $serializer:ident ($($ignores:pat)*) ($m:ident $($r:ident)*)) => {
let ($($ignores)*, _field, ..) = $self;
_field.serialize($serializer).await?;
impl_serialize_for_tuple!(@inner $self $serializer ($($ignores)* _) ($($r)*));
};
(@inner $self:ident $serializer:ident ($($ignores:pat)*) ($m:ident)) => {
let ($($ignores)*, _field) = $self;
_field.serialize($serializer).await?;
};

// turns (a b c) into (_, _, _,)
(@to_underscore $($x:ident)*) => ($(_,)*);
}

const fn increment(x: usize) -> usize {
x + 1
}

macro_rules! count_tup {
() => { 0 };
($t:ident $($rest:ident)*) => { 1 + count_tup!($($rest)*) };
}

impl_serialize_for_tuple!(T0);

#[cfg(test)]
mod tests;
2 changes: 2 additions & 0 deletions merde_json/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -217,6 +217,8 @@ pub trait JsonSerialize: Serialize + Sized {
}
}

impl<T> JsonSerialize for T where T: Serialize {}

/// Unifies [MerdeError] and [JiterError] into a single type
pub enum MerdeJsonError<'s> {
/// A [MerdeError]
Expand Down

0 comments on commit dabf786

Please sign in to comment.