Skip to main content

juniper/types/
marker.rs

1//! Marker traits for GraphQL types.
2//!
3//! This module provide specialized types for GraphQL. To ensure that
4//! only specification compliant construct compile, these marker
5//! traits are used. Encountering an error where one of these traits
6//! is involved implies that the construct is not valid in GraphQL.
7
8use std::sync::Arc;
9
10use crate::{GraphQLType, ScalarValue};
11
12/// Maker trait for [GraphQL objects][1].
13///
14/// This trait extends the [`GraphQLType`] and is only used to mark an [object][1]. During
15/// compile this addition information is required to prevent unwanted structure compiling. If an
16/// object requires this trait instead of the [`GraphQLType`], then it explicitly requires
17/// [GraphQL objects][1]. Other types ([scalars][2], [enums][3], [interfaces][4], [input objects][5]
18/// and [unions][6]) are not allowed.
19///
20/// [1]: https://spec.graphql.org/October2021#sec-Objects
21/// [2]: https://spec.graphql.org/October2021#sec-Scalars
22/// [3]: https://spec.graphql.org/October2021#sec-Enums
23/// [4]: https://spec.graphql.org/October2021#sec-Interfaces
24/// [5]: https://spec.graphql.org/October2021#sec-Input-Objects
25/// [6]: https://spec.graphql.org/October2021#sec-Unions
26pub trait GraphQLObject<S: ScalarValue>: GraphQLType<S> {
27    /// An arbitrary function without meaning.
28    ///
29    /// May contain compile timed check logic which ensures that types are used correctly according
30    /// to the [GraphQL specification][1].
31    ///
32    /// [1]: https://spec.graphql.org/October2021
33    fn mark() {}
34}
35
36impl<S, T> GraphQLObject<S> for &T
37where
38    T: GraphQLObject<S> + ?Sized,
39    S: ScalarValue,
40{
41    #[inline]
42    fn mark() {
43        T::mark()
44    }
45}
46
47impl<S, T> GraphQLObject<S> for Box<T>
48where
49    T: GraphQLObject<S> + ?Sized,
50    S: ScalarValue,
51{
52    #[inline]
53    fn mark() {
54        T::mark()
55    }
56}
57
58impl<S, T> GraphQLObject<S> for Arc<T>
59where
60    T: GraphQLObject<S> + ?Sized,
61    S: ScalarValue,
62{
63    #[inline]
64    fn mark() {
65        T::mark()
66    }
67}
68
69/// Maker trait for [GraphQL interfaces][1].
70///
71/// This trait extends the [`GraphQLType`] and is only used to mark an [interface][1]. During
72/// compile this addition information is required to prevent unwanted structure compiling. If an
73/// object requires this trait instead of the [`GraphQLType`], then it explicitly requires
74/// [GraphQL interfaces][1]. Other types ([scalars][2], [enums][3], [objects][4], [input objects][5]
75/// and [unions][6]) are not allowed.
76///
77/// [1]: https://spec.graphql.org/October2021#sec-Interfaces
78/// [2]: https://spec.graphql.org/October2021#sec-Scalars
79/// [3]: https://spec.graphql.org/October2021#sec-Enums
80/// [4]: https://spec.graphql.org/October2021#sec-Objects
81/// [5]: https://spec.graphql.org/October2021#sec-Input-Objects
82/// [6]: https://spec.graphql.org/October2021#sec-Unions
83pub trait GraphQLInterface<S: ScalarValue>: GraphQLType<S> {
84    /// An arbitrary function without meaning.
85    ///
86    /// May contain compile timed check logic which ensures that types are used correctly according
87    /// to the [GraphQL specification][1].
88    ///
89    /// [1]: https://spec.graphql.org/October2021
90    fn mark() {}
91}
92
93impl<S, T> GraphQLInterface<S> for &T
94where
95    T: GraphQLInterface<S> + ?Sized,
96    S: ScalarValue,
97{
98    #[inline]
99    fn mark() {
100        T::mark()
101    }
102}
103
104impl<S, T> GraphQLInterface<S> for Box<T>
105where
106    T: GraphQLInterface<S> + ?Sized,
107    S: ScalarValue,
108{
109    #[inline]
110    fn mark() {
111        T::mark()
112    }
113}
114
115impl<S, T> GraphQLInterface<S> for Arc<T>
116where
117    T: GraphQLInterface<S> + ?Sized,
118    S: ScalarValue,
119{
120    #[inline]
121    fn mark() {
122        T::mark()
123    }
124}
125
126/// Maker trait for [GraphQL unions][1].
127///
128/// This trait extends the [`GraphQLType`] and is only used to mark an [union][1]. During compile
129/// this addition information is required to prevent unwanted structure compiling. If an object
130/// requires this trait instead of the [`GraphQLType`], then it explicitly requires
131/// [GraphQL unions][1]. Other types ([scalars][2], [enums][3], [objects][4], [input objects][5] and
132/// [interfaces][6]) are not allowed.
133///
134/// [1]: https://spec.graphql.org/October2021#sec-Unions
135/// [2]: https://spec.graphql.org/October2021#sec-Scalars
136/// [3]: https://spec.graphql.org/October2021#sec-Enums
137/// [4]: https://spec.graphql.org/October2021#sec-Objects
138/// [5]: https://spec.graphql.org/October2021#sec-Input-Objects
139/// [6]: https://spec.graphql.org/October2021#sec-Interfaces
140pub trait GraphQLUnion<S: ScalarValue>: GraphQLType<S> {
141    /// An arbitrary function without meaning.
142    ///
143    /// May contain compile timed check logic which ensures that types are used correctly according
144    /// to the [GraphQL specification][1].
145    ///
146    /// [1]: https://spec.graphql.org/October2021
147    fn mark() {}
148}
149
150impl<S, T> GraphQLUnion<S> for &T
151where
152    T: GraphQLUnion<S> + ?Sized,
153    S: ScalarValue,
154{
155    #[inline]
156    fn mark() {
157        T::mark()
158    }
159}
160
161impl<S, T> GraphQLUnion<S> for Box<T>
162where
163    T: GraphQLUnion<S> + ?Sized,
164    S: ScalarValue,
165{
166    #[inline]
167    fn mark() {
168        T::mark()
169    }
170}
171
172impl<S, T> GraphQLUnion<S> for Arc<T>
173where
174    T: GraphQLUnion<S> + ?Sized,
175    S: ScalarValue,
176{
177    #[inline]
178    fn mark() {
179        T::mark()
180    }
181}
182
183/// Marker trait for types which can be used as output types.
184///
185/// The GraphQL specification differentiates between input and output
186/// types. Each type which can be used as an output type should
187/// implement this trait. The specification defines enum, scalar,
188/// object, union, and interface as output types.
189pub trait IsOutputType<S: ScalarValue>: GraphQLType<S> {
190    /// An arbitrary function without meaning.
191    ///
192    /// May contain compile timed check logic which ensures that types
193    /// are used correctly according to the GraphQL specification.
194    fn mark() {}
195}
196
197impl<S, T> IsOutputType<S> for &T
198where
199    T: IsOutputType<S> + ?Sized,
200    S: ScalarValue,
201{
202    #[inline]
203    fn mark() {
204        T::mark()
205    }
206}
207
208impl<S, T> IsOutputType<S> for Box<T>
209where
210    T: IsOutputType<S> + ?Sized,
211    S: ScalarValue,
212{
213    #[inline]
214    fn mark() {
215        T::mark()
216    }
217}
218
219impl<S, T> IsOutputType<S> for Arc<T>
220where
221    T: IsOutputType<S> + ?Sized,
222    S: ScalarValue,
223{
224    #[inline]
225    fn mark() {
226        T::mark()
227    }
228}
229
230impl<S, T> IsOutputType<S> for Option<T>
231where
232    T: IsOutputType<S>,
233    S: ScalarValue,
234{
235    #[inline]
236    fn mark() {
237        T::mark()
238    }
239}
240
241impl<S, T> IsOutputType<S> for Vec<T>
242where
243    T: IsOutputType<S>,
244    S: ScalarValue,
245{
246    #[inline]
247    fn mark() {
248        T::mark()
249    }
250}
251
252impl<S, T> IsOutputType<S> for [T]
253where
254    T: IsOutputType<S>,
255    S: ScalarValue,
256{
257    #[inline]
258    fn mark() {
259        T::mark()
260    }
261}
262
263impl<S, T, const N: usize> IsOutputType<S> for [T; N]
264where
265    T: IsOutputType<S>,
266    S: ScalarValue,
267{
268    #[inline]
269    fn mark() {
270        T::mark()
271    }
272}
273
274impl<S> IsOutputType<S> for str where S: ScalarValue {}
275
276/// Marker trait for types which can be used as input types.
277///
278/// The GraphQL specification differentiates between input and output
279/// types. Each type which can be used as an input type should
280/// implement this trait. The specification defines enum, scalar, and
281/// input object input types.
282pub trait IsInputType<S: ScalarValue>: GraphQLType<S> {
283    /// An arbitrary function without meaning.
284    ///
285    /// May contain compile timed check logic which ensures that types
286    /// are used correctly according to the GraphQL specification.
287    fn mark() {}
288}
289
290impl<S, T> IsInputType<S> for &T
291where
292    T: IsInputType<S> + ?Sized,
293    S: ScalarValue,
294{
295    #[inline]
296    fn mark() {
297        T::mark()
298    }
299}
300
301impl<S, T> IsInputType<S> for Box<T>
302where
303    T: IsInputType<S> + ?Sized,
304    S: ScalarValue,
305{
306    #[inline]
307    fn mark() {
308        T::mark()
309    }
310}
311
312impl<S, T> IsInputType<S> for Arc<T>
313where
314    T: IsInputType<S> + ?Sized,
315    S: ScalarValue,
316{
317    #[inline]
318    fn mark() {
319        T::mark()
320    }
321}
322
323impl<S, T> IsInputType<S> for Option<T>
324where
325    T: IsInputType<S>,
326    S: ScalarValue,
327{
328    #[inline]
329    fn mark() {
330        T::mark()
331    }
332}
333
334impl<S, T> IsInputType<S> for Vec<T>
335where
336    T: IsInputType<S>,
337    S: ScalarValue,
338{
339    #[inline]
340    fn mark() {
341        T::mark()
342    }
343}
344
345impl<S, T> IsInputType<S> for [T]
346where
347    T: IsInputType<S>,
348    S: ScalarValue,
349{
350    #[inline]
351    fn mark() {
352        T::mark()
353    }
354}
355
356impl<S, T, const N: usize> IsInputType<S> for [T; N]
357where
358    T: IsInputType<S>,
359    S: ScalarValue,
360{
361    #[inline]
362    fn mark() {
363        T::mark()
364    }
365}
366
367impl<S> IsInputType<S> for str where S: ScalarValue {}