Skip to content

Commit 5bc4737

Browse files
committed
fix deriving scalar on generic types
1 parent 5a35b9f commit 5bc4737

File tree

9 files changed

+62
-66
lines changed

9 files changed

+62
-66
lines changed

cynic-codegen/src/fragment_derive/deserialize_impl.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
use proc_macro2::TokenStream;
22
use quote::quote_spanned;
33

4-
use crate::schema::{types::OutputType, Schema, Unvalidated};
4+
use crate::schema::{Schema, Unvalidated};
55

66
use super::FieldKind;
77

cynic-codegen/src/fragment_derive/fragment_impl.rs

Lines changed: 1 addition & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,7 @@ use {
66

77
use crate::{
88
error::Errors,
9-
schema::{
10-
types::{Field, OutputType},
11-
Schema, Unvalidated,
12-
},
9+
schema::{types::Field, Schema, Unvalidated},
1310
types::{self, check_spread_type, check_types_are_compatible, CheckMode},
1411
variables_fields_path,
1512
};
@@ -409,12 +406,3 @@ impl quote::ToTokens for SpreadSelection {
409406
})
410407
}
411408
}
412-
413-
impl OutputType<'_> {
414-
fn is_composite(&self) -> bool {
415-
matches!(
416-
self,
417-
OutputType::Object(_) | OutputType::Interface(_) | OutputType::Union(_)
418-
)
419-
}
420-
}

cynic-codegen/src/scalar_derive/mod.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -82,7 +82,7 @@ pub fn scalar_derive_impl(input: ScalarDeriveInput) -> Result<TokenStream, syn::
8282
}
8383

8484
#[automatically_derived]
85-
impl #impl_generics cynic::schema::IsScalar<#marker_ident> for #ident #ty_generics #where_clause {
85+
impl #impl_generics_with_ser cynic::schema::IsScalar<#marker_ident> for #ident #ty_generics #where_clause_with_ser {
8686
type SchemaType = #marker_ident;
8787

8888
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
@@ -94,12 +94,12 @@ pub fn scalar_derive_impl(input: ScalarDeriveInput) -> Result<TokenStream, syn::
9494
}
9595

9696
#[automatically_derived]
97-
impl #impl_generics cynic::schema::IsOutputScalar<#marker_ident> for #ident #ty_generics #where_clause {
97+
impl #impl_generics_with_de cynic::schema::IsOutputScalar<'de, #marker_ident> for #ident #ty_generics #where_clause_with_de {
9898
type SchemaType = #marker_ident;
9999

100-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
100+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
101101
where
102-
D: cynic::serde::Deserializer<'de>
102+
D: cynic::serde::Deserializer<'de>,
103103
{
104104
<Self as cynic::serde::Deserialize>::deserialize(deserializer)
105105
}

cynic/src/lib.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -247,10 +247,10 @@ macro_rules! impl_scalar {
247247
}
248248

