Basics of GraphQL with SpringBoot
Pre requisite: Basic knowledge of Java with Spring Boot and JPA to create REST based APIs.
As per the official documentation,
"GraphQL is a query language for APIs and a runtime for fulfilling those queries with your existing data. GraphQL provides a complete and understandable description of the data in your API, gives clients the power to ask for exactly what they need and nothing more, makes it easier to evolve APIs over time, and enables powerful developer tools."
In simple words,
"GraphQL is the better REST. It lets user send a JSON formatted request to the server, it resolves and returns back the exact same JSON as response. There is no under or over information."
Here, we requested data from the server in the given format (left hand side) and it returns back response in the same format (right hand side).
GraphQL lets us perform three types of operations:
Query: Queries are used by clients to request the data it needs from the server.
Mutation: Mutation lets the clients perform Create/Update/Delete operations with the API.
Subscription: Subscriptions lets the client subscribe to a particular event and get real time information.
In this article, we'll look into Query and Mutation.
To perform API operations (Query/Mutation) GraphQL uses a Schema Definition Language (SDL). It’s a language with very simple syntax that allows to define a schema. Here, we have defined a schema to query Books and Authors.
- We have defined 2 simple types, Book and Author.
- Then we defined different query operations to get the required results. Like:
- allBooks: [Book] - query returns us a list of type Book.
- [<type>] returns a list of the given type.
- book(id: ID): Book - returns type Book with the provided ID.
- Same for author, see the screenshot above of request/response to get a better idea of how queries are used.
Also, a sample of schema for mutation.
We have defined one input Author and one Type Book
Then we defined different mutation operations like:
addBook: Book - This takes a bunch of inputs like title, publisher and returns response of type Book.
updateBook: Book - returns type Book after updating the details of book with given bookId.
Same can be done for author.
We can combine both the query and Mutation schema, please see here.
We need to put the GraphQL schema in resources folder of our project as shown below
Let's start with the demo for better understanding. For this article we will be making the backend of a Book-Author API. We have used Java 8, SpringBoot 2. For a complete list of tech stack see here.
First we need to define our model of Book and Author.
After defining the models we need to create a controller for our Rest.
We have used a POJO "Data" to hold the requested String and used it with @RequestBody.
- We have also used a GraphQL instance to execute the query request from consumer. We'll see how to create a GraphQL instance below.
In the service class we have created a GraphQL instance and loaded the schema file. We used TypeDefinitionRegistry (of GraphQL) to register the schema definition. Then we used RuntimeWiring of GraphQL to build a new type wiring with data fetchers mapped to their respective classes.
We have created two RuntimeWiring one for "Query" and other for "Mutation". We have mapped the fieldName allBooks(same name as in Schema) to the class that will handle the request for that particular query. Similarly, we have mapped fieldName addBook to the SaveBook class for mutation.
After this we need to define our DataFetcher classes. We'll look into BookDataFetcher class that implements the get method of DataFetcher interface provided by GraphQL. We can get all the requested arguments (in our case it's just "id" but it gives a map having all arguments) from parameter dataFetchingEnvironment of get method. Then we fire JPA queries to get the required data from DB.
For Mutation, we'll look into the SaveBook class.
Here, we got all the arguments from dataFetchingEnvironment parameter (it returns a Map) and used the save method of JPA to add author and book respectively.
Once this is done, we can start our spring boot application and hit https://localhost:<port>/api/graphql on any API testing tool (I am using Insomnia) and send the below request. Replace the id with one present in your DB (https://localhost:<port>/h2).
{ book(id: "<Id>"){ title } }
mutation { addBook( title: "Meluha", publisher: "Amish", authors: [{ authorName: "Amish" age: "45" }], publishedDate: "2012-08-29") { title publisher authors { authorName age } } }
With that we created out first GraphQL API. Congrats !!
You can find the whole source code here.
Please go through the official documentation of GraphQL here and tutorial here
Conclusion: GraphQL has simplified the REST. It's easy to use and configure. We can perform numerous operations in one endpoint and return the exact data as requested. It can help mobile and web development teams to reduce and simplify API calls. It keeps our code clean and maintainable.
Thank You !!
Manager - Capgemini US
4 年Very informative in simple way ... good one ????????
Software Engineer at Finastra
4 年Well written! Saurabh Kundu