Repository: apollographql/apollo-rs (rust)

Issue:
validation: root operation type should be of Object Type
from conversation in https://github.com/apollographql/apollo-rs/pull/415#issuecomment-1380047832

we should validate operation type to be of object type, for example:

```graphql
schema {
  query: SomeInputType
}

input SomeInputType {
  name: String
}

type ShouldBeTheQuery {
  name: String
}
```

Pull request:
feat(compiler): validate root operation type is of Object Type
closes #418

Patch:
diff --git a/crates/apollo-compiler/src/database/hir.rs b/crates/apollo-compiler/src/database/hir.rs
index 6018376..f360146 100644
--- a/crates/apollo-compiler/src/database/hir.rs
+++ b/crates/apollo-compiler/src/database/hir.rs
@@ -141,6 +141,53 @@ impl TypeDefinition {
             Self::ScalarTypeDefinition(def) => def.loc(),
         }
     }
+    /// Returns `true` if the type definition is [`ScalarTypeDefinition`].
+    ///
+    /// [`ScalarTypeDefinition`]: TypeDefinition::ScalarTypeDefinition
+    #[must_use]
+    pub fn is_scalar_type_definition(&self) -> bool {
+        matches!(self, Self::ScalarTypeDefinition(..))
+    }
+
+    /// Returns `true` if the type definition is [`ObjectTypeDefinition`].
+    ///
+    /// [`ObjectTypeDefinition`]: TypeDefinition::ObjectTypeDefinition
+    #[must_use]
+    pub fn is_object_type_definition(&self) -> bool {
+        matches!(self, Self::ObjectTypeDefinition(..))
+    }
+
+    /// Returns `true` if the type definition is [`InterfaceTypeDefinition`].
+    ///
+    /// [`InterfaceTypeDefinition`]: TypeDefinition::InterfaceTypeDefinition
+    #[must_use]
+    pub fn is_interface_type_definition(&self) -> bool {
+        matches!(self, Self::InterfaceTypeDefinition(..))
+    }
+
+    /// Returns `true` if the type definition is [`UnionTypeDefinition`].
+    ///
+    /// [`UnionTypeDefinition`]: TypeDefinition::UnionTypeDefinition
+    #[must_use]
+    pub fn is_union_type_definition(&self) -> bool {
+        matches!(self, Self::UnionTypeDefinition(..))
+    }
+
+    /// Returns `true` if the type definition is [`EnumTypeDefinition`].
+    ///
+    /// [`EnumTypeDefinition`]: TypeDefinition::EnumTypeDefinition
+    #[must_use]
+    pub fn is_enum_type_definition(&self) -> bool {
+        matches!(self, Self::EnumTypeDefinition(..))
+    }
+
+    /// Returns `true` if the type definition is [`InputObjectTypeDefinition`].
+    ///
+    /// [`InputObjectTypeDefinition`]: TypeDefinition::InputObjectTypeDefinition
+    #[must_use]
+    pub fn is_input_object_type_definition(&self) -> bool {
+        matches!(self, Self::InputObjectTypeDefinition(..))
+    }
 }
 
 #[derive(Clone, Debug, Hash, PartialEq, Eq)]
