While a GraphQL API may be less susceptible to the common REST API performance issues of under and over-fetching data, allowing users to request and receive a wide range of data in a single, nestable query can also come with performance risks.
AppSignal for Elixir now supports Absinthe out of the box, and automatically adds Absinthe spans to your app's metrics. AppSignal also automatically instruments Ecto, giving you insights into your application's queries. When combined, AppSignal can be used to gain insights into how queries passed to the GraphQL endpoint translate to the database.
This blog post will explore how you can use both AppSignal's Absinthe and Ecto integrations to monitor and fine-tune your GraphQL API.
From Request To Response
Unlike a REST API which has data-specific endpoints, the flexibility of a GraphQL API means requests must go through several steps to return the expected information:
|Parsing and Validating||The server parses the request and checks that it is in a valid format.|
|Query Execution||Root and field resolvers fetch the requested data from the application's database.|
|Transforming and Responding||The fetched data is transformed, allowing your API to return an array of meaningful data rather than relational IDs. The transformed data is then structured according to the request query. |
Any errors that occurred while executing and transforming the query will also be included in the response.
|Response Delivery||The requested data is delivered in JSON format to the client — it includes all requested data, appropriately formatted, as well as any error messages.|
To take full advantage of the performance benefits of a GraphQL API, your application must be able to parse, query, and transform data efficiently, especially when receiving more complex requests that have nested queries or require higher levels of data transformation.
AppSignal's Absinthe and Ecto integrations assist in monitoring the performance of your application's parsing, querying, and data transformation. They provide clear insights, on an event level, of exactly how your API is responding to requests — enabling you to quickly identify areas where optimizations are needed for specific requests.
Monitoring GraphQL via Absinthe
AppSignal automatically recognizes operations executed by Absinthe and wraps them into a
call.graphql event on your Event Timeline, allowing you to see how much time Absinthe spends parsing, querying, and transforming data:
call.graphql is taking up a large portion of the event timeline, this could indicate it is having trouble parsing a request or transforming data. Often, this is due to deeply nested requests or querying modules that have high levels of relational data.
For example, let's say we have a GraphQL API that returns all courses, exam results, and lecturers for a student. This query requires nesting and several data transformations. If your application is taking a long time to execute GraphQL logic, it may be an indication that you need to take steps such as refactoring resolver logic, data fetching strategies, or implementing caching mechanisms for frequently requested data.
With AppSignal's Ecto integration, you can see how long it takes for Ecto queries to be executed in your application's requests, displaying them in the Event Timeline.
You can investigate Ecto's performance in slow requests and apply suitable strategies to enhance performance when necessary, such as caching, query optimization, and indexing for large nested data sets. You could also implement pagination, rate, and depth limiting to limit the amount of data requested within reasonable bounds and limit the frequency and complexity of incoming queries.
Get Going with GraphQL and AppSignal
Absinthe and Ecto are automatically instrumented and available in AppSignal 2.7.0 or higher. For Ecto, you need to ensure that the value of
:otp_app in your
appsignal.exs configuration matches your application's app name.
Once correctly configured, AppSignal will automatically display GraphQL and Ecto events in your Event Timeline, giving you effortless insights into two of your API's most important components.
You can learn more about configuring Absinthe and Ecto in our Elixir integration documentation.
Delve Deeper into Absinthe and Ecto
If you enjoyed this blog post, you'll enjoy some of our recent related blog posts on Absinthe and Ecto:
- An Introduction to Absinthe
- Tackling Performance Issues in Ecto Applications
- Absinthe for Large Elixir Applications
In the meantime, if you have any questions about AppSignal, please don't hesitate to get in touch! We offer dev-to-dev support, give free accounts to open-source projects, and if you're new to AppSignal, we'll welcome you onboard with a delicious shipment of stroopwafels 🍪 😋