A Julia GraphQL client for seamless integration with a server
This package is intended to make connecting to and communicating with GraphQL servers easy whilst integrating easily with the wider Julia ecosystem.
- Querying, mutating and subscribing without manual writing of query strings
@gql_str
non-standard string literal which which validates a query string at compile time- Deserializing responses directly using StructTypes
- Type stable querying
- Construction of Julia types from GraphQL objects
- Using introspection to help with querying
The package can be installed with Julia's package manager,
either by using the Pkg REPL mode (press ]
to enter):
pkg> add GraphQLClient
or by using Pkg functions
julia> using Pkg; Pkg.add("GraphQLClient")
A client can be instantiated by using the Client
type
using GraphQLClient
client = Client("https://countries.trevorblades.com")
This will, by default, use a query to introspect the server schema.
We can also set a global client to be user by queries, mutations, subscriptions and introspection functions.
global_graphql_client(Client("https://countries.trevorblades.com"))
We can query a client
without having to type a full GraphQL query by hand, with the response containing fields obtained by introspection
response = query(client, "countries")
Or we can query the global client
response = query("countries")
We can add arguments and specify fields in the response
query_args = Dict("filter" => Dict("code" => Dict("eq" => "AU")))
response = query("countries"; query_args=query_args, output_fields="name");
response.data["countries"]
# 1-element Vector{Any}:
# Dict{String, Any}("name" => "Australia")
Or we can query with the query string directly using either a normal String
or the gql
non-standard string literal which also performs some validation of the string:
query_string = gql"""
query(
$eq: String
){
countries(
filter:{
code:{
eq:$eq
}
}
){
name
}
}
"""
variables = Dict("eq" => "AU")
response = GraphQLClient.execute(query_string, variables=variables)
We can define a StructType
to deserialise the result into
using StructTypes
struct CountryName
name::String
end
StructTypes.StructType(::Type{CountryName}) = StructTypes.OrderedStruct()
response = query("countries", Vector{CountryName}, query_args=query_args, output_fields="name")
response.data["countries"][1]
# CountryName("Australia")
Or we can use introspection to build the type automatically
Country = GraphQLClient.introspect_object("Country")
response = query("countries", Vector{Country}, query_args=query_args, output_fields="name")
response.data["countries"][1]
# Country
# name : Australia
Mutations can be constructed in a similar way, except the arguments are not a keyword argument as typically a mutation is doing something with an input. For example
response = mutate(client, "mutation_name", Dict("new_id" => 1))
response = mutate("mutation_name", Dict("new_id" => 1)) # Use global client
The subscriptions syntax is similar, except that we use Julia's do
notation
open_subscription(
client,
"subscription_name",
sub_args=("id" => 1),
output_fields="val"
) do response
val = response.data["subscription_name"]["val"]
stop_sub = val == 2
return stop_sub # If this is true, the subscription ends
end