Around IT in 256 seconds

#3: GraphQL

June 02, 2020 | 4 Minute Read

GraphQL is a communication protocol that can be compared to RESTful APIs. Just like REST it uses HTTP, however, it tries to solve some issues with it, namely the lack of schema over- and under-fetching.

Let’s take a simple API: a customer apart from name, date of birth and VIP status has many orders. Each order has many products and each product has some attributes like name, price, discounts, etc. With RESTful API if you want to fetch the customer with all his or her orders you have to make multiple queries. The first query is for a customer and then most likely you’re going to have to make a second query for all orders. Or, in the worst case scenario, as many requests as many orders a customer has. There are some ways to fix this issue with RESTful APIs. For example, customer can return all orders and each order can have details of each product. However, what if you are only interested in name and date of birth of the customer? Even though you didn’t want all this data you still get all orders and all products. And this can be a lot of data. In GraphQL the whole API is described using a strict schema. When you make a GraphQL query you not only specify what resources you want. You also have to specify which attributes you need. So if you only need a name and date of birth you say: I want a customer with a name and date of birth. If you need a customer with name, date of birth, the VIP status, all orders and all products within each order this is the query you issue to the server. With RESTful API you have no choice, you always get what the implementor of the server gave you. You can work around it using different representations of a customer entity, like a “small customer” and a “large customer”, using different content types tou accept. However, this does becomes troublesome and the number of representations quickly grows exponentially. GraphQL solves the problem of under-fetching because you always get all data you ask for. It also solves the problem of over-fetching because you never get more data. For example if computing the VIP flag is costly on the server side you don’t have to pay that price because you didn’t ask for it. In RESTful API you always get what the server returns.

API evolution with GraphQL is also much simpler. For example if you want to remove a duplicated field you can easily see which clients are consuming that field because you see it in the query. If no one ‘s using it you can just remove it and no one’s going to notice. If you want to introduce new field it’s also not a problem because all the customers see the old version of the schema without that field so they don’t consume it. There’s no reason for special content type, there’s no reason for versioning. You just have a constant schema evolution. This is especially useful for mobile clients because typically you have lots of different versions in the wild.

Another benefit is that each and every property, so for example name, date of birth, VIP status, orders and so on - each and every property can have its own fetcher. If a fetcher is expensive, for example computing VIP status requires some complex logic, however someone’s not asking for the VIP status, you simply don’t invoke that fetcher.

All right, so what are the disadvantages of GraphQL? First of all, all the communication goes through a single URL over HTTP POST. POST requests are not cached by default. Secondly, this is no longer idiomatic HTTP because most of the time you are issuing simple stateless queries over HTTP POST. Which reminds me of SOAP. Also it’s no longer idiomatic HTTP because you’re making simple stateless immutable queries over HTTP POST. Finally it’s fairly easy to make small requests that accidentally loads a lot of data. For example if I ask: give me a customer, give me his or her orders and give me all the products related to all the orders, I can easily get kilobytes or even megabytes of data by issuing just a simple small request.

More details:

Tags: graphql, rest, soap

Be the first to listen to new episodes!

To get exclusive content: