graphql_federated_graph/directives/
complexity_control.rs

1use cynic_parser_deser::ValueDeserialize;
2
3#[derive(ValueDeserialize)]
4pub struct CostDirective {
5    pub weight: i32,
6}
7
8impl CostDirective {
9    pub fn definition() -> &'static str {
10        indoc::indoc! {r#"
11            directive @cost(weight: Int!) on
12                ARGUMENT_DEFINITION
13              | ENUM
14              | FIELD_DEFINITION
15              | INPUT_FIELD_DEFINITION
16              | OBJECT
17              | SCALAR
18        "#}
19    }
20}
21
22#[derive(ValueDeserialize, PartialEq, PartialOrd, Clone, Debug)]
23#[deser(rename_all = "camelCase", default)]
24pub struct ListSizeDirective {
25    pub assumed_size: Option<u32>,
26    pub slicing_arguments: Vec<String>,
27    pub sized_fields: Vec<String>,
28    #[deser(default = true)]
29    pub require_one_slicing_argument: bool,
30}
31
32impl ListSizeDirective {
33    pub fn definition() -> &'static str {
34        indoc::indoc! {r#"
35            directive @listSize(
36              assumedSize: Int,
37              slicingArguments: [String!],
38              sizedFields: [String!],
39              requireOneSlicingArgument: Boolean = true
40            ) on FIELD_DEFINITION
41        "#}
42    }
43
44    pub fn merge(self, other: ListSizeDirective) -> Self {
45        let mut slicing_arguments = self.slicing_arguments;
46        slicing_arguments.extend(other.slicing_arguments);
47
48        let mut sized_fields = self.sized_fields;
49        sized_fields.extend(other.sized_fields);
50
51        ListSizeDirective {
52            assumed_size: match (self.assumed_size, other.assumed_size) {
53                (Some(lhs), Some(rhs)) => Some(std::cmp::max(lhs, rhs)),
54                (lhs, rhs) => lhs.or(rhs),
55            },
56            slicing_arguments,
57            sized_fields,
58            require_one_slicing_argument: self.require_one_slicing_argument || other.require_one_slicing_argument,
59        }
60    }
61}
62
63#[cfg(test)]
64mod tests {
65    use super::*;
66    use crate::directives::parse_directive;
67
68    #[test]
69    fn test_parsing_cost() {
70        let value = parse_directive::<CostDirective>("@cost(weight: 1)").unwrap();
71
72        assert_eq!(value.weight, 1);
73    }
74}