249249
#[automatically_derived]
250-
impl $crate::schema::IsOutputScalar<$schema_module$(::$schema_module_rest)*::$type_lock> for $type {
250+
impl<'de> $crate::schema::IsOutputScalar<'de, $schema_module$(::$schema_module_rest)*::$type_lock> for $type {
251251
type SchemaType = $schema_module$(::$schema_module_rest)*::$type_lock;
252252

253-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
253+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
254254
where
255255
D: $crate::serde::Deserializer<'de>
256256
{

cynic/src/private/flatten_de.rs

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
use std::marker::PhantomData;
2+
13
use serde::Deserialize;
24

35
use crate::schema::IsOutputScalar;
@@ -44,27 +46,29 @@ where
4446

4547
impl<'de, T, U> Deserialize<'de> for Flattened<super::ScalarDeserialize<Vec<T>, U>>
4648
where
47-
Option<Vec<Option<T>>>: IsOutputScalar<U>,
49+
Option<Vec<Option<T>>>: IsOutputScalar<'de, U>,
4850
{
4951
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
5052
where
5153
D: serde::Deserializer<'de>,
5254
{
5355
super::ScalarDeserialize::<Option<Vec<Option<T>>>, U>::deserialize(deserializer).map(
54-
|opt_vec| Flattened {
55-
inner: todo!(
56-
"opt_vec
57-
.map(|vec| vec.into_iter().flatten().collect::<Vec<_>>())
58-
.unwrap_or_default(),"
59-
),
56+
|deser| Flattened {
57+
inner: super::ScalarDeserialize {
58+
inner: deser
59+
.into_inner()
60+
.map(|vec| vec.into_iter().flatten().collect::<Vec<_>>())
61+
.unwrap_or_default(),
62+
phantom: PhantomData,
63+
},
6064
},
6165
)
6266
}
6367
}
6468

6569
impl<'de, T, U> Deserialize<'de> for Flattened<super::ScalarDeserialize<Option<Vec<T>>, U>>
6670
where
67-
Option<Vec<Option<T>>>: IsOutputScalar<U>,
71+
Option<Vec<Option<T>>>: IsOutputScalar<'de, U>,
6872
{
6973
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
7074
where

cynic/src/private/scalar_serde.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,8 @@ use serde::Deserialize;
55
use crate::schema::{IsOutputScalar, IsScalar};
66

77
pub struct ScalarDeserialize<T, U> {
8-
inner: T,
9-
phantom: PhantomData<fn() -> U>,
8+
pub(super) inner: T,
9+
pub(super) phantom: PhantomData<fn() -> U>,
1010
}
1111

1212
impl<T, U> ScalarDeserialize<T, U> {
@@ -27,7 +27,7 @@ impl<T, U> ScalarDeserialize<T, U> {
2727

2828
impl<'de, T, U> Deserialize<'de> for ScalarDeserialize<T, U>
2929
where
30-
T: IsOutputScalar<U>,
30+
T: IsOutputScalar<'de, U>,
3131
{
3232
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
3333
where

cynic/src/schema.rs

Lines changed: 27 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
//! usually be marker types and the associated types will also usually be
1212
//! markers.
1313
14-
use std::borrow::{Borrow, Cow};
14+
use std::borrow::Cow;
1515

1616
use serde::{ser::SerializeSeq, Deserialize, Deserializer, Serializer};
1717

@@ -75,11 +75,11 @@ pub trait IsScalar<SchemaType> {
7575

7676
// TODO: serialize should maybe be on an InputScalar trait
7777
// or maybe just ScalarSerialize/ScalarDeserialize? not sure...
78-
pub trait IsOutputScalar<SchemaType>: Sized {
78+
pub trait IsOutputScalar<'de, SchemaType>: Sized {
7979
/// The schema marker type this scalar represents.
8080
type SchemaType;
8181

82-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
82+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
8383
where
8484
D: Deserializer<'de>;
8585
}
@@ -115,13 +115,13 @@ where
115115
}
116116
}
117117

118-
impl<T, U> IsOutputScalar<Option<T>> for Option<U>
118+
impl<'de, T, U> IsOutputScalar<'de, Option<T>> for Option<U>
119119
where
120-
U: IsOutputScalar<T>,
120+
U: IsOutputScalar<'de, T>,
121121
{
122122
type SchemaType = Option<U::SchemaType>;
123123

124-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
124+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
125125
where
126126
D: Deserializer<'de>,
127127
{
@@ -150,13 +150,13 @@ where
150150
}
151151
}
152152

153-
impl<T, U> IsOutputScalar<Vec<T>> for Vec<U>
153+
impl<'de, T, U> IsOutputScalar<'de, Vec<T>> for Vec<U>
154154
where
155-
U: IsOutputScalar<T>,
155+
U: IsOutputScalar<'de, T>,
156156
{
157157
type SchemaType = Vec<U::SchemaType>;
158158

159-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
159+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
160160
where
161161
D: Deserializer<'de>,
162162
{
@@ -217,13 +217,13 @@ where
217217
}
218218
}
219219

220-
impl<T, U: ?Sized> IsOutputScalar<Box<T>> for Box<U>
220+
impl<'de, T, U: ?Sized> IsOutputScalar<'de, Box<T>> for Box<U>
221221
where
222-
U: IsOutputScalar<T>,
222+
U: IsOutputScalar<'de, T>,
223223
{
224224
type SchemaType = Box<U::SchemaType>;
225225

226-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
226+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
227227
where
228228
D: Deserializer<'de>,
229229
{
@@ -245,24 +245,24 @@ where
245245
}
246246
}
247247

248-
impl<T, U: ?Sized> IsOutputScalar<T> for std::borrow::Cow<'_, U>
248+
impl<'de, T, U: ?Sized> IsOutputScalar<'de, T> for std::borrow::Cow<'_, U>
249249
where
250-
U: IsOutputScalar<T> + ToOwned,
250+
U: IsOutputScalar<'de, T> + ToOwned,
251251
{
252252
type SchemaType = U::SchemaType;
253253

254-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
254+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
255255
where
256256
D: Deserializer<'de>,
257257
{
258258
Ok(Cow::Owned(U::deserialize(deserializer)?.to_owned()))
259259
}
260260
}
261261

262-
impl IsOutputScalar<String> for std::borrow::Cow<'static, str> {
262+
impl<'de> IsOutputScalar<'de, String> for std::borrow::Cow<'static, str> {
263263
type SchemaType = String;
264264

265-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
265+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
266266
where
267267
D: Deserializer<'de>,
268268
{
@@ -283,10 +283,10 @@ impl IsScalar<bool> for bool {
283283
}
284284
}
285285

286-
impl IsOutputScalar<bool> for bool {
286+
impl<'de> IsOutputScalar<'de, bool> for bool {
287287
type SchemaType = bool;
288288

289-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
289+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
290290
where
291291
D: Deserializer<'de>,
292292
{
@@ -305,10 +305,10 @@ impl IsScalar<String> for String {
305305
}
306306
}
307307

308-
impl IsOutputScalar<String> for String {
308+
impl<'de> IsOutputScalar<'de, String> for String {
309309
type SchemaType = String;
310310

311-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
311+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
312312
where
313313
D: Deserializer<'de>,
314314
{
@@ -338,10 +338,10 @@ impl IsScalar<i32> for i32 {
338338
}
339339
}
340340

341-
impl IsOutputScalar<i32> for i32 {
341+
impl<'de> IsOutputScalar<'de, i32> for i32 {
342342
type SchemaType = i32;
343343

344-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
344+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
345345
where
346346
D: Deserializer<'de>,
347347
{
@@ -360,10 +360,10 @@ impl IsScalar<f64> for f64 {
360360
}
361361
}
362362

363-
impl IsOutputScalar<f64> for f64 {
363+
impl<'de> IsOutputScalar<'de, f64> for f64 {
364364
type SchemaType = f64;
365365

366-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
366+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
367367
where
368368
D: Deserializer<'de>,
369369
{
@@ -382,10 +382,10 @@ impl IsScalar<crate::Id> for crate::Id {
382382
}
383383
}
384384

385-
impl IsOutputScalar<crate::Id> for crate::Id {
385+
impl<'de> IsOutputScalar<'de, crate::Id> for crate::Id {
386386
type SchemaType = crate::Id;
387387

388-
fn deserialize<'de, D>(deserializer: D) -> Result<Self, D::Error>
388+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
389389
where
390390
D: Deserializer<'de>,
391391
{

cynic/tests/mutation_generics.rs

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -40,9 +40,11 @@ pub struct SignIn {
4040
variables = "SignInVariablesMoreGeneric",
4141
schema_path = "../schemas/raindancer.graphql"
4242
)]
43-
pub struct SignInMoreGeneric<SI: cynic::schema::IsOutputScalar<String>>
43+
pub struct SignInMoreGeneric<SI>
4444
where
45-
<SI as cynic::schema::IsOutputScalar<String>>::SchemaType: cynic::queries::IsFieldType<String>,
45+
for<'de2> SI: cynic::schema::IsOutputScalar<'de2, String>,
46+
for<'de2> <SI as cynic::schema::IsOutputScalar<'de2, String>>::SchemaType:
47+
cynic::queries::IsFieldType<String>,
4648
{
4749
#[arguments(input: $input)]
4850
pub sign_in: SI,

cynic/tests/scalars.rs

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
use serde::{de::DeserializeOwned, Deserialize, Serialize};
2-
31
mod schema {
42
cynic::use_schema!("tests/test-schema.graphql");
53
}
@@ -11,24 +9,28 @@ pub struct DateTime(pub chrono::DateTime<chrono::Utc>);
119
// Make sure we can impl_scalar for third party types.
1210
cynic::impl_scalar!(chrono::DateTime<chrono::Utc>, schema::DateTime);
1311

14-
// TODO: Reinstate this...
15-
// #[derive(cynic::Scalar)]
16-
// #[cynic(graphql_type = "DateTime")]
17-
// pub struct DateTimeInner<DT>(pub DT);
12+
#[derive(cynic::Scalar)]
13+
#[cynic(graphql_type = "DateTime")]
14+
pub struct DateTimeInner<DT>(pub DT);
1815

1916
// Make sure we can use impl scalar on built in types
17+
#[derive(serde::Serialize, serde::Deserialize)]
2018
pub struct MyString(#[allow(dead_code)] String);
2119
cynic::impl_scalar!(MyString, schema::String);
2220

21+
#[derive(serde::Serialize, serde::Deserialize)]
2322
pub struct MyInt(#[allow(dead_code)] i64);
2423
cynic::impl_scalar!(MyInt, schema::Int);
2524

25+
#[derive(serde::Serialize, serde::Deserialize)]
2626
pub struct MyFloat(#[allow(dead_code)] f64);
2727
cynic::impl_scalar!(MyFloat, schema::Float);
2828

29+
#[derive(serde::Serialize, serde::Deserialize)]
2930
pub struct MyBool(#[allow(dead_code)] bool);
3031
cynic::impl_scalar!(MyBool, schema::Boolean);
3132

33+
#[derive(serde::Serialize, serde::Deserialize)]
3234
pub struct MyId(#[allow(dead_code)] cynic::Id);
3335
cynic::impl_scalar!(MyId, schema::ID);
3436

0 commit comments

Comments
 (0)