Expand description
§Features
- A (comparatively) low-level AST for GraphQL grammar,
and high-level representation of
Schema
andExecutableDocument
. - All three can be parsed (using
apollo-parser
internally), created or modified programatically, and serialized. - Validation of schemas and executable documents, as defined in the GraphQL specification.
- Execution of the schema introspection portion of queries.
§Getting started
Add the dependency to start using apollo-compiler
:
cargo add apollo-compiler
Or add this to your Cargo.toml
for a manual installation:
# Just an example, change to the necessary package version.
[dependencies]
apollo-compiler = "1.28.0"
§Rust versions
apollo-compiler
is tested on the latest stable version of Rust.
Older version may or may not be compatible.
§Usage
You can get started with apollo-compiler
:
use apollo_compiler::Schema;
use apollo_compiler::ExecutableDocument;
let sdl = r#"
type Query {
field: Int
}
"#;
let query = "{ field }";
/// In case of validation errors, the panic message will be nicely formatted
/// to point at relevant parts of the source file(s)
let schema = Schema::parse_and_validate(sdl, "sdl.graphql").unwrap();
let doc = ExecutableDocument::parse_and_validate(&schema, query, "query.graphql").unwrap();
§Examples
§Accessing fragment definition field types
use apollo_compiler::{Schema, ExecutableDocument, Node, executable};
let schema_input = r#"
type User {
id: ID
name: String
profilePic(size: Int): URL
}
schema { query: User }
scalar URL @specifiedBy(url: "https://tools.ietf.org/html/rfc3986")
"#;
let query_input = r#"
query getUser {
... vipCustomer
}
#fragment definition where we want to know the field types.
fragment vipCustomer on User {
id
name
profilePic(size: 50)
}
"#;
let schema = Schema::parse_and_validate(schema_input, "schema.graphql").unwrap();
let document = ExecutableDocument::parse_and_validate(&schema, query_input, "query.graphql")
.unwrap();
let op = document.operations.get(Some("getUser")).expect("getUser query does not exist");
let fragment_in_op = op.selection_set.selections.iter().filter_map(|sel| match sel {
executable::Selection::FragmentSpread(spread) => {
Some(document.fragments.get(&spread.fragment_name)?.as_ref())
}
_ => None
}).collect::<Vec<&executable::Fragment>>();
let fragment_fields = fragment_in_op.iter().flat_map(|frag| {
frag.selection_set.fields()
}).collect::<Vec<&Node<executable::Field>>>();
let field_ty = fragment_fields
.iter()
.map(|f| f.ty().inner_named_type().as_str())
.collect::<Vec<&str>>();
assert_eq!(field_ty, ["ID", "String", "URL"]);
§Get a directive defined on a field used in a query operation definition.
use apollo_compiler::{Schema, ExecutableDocument, Node, executable};
let schema_input = r#"
type Query {
topProducts: Product
}
type Product {
inStock: Boolean @join__field(graph: INVENTORY)
name: String @join__field(graph: PRODUCTS)
}
enum join__Graph {
INVENTORY,
PRODUCTS,
}
directive @join__field(graph: join__Graph) on FIELD_DEFINITION
"#;
let query_input = r#"
query getProduct {
topProducts {
inStock
}
}
"#;
let schema = Schema::parse_and_validate(schema_input, "schema.graphql").unwrap();
let document = ExecutableDocument::parse_and_validate(&schema, query_input, "query.graphql")
.unwrap();
let get_product_op = document
.operations
.get(Some("getProduct"))
.expect("getProduct query does not exist");
let in_stock_field = &get_product_op
.selection_set
.fields()
.find(|f| f.name == "topProducts")
.expect("topProducts field does not exist")
.selection_set
.fields()
.find(|f| f.name == "inStock")
.expect("inStock field does not exist")
.definition;
let in_stock_directive: Vec<_> = in_stock_field
.directives
.iter()
.map(|dir| &dir.name)
.collect();
assert_eq!(in_stock_directive, ["join__field"]);
§Printing diagnostics for a faulty GraphQL document
use apollo_compiler::parser::Parser;
let input = "{ ... }";
if let Err(diagnostics) = Parser::new().parse_mixed_validate(input, "document.graphql") {
println!("{diagnostics}")
}
§License
Licensed under either of
- Apache License, Version 2.0 (LICENSE-APACHE or https://www.apache.org/licenses/LICENSE-2.0)
- MIT license (LICENSE-MIT or https://opensource.org/licenses/MIT)
at your option.
Re-exports§
pub use self::executable::ExecutableDocument;
pub use self::schema::Schema;
Modules§
- ast
- Abstract Syntax Tree for GraphQL documents.
An AST
Document
is more permissive but lower-level thanSchema
orExecutableDocument
. - collections
- Type aliases for hashing-based collections configured with a specific hasher, as used in various places thorough the API
- coordinate
- Parsing and printing for schema coordinates as described in the RFC.
- diagnostic
- Pretty-printable diagnostic reports for errors that reference GraphQL documents.
- executable
- High-level representation of an executable document, which can contain operations and fragments.
- introspection
- Execution engine for the schema introspection portion of a query
- parser
- APIs related to parsing
&str
inputs as GraphQL syntax. - request
- GraphQL requests
- response
- GraphQL responses
- schema
- High-level representation of a GraphQL type system document a.k.a. schema.
- validation
- Supporting APIs for GraphQL validation and other kinds of errors.
Macros§
- coord
- Create a
DirectiveCoordinate
,DirectiveArgumentCoordinate
,TypeCoordinate
,TypeAttributeCoordinate
, orFieldArgumentCoordinate
at compile time. - name
- Create a
Name
from a string literal or identifier, checked for validity at compile time. - ty
- Create a static
Type
with GraphQL-like syntax
Structs§
- Invalid
Name Error - Tried to create a
Name
from a string that is not in valid GraphQL name syntax. - Name
- A GraphQL Name identifier
- Node
- A thread-safe reference-counted smart pointer for GraphQL nodes.