diff --git a/crates/apollo-compiler/src/database/hir_db.rs b/crates/apollo-compiler/src/database/hir_db.rs
index 7b035ce..af797bf 100644
--- a/crates/apollo-compiler/src/database/hir_db.rs
+++ b/crates/apollo-compiler/src/database/hir_db.rs
@@ -1004,15 +1004,19 @@ fn root_operation_type_definition(
     let type_defs: Vec<RootOperationTypeDefinition> = root_type_def
         .into_iter()
         .filter_map(|ty| {
-            let operation_type = operation_type(ty.operation_type());
-            let named_type = named_type(ty.named_type()?.name()?, file_id);
-            let loc = location(file_id, ty.syntax());
+            if let Some(named_ty) = ty.named_type() {
+                let operation_type = operation_type(ty.operation_type());
+                let named_type = named_type(named_ty.name()?, file_id);
+                let loc = location(file_id, ty.syntax());
 
-            Some(RootOperationTypeDefinition {
-                operation_ty: operation_type,
-                named_type,
-                loc: Some(loc),
-            })
+                Some(RootOperationTypeDefinition {
+                    operation_ty: operation_type,
+                    named_type,
+                    loc: Some(loc),
+                })
+            } else {
+                None
+            }
         })
         .collect();
 
diff --git a/crates/apollo-compiler/src/diagnostics.rs b/crates/apollo-compiler/src/diagnostics.rs
index a458ae7..0768158 100644
--- a/crates/apollo-compiler/src/diagnostics.rs
+++ b/crates/apollo-compiler/src/diagnostics.rs
@@ -235,7 +235,7 @@ pub enum DiagnosticData {
     BuiltInScalarDefinition,
     #[error("unused variable: `{name}`")]
     UnusedVariable { name: String },
-    #[error("`{name}` field must return an output type")]
+    #[error("`{name}` field must return an object type")]
     ObjectType {
         // union member
         name: String,
@@ -301,6 +301,3 @@ impl ApolloDiagnostic {
         builder.finish()
     }
 }
-
-/* Stash: new diagnostic
-*/
diff --git a/crates/apollo-compiler/src/validation/0062_root_operation_with_list_type.graphql b/crates/apollo-compiler/src/validation/0062_root_operation_with_list_type.graphql
new file mode 100644
index 0000000..c610245
--- /dev/null
+++ b/crates/apollo-compiler/src/validation/0062_root_operation_with_list_type.graphql
@@ -0,0 +1,6 @@
+schema {
+  query: [Object]
+}
+type Object {
+  field: Int
+}
\ No newline at end of file
diff --git a/crates/apollo-compiler/src/validation/schema.rs b/crates/apollo-compiler/src/validation/schema.rs
index 01ff332..b06f144 100644
--- a/crates/apollo-compiler/src/validation/schema.rs
+++ b/crates/apollo-compiler/src/validation/schema.rs
@@ -1,8 +1,8 @@
 use std::{collections::HashMap, sync::Arc};
 
 use crate::{
-    diagnostics::{ApolloDiagnostic, DiagnosticData, Label},
-    hir, ValidationDatabase,
+    diagnostics::{DiagnosticData, Label},
+    hir, ApolloDiagnostic, ValidationDatabase,
 };
 
 pub fn validate_schema_definition(
@@ -50,6 +50,10 @@ pub fn validate_root_operation_definitions(
 
     for op_type in root_op_defs.iter() {
         let name = op_type.named_type().name();
+
+        // All root operations in a schema definition must be unique.
+        //
+        // Return a Unique Operation Definition error in case of a duplicate name.
         if let Some(prev_def) = seen.get(&name) {
             if let (Some(original_definition), Some(redefined_definition)) =
                 (prev_def.loc(), op_type.loc())
@@ -80,6 +84,41 @@ pub fn validate_root_operation_definitions(
         } else {
             seen.insert(name, op_type);
         }
+
+        // Root Operation Named Type must be of Object Type.
+        //
+        // Return a Object Type error if it's any other type definition.
+        let type_def = db.find_type_definition_by_name(op_type.named_type().name());
+        if let Some(type_def) = type_def {
+            if !type_def.is_object_type_definition() {
+                if let Some(op_loc) = op_type.loc() {
+                    let kind = type_def.kind();
+                    diagnostics.push(
+                        ApolloDiagnostic::new(
+                            db,
+                            op_loc.into(),
+                            DiagnosticData::ObjectType {
+                                name: op_type.named_type().name(),
+                                ty: kind,
+                            },
+                        )
+                        .label(Label::new(op_loc, format!("This is of `{kind}` type")))
+                        .help("root operation type must be of an Object Type"),
+                    );
+                }
+            }
+        } else if let Some(op_loc) = op_type.loc() {
+            diagnostics.push(
+                ApolloDiagnostic::new(
+                    db,
+                    op_loc.into(),
+                    DiagnosticData::UndefinedDefinition {
+                        name: op_type.named_type().name(),
+                    },
+                )
+                .label(Label::new(op_loc, "not found in this scope")),
+            );
+        }
     }
 
     diagnostics
diff --git a/crates/apollo-parser/src/parser/grammar/name.rs b/crates/apollo-parser/src/parser/grammar/name.rs
index b0ae738..fd43c05 100644
--- a/crates/apollo-parser/src/parser/grammar/name.rs
+++ b/crates/apollo-parser/src/parser/grammar/name.rs
@@ -5,9 +5,9 @@ use crate::{Parser, SyntaxKind, TokenKind, S};
 /// *Name*:
 ///     [_A-Za-z][_0-9A-Za-z]
 pub(crate) fn name(p: &mut Parser) {
-    let _g = p.start_node(SyntaxKind::NAME);
     match p.peek() {
         Some(TokenKind::Name) => {
+            let _g = p.start_node(SyntaxKind::NAME);
             validate_name(&p.peek_data().unwrap(), p);
             p.bump(SyntaxKind::IDENT);
         }
diff --git a/crates/apollo-parser/src/parser/grammar/ty.rs b/crates/apollo-parser/src/parser/grammar/ty.rs
index 4e4d889..f57f0df 100644
--- a/crates/apollo-parser/src/parser/grammar/ty.rs
+++ b/crates/apollo-parser/src/parser/grammar/ty.rs
@@ -79,8 +79,10 @@ fn parse(p: &mut Parser) -> Result<(), Token> {
 /// *NamedType*:
 ///     Name
 pub(crate) fn named_type(p: &mut Parser) {
-    let _g = p.start_node(SyntaxKind::NAMED_TYPE);
-    name::name(p);
+    if let Some(TokenKind::Name) = p.peek() {
+        let _g = p.start_node(SyntaxKind::NAMED_TYPE);
+        name::name(p);
+    }
 }
 
 #[cfg(test)]


Test patch:
diff --git a/crates/apollo-compiler/test_data/diagnostics/0059_root_operation_object_type.graphql b/crates/apollo-compiler/test_data/diagnostics/0059_root_operation_object_type.graphql
new file mode 100644
index 0000000..7ffa232
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0059_root_operation_object_type.graphql
@@ -0,0 +1,11 @@
+schema {
+    query: SomeInterface 
+}
+
+interface SomeInterface {
+    name: String
+}
+
+type ShouldBeTheQuery {
+    name: String
+}
\ No newline at end of file
diff --git a/crates/apollo-compiler/test_data/diagnostics/0059_root_operation_object_type.txt b/crates/apollo-compiler/test_data/diagnostics/0059_root_operation_object_type.txt
new file mode 100644
index 0000000..8d5c287
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0059_root_operation_object_type.txt
@@ -0,0 +1,59 @@
+[
+    ApolloDiagnostic {
+        cache: {
+            59: "0059_root_operation_object_type.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 59,
+            },
+            offset: 0,
+            length: 36,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 59,
+                    },
+                    offset: 0,
+                    length: 36,
+                },
+                text: "`query` root operation type must be defined here",
+            },
+        ],
+        help: None,
+        data: QueryRootOperationType,
+    },
+    ApolloDiagnostic {
+        cache: {
+            59: "0059_root_operation_object_type.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 59,
+            },
+            offset: 13,
+            length: 20,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 59,
+                    },
+                    offset: 13,
+                    length: 20,
+                },
+                text: "This is of `InterfaceTypeDefinition` type",
+            },
+        ],
+        help: Some(
+            "root operation type must be of an Object Type",
+        ),
+        data: ObjectType {
+            name: "SomeInterface",
+            ty: "InterfaceTypeDefinition",
+        },
+    },
+]
diff --git a/crates/apollo-compiler/test_data/diagnostics/0060_root_operation_definition_undefined_operation_type.graphql b/crates/apollo-compiler/test_data/diagnostics/0060_root_operation_definition_undefined_operation_type.graphql
new file mode 100644
index 0000000..ac711fd
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0060_root_operation_definition_undefined_operation_type.graphql
@@ -0,0 +1,7 @@
+schema {
+    query: SomeQuery
+}
+
+type ShouldBeTheQuery {
+    name: String
+}
\ No newline at end of file
diff --git a/crates/apollo-compiler/test_data/diagnostics/0060_root_operation_definition_undefined_operation_type.txt b/crates/apollo-compiler/test_data/diagnostics/0060_root_operation_definition_undefined_operation_type.txt
new file mode 100644
index 0000000..2b898d8
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0060_root_operation_definition_undefined_operation_type.txt
@@ -0,0 +1,56 @@
+[
+    ApolloDiagnostic {
+        cache: {
+            60: "0060_root_operation_definition_undefined_operation_type.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 60,
+            },
+            offset: 0,
+            length: 31,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 60,
+                    },
+                    offset: 0,
+                    length: 31,
+                },
+                text: "`query` root operation type must be defined here",
+            },
+        ],
+        help: None,
+        data: QueryRootOperationType,
+    },
+    ApolloDiagnostic {
+        cache: {
+            60: "0060_root_operation_definition_undefined_operation_type.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 60,
+            },
+            offset: 13,
+            length: 16,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 60,
+                    },
+                    offset: 13,
+                    length: 16,
+                },
+                text: "not found in this scope",
+            },
+        ],
+        help: None,
+        data: UndefinedDefinition {
+            name: "SomeQuery",
+        },
+    },
+]
diff --git a/crates/apollo-compiler/test_data/diagnostics/0061_root_operation_with_default_undefined_query.graphql b/crates/apollo-compiler/test_data/diagnostics/0061_root_operation_with_default_undefined_query.graphql
new file mode 100644
index 0000000..b521ecb
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0061_root_operation_with_default_undefined_query.graphql
@@ -0,0 +1,3 @@
+schema {
+    query: Query
+}
\ No newline at end of file
diff --git a/crates/apollo-compiler/test_data/diagnostics/0061_root_operation_with_default_undefined_query.txt b/crates/apollo-compiler/test_data/diagnostics/0061_root_operation_with_default_undefined_query.txt
new file mode 100644
index 0000000..8240619
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0061_root_operation_with_default_undefined_query.txt
@@ -0,0 +1,56 @@
+[
+    ApolloDiagnostic {
+        cache: {
+            61: "0061_root_operation_with_default_undefined_query.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 61,
+            },
+            offset: 0,
+            length: 27,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 61,
+                    },
+                    offset: 0,
+                    length: 27,
+                },
+                text: "`query` root operation type must be defined here",
+            },
+        ],
+        help: None,
+        data: QueryRootOperationType,
+    },
+    ApolloDiagnostic {
+        cache: {
+            61: "0061_root_operation_with_default_undefined_query.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 61,
+            },
+            offset: 13,
+            length: 12,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 61,
+                    },
+                    offset: 13,
+                    length: 12,
+                },
+                text: "not found in this scope",
+            },
+        ],
+        help: None,
+        data: UndefinedDefinition {
+            name: "Query",
+        },
+    },
+]
diff --git a/crates/apollo-compiler/test_data/diagnostics/0062_root_operation_with_list.graphql b/crates/apollo-compiler/test_data/diagnostics/0062_root_operation_with_list.graphql
new file mode 100644
index 0000000..c610245
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0062_root_operation_with_list.graphql
@@ -0,0 +1,6 @@
+schema {
+  query: [Object]
+}
+type Object {
+  field: Int
+}
\ No newline at end of file
diff --git a/crates/apollo-compiler/test_data/diagnostics/0062_root_operation_with_list.txt b/crates/apollo-compiler/test_data/diagnostics/0062_root_operation_with_list.txt
new file mode 100644
index 0000000..4abab10
--- /dev/null
+++ b/crates/apollo-compiler/test_data/diagnostics/0062_root_operation_with_list.txt
@@ -0,0 +1,168 @@
+[
+    ApolloDiagnostic {
+        cache: {
+            62: "0062_root_operation_with_list.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 62,
+            },
+            offset: 18,
+            length: 1,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 62,
+                    },
+                    offset: 18,
+                    length: 1,
+                },
+                text: "expected R_CURLY, got [",
+            },
+        ],
+        help: None,
+        data: SyntaxError {
+            message: "expected R_CURLY, got [",
+        },
+    },
+    ApolloDiagnostic {
+        cache: {
+            62: "0062_root_operation_with_list.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 62,
+            },
+            offset: 18,
+            length: 1,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 62,
+                    },
+                    offset: 18,
+                    length: 1,
+                },
+                text: "expected a StringValue, Name or OperationDefinition",
+            },
+        ],
+        help: None,
+        data: SyntaxError {
+            message: "expected a StringValue, Name or OperationDefinition",
+        },
+    },
+    ApolloDiagnostic {
+        cache: {
+            62: "0062_root_operation_with_list.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 62,
+            },
+            offset: 19,
+            length: 6,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 62,
+                    },
+                    offset: 19,
+                    length: 6,
+                },
+                text: "expected definition",
+            },
+        ],
+        help: None,
+        data: SyntaxError {
+            message: "expected definition",
+        },
+    },
+    ApolloDiagnostic {
+        cache: {
+            62: "0062_root_operation_with_list.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 62,
+            },
+            offset: 25,
+            length: 1,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 62,
+                    },
+                    offset: 25,
+                    length: 1,
+                },
+                text: "expected a StringValue, Name or OperationDefinition",
+            },
+        ],
+        help: None,
+        data: SyntaxError {
+            message: "expected a StringValue, Name or OperationDefinition",
+        },
+    },
+    ApolloDiagnostic {
+        cache: {
+            62: "0062_root_operation_with_list.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 62,
+            },
+            offset: 27,
+            length: 1,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 62,
+                    },
+                    offset: 27,
+                    length: 1,
+                },
+                text: "expected a StringValue, Name or OperationDefinition",
+            },
+        ],
+        help: None,
+        data: SyntaxError {
+            message: "expected a StringValue, Name or OperationDefinition",
+        },
+    },
+    ApolloDiagnostic {
+        cache: {
+            62: "0062_root_operation_with_list.graphql",
+        },
+        location: DiagnosticLocation {
+            file_id: FileId {
+                id: 62,
+            },
+            offset: 0,
+            length: 17,
+        },
+        labels: [
+            Label {
+                location: DiagnosticLocation {
+                    file_id: FileId {
+                        id: 62,
+                    },
+                    offset: 0,
+                    length: 17,
+                },
+                text: "`query` root operation type must be defined here",
+            },
+        ],
+        help: None,
+        data: QueryRootOperationType,
+    },
+]
diff --git a/crates/apollo-compiler/test_data/ok/0014_float_values.graphql b/crates/apollo-compiler/test_data/ok/0014_float_values.graphql
index c7291af..6701378 100644
--- a/crates/apollo-compiler/test_data/ok/0014_float_values.graphql
+++ b/crates/apollo-compiler/test_data/ok/0014_float_values.graphql
@@ -1,3 +1,7 @@
+type Query {
+  name(arg: WithAllKindsOfFloats): String
+}
+
 input WithAllKindsOfFloats {
   a_regular_float: Float = 1.2
   an_integer_float: Float = 1234
diff --git a/crates/apollo-compiler/test_data/ok/0014_float_values.txt b/crates/apollo-compiler/test_data/ok/0014_float_values.txt
index 3b5d54b..3bff293 100644
--- a/crates/apollo-compiler/test_data/ok/0014_float_values.txt
+++ b/crates/apollo-compiler/test_data/ok/0014_float_values.txt
@@ -1,87 +1,118 @@
-- DOCUMENT@0..214
-    - INPUT_OBJECT_TYPE_DEFINITION@0..213
-        - input_KW@0..5 "input"
-        - WHITESPACE@5..6 " "
-        - NAME@6..26
-            - IDENT@6..26 "WithAllKindsOfFloats"
-        - WHITESPACE@26..27 " "
-        - INPUT_FIELDS_DEFINITION@27..213
-            - L_CURLY@27..28 "{"
-            - WHITESPACE@28..31 "\n  "
-            - INPUT_VALUE_DEFINITION@31..59
-                - NAME@31..46
-                    - IDENT@31..46 "a_regular_float"
+- DOCUMENT@0..272
+    - OBJECT_TYPE_DEFINITION@0..56
+        - type_KW@0..4 "type"
+        - WHITESPACE@4..5 " "
+        - NAME@5..10
+            - IDENT@5..10 "Query"
+        - WHITESPACE@10..11 " "
+        - FIELDS_DEFINITION@11..56
+            - L_CURLY@11..12 "{"
+            - WHITESPACE@12..15 "\n  "
+            - FIELD_DEFINITION@15..54
+                - NAME@15..19
+                    - IDENT@15..19 "name"
+                - ARGUMENTS_DEFINITION@19..46
+                    - L_PAREN@19..20 "("
+                    - INPUT_VALUE_DEFINITION@20..45
+                        - NAME@20..23
+                            - IDENT@20..23 "arg"
+                        - COLON@23..24 ":"
+                        - WHITESPACE@24..25 " "
+                        - NAMED_TYPE@25..45
+                            - NAME@25..45
+                                - IDENT@25..45 "WithAllKindsOfFloats"
+                    - R_PAREN@45..46 ")"
                 - COLON@46..47 ":"
                 - WHITESPACE@47..48 " "
-                - NAMED_TYPE@48..53
-                    - NAME@48..53
-                        - IDENT@48..53 "Float"
-                - WHITESPACE@53..54 " "
-                - DEFAULT_VALUE@54..59
-                    - EQ@54..55 "="
-                    - WHITESPACE@55..56 " "
-                    - FLOAT_VALUE@56..59
-                        - FLOAT@56..59 "1.2"
-            - WHITESPACE@59..62 "\n  "
-            - INPUT_VALUE_DEFINITION@62..92
-                - NAME@62..78
-                    - IDENT@62..78 "an_integer_float"
-                - COLON@78..79 ":"
-                - WHITESPACE@79..80 " "
-                - NAMED_TYPE@80..85
-                    - NAME@80..85
-                        - IDENT@80..85 "Float"
-                - WHITESPACE@85..86 " "
-                - DEFAULT_VALUE@86..92
-                    - EQ@86..87 "="
-                    - WHITESPACE@87..88 " "
-                    - INT_VALUE@88..92
-                        - INT@88..92 "1234"
-            - WHITESPACE@92..95 "\n  "
-            - INPUT_VALUE_DEFINITION@95..145
-                - NAME@95..125
-                    - IDENT@95..125 "a_float_that_doesnt_fit_an_int"
-                - COLON@125..126 ":"
-                - WHITESPACE@126..127 " "
-                - NAMED_TYPE@127..132
-                    - NAME@127..132
-                        - IDENT@127..132 "Float"
-                - WHITESPACE@132..133 " "
-                - DEFAULT_VALUE@133..145
-                    - EQ@133..134 "="
-                    - WHITESPACE@134..135 " "
-                    - INT_VALUE@135..145
-                        - INT@135..145 "9876543210"
-            - WHITESPACE@145..148 "\n  "
-            - INPUT_VALUE_DEFINITION@148..211
-                - NAME@148..162
-                    - IDENT@148..162 "list_of_floats"
-                - COLON@162..163 ":"
-                - WHITESPACE@163..164 " "
-                - LIST_TYPE@164..171
-                    - L_BRACK@164..165 "["
-                    - NAMED_TYPE@165..170
-                        - NAME@165..170
-                            - IDENT@165..170 "Float"
-                    - R_BRACK@170..171 "]"
-                - WHITESPACE@171..172 " "
-                - DEFAULT_VALUE@172..211
-                    - EQ@172..173 "="
-                    - WHITESPACE@173..174 " "
-                    - LIST_VALUE@174..211
-                        - L_BRACK@174..175 "["
-                        - INT_VALUE@175..176
-                            - INT@175..176 "4"
-                        - COMMA@176..177 ","
-                        - WHITESPACE@177..178 " "
-                        - INT_VALUE@178..188
-                            - INT@178..188 "9876543210"
-                        - COMMA@188..189 ","
-                        - WHITESPACE@189..190 " "
-                        - INT_VALUE@190..210
-                            - INT@190..210 "98765432109876543210"
-                        - R_BRACK@210..211 "]"
-            - WHITESPACE@211..212 "\n"
-            - R_CURLY@212..213 "}"
-    - WHITESPACE@213..214 "\n"
+                - NAMED_TYPE@48..54
+                    - NAME@48..54
+                        - IDENT@48..54 "String"
+            - WHITESPACE@54..55 "\n"
+            - R_CURLY@55..56 "}"
+    - WHITESPACE@56..58 "\n\n"
+    - INPUT_OBJECT_TYPE_DEFINITION@58..271
+        - input_KW@58..63 "input"
+        - WHITESPACE@63..64 " "
+        - NAME@64..84
+            - IDENT@64..84 "WithAllKindsOfFloats"
+        - WHITESPACE@84..85 " "
+        - INPUT_FIELDS_DEFINITION@85..271
+            - L_CURLY@85..86 "{"
+            - WHITESPACE@86..89 "\n  "
+            - INPUT_VALUE_DEFINITION@89..117
+                - NAME@89..104
+                    - IDENT@89..104 "a_regular_float"
+                - COLON@104..105 ":"
+                - WHITESPACE@105..106 " "
+                - NAMED_TYPE@106..111
+                    - NAME@106..111
+                        - IDENT@106..111 "Float"
+                - WHITESPACE@111..112 " "
+                - DEFAULT_VALUE@112..117
+                    - EQ@112..113 "="
+                    - WHITESPACE@113..114 " "
+                    - FLOAT_VALUE@114..117
+                        - FLOAT@114..117 "1.2"
+            - WHITESPACE@117..120 "\n  "
+            - INPUT_VALUE_DEFINITION@120..150
+                - NAME@120..136
+                    - IDENT@120..136 "an_integer_float"
+                - COLON@136..137 ":"
+                - WHITESPACE@137..138 " "
+                - NAMED_TYPE@138..143
+                    - NAME@138..143
+                        - IDENT@138..143 "Float"
+                - WHITESPACE@143..144 " "
+                - DEFAULT_VALUE@144..150
+                    - EQ@144..145 "="
+                    - WHITESPACE@145..146 " "
+                    - INT_VALUE@146..150
+                        - INT@146..150 "1234"
+            - WHITESPACE@150..153 "\n  "
+            - INPUT_VALUE_DEFINITION@153..203
+                - NAME@153..183
+                    - IDENT@153..183 "a_float_that_doesnt_fit_an_int"
+                - COLON@183..184 ":"
+                - WHITESPACE@184..185 " "
+                - NAMED_TYPE@185..190
+                    - NAME@185..190
+                        - IDENT@185..190 "Float"
+                - WHITESPACE@190..191 " "
+                - DEFAULT_VALUE@191..203
+                    - EQ@191..192 "="
+                    - WHITESPACE@192..193 " "
+                    - INT_VALUE@193..203
+                        - INT@193..203 "9876543210"
+            - WHITESPACE@203..206 "\n  "
+            - INPUT_VALUE_DEFINITION@206..269
+                - NAME@206..220
+                    - IDENT@206..220 "list_of_floats"
+                - COLON@220..221 ":"
+                - WHITESPACE@221..222 " "
+                - LIST_TYPE@222..229
+                    - L_BRACK@222..223 "["
+                    - NAMED_TYPE@223..228
+                        - NAME@223..228
+                            - IDENT@223..228 "Float"
+                    - R_BRACK@228..229 "]"
+                - WHITESPACE@229..230 " "
+                - DEFAULT_VALUE@230..269
+                    - EQ@230..231 "="
+                    - WHITESPACE@231..232 " "
+                    - LIST_VALUE@232..269
+                        - L_BRACK@232..233 "["
+                        - INT_VALUE@233..234
+                            - INT@233..234 "4"
+                        - COMMA@234..235 ","
+                        - WHITESPACE@235..236 " "
+                        - INT_VALUE@236..246
+                            - INT@236..246 "9876543210"
+                        - COMMA@246..247 ","
+                        - WHITESPACE@247..248 " "
+                        - INT_VALUE@248..268
+                            - INT@248..268 "98765432109876543210"
+                        - R_BRACK@268..269 "]"
+            - WHITESPACE@269..270 "\n"
+            - R_CURLY@270..271 "}"
+    - WHITESPACE@271..272 "\n"
 recursion limit: 4096, high: 0