
Absinthe is a popular GraphQL toolkit for building robust APIs in Elixir. Monitoring such APIs is essential to ensure performance, detect bottlenecks, and handle errors effectively. AppSignal offers a seamless way to monitor and gain insights into your Absinthe-powered GraphQL APIs, enabling you to keep applications performant and reliable.
In this post, we’ll explore how to leverage AppSignal’s automatic instrumentation and custom metrics for Absinthe, along with strategies to monitor errors, track subscriptions, and enhance performance through actionable metrics.
Automatic Absinthe for Elixir Instrumentation with AppSignal
Setting up AppSignal for your Elixir application is straightforward. You can follow the official setup guide to install the AppSignal package and configure it with your application key. Once integrated, AppSignal automatically instruments your Absinthe GraphQL API, giving you insights into the execution time and performance of individual queries and mutations.
Here's an example of how your AppSignal performance report might look, showcasing query performance breakdown:

The sample breakdown above shows that GraphQL took 45 ms—this duration covers both parsing the query and encoding the results. Ecto took 37 ms, with most of that time spent executing the database query.
Let's check out the Event Timeline now:

As you can see, this provides a breakdown of all the Ecto queries performed during the resolution of this query. With this instrumentation, you can identify slow queries, measure throughput, and understand which resolvers might need optimization—all without adding any manual instrumentation.
Handling Errors and Exceptions in Absinthe with AppSignal
In GraphQL APIs, errors can occur at multiple points: within resolvers, due to validation issues, or from an underlying data source. AppSignal helps capture and report these errors along with contextual information, making debugging efficient.
Resolver Exceptions and Validation Errors
When an error occurs in a resolver, AppSignal captures it and provides details about the query that caused the issue, the resolver, and the stack trace.
For example, if a single field on a GraphQL API has an error, it will be reported on the "Errors" page on AppSignal. Here's an example of such an error:

Clicking on "Inspect latest sample" takes you to the full sample details, including:
- A backtrace that can help us pinpoint where the error originated.
- The full GraphQL query and variables (if any), and a lot of other information that can be useful to reproduce that issue.

Tracking Custom Metrics
While automatic instrumentation provides valuable insights into the performance of your Absinthe API, tracking custom metrics can offer even deeper visibility into specific areas of your application. Custom metrics allow you to define and collect data points unique to your business logic or performance needs. AppSignal makes it easy to track these metrics in your Absinthe GraphQL API.
Defining Custom Metrics
To start tracking custom metrics, you'll need to define the specific aspects of your API that you want to measure. This could include:
- Resolver Performance: Measure how long specific resolvers take to execute.
- Query Complexity: Track the number of fields requested in a query or the depth of the query.
- Subscription Events: Monitor events related to GraphQL subscriptions, such as connection counts and active subscriptions.
Implementing Custom Metrics
You can implement custom metrics using AppSignal's built-in APIs. Here’s a simple example, tracking the execution time of a resolver:
defmodule MyAppWeb.Resolvers.PostResolver do def get_pots(_, %{id: id}, _) do start_time = System.monotonic_time() case Blog.get_post(id) do nil -> Appsignal.increment_counter("post.not_found") {:error, "Post not found"} post -> duration = System.monotonic_time() - start_time Appsignal.set_gauge("post.fetch_time", duration) {:ok, post} end end end
Once you've defined and implemented your custom metrics, you can view them in your AppSignal dashboard, which includes various graphs and charts. These graphs and charts are crucial for identifying trends over time, such as increasing fetch times or spikes in 'post not found' errors.

Monitoring Absinthe Subscriptions
Subscriptions in Absinthe allow for real-time updates, typically used in chat or notification systems. Monitoring these subscriptions is crucial to ensure they perform well throughout their lifecycle.
Example: Monitoring Subscription Performance
A typical Absinthe subscription might look like this:
subscription :comment_added do arg :post_id, non_null(:id) config fn args, _ -> {:ok, topic: args.post_id} end trigger :comment_added, topic: fn %{post_id: post_id} -> "post:#{post_id}" end resolve fn comment, _, _ -> {:ok, comment} end end
Similar to custom metrics monitoring, we can track subscription activation time, latency during updates, total active subscriptions at any given time, and any errors that occur within these subscriptions, giving you full visibility into their behavior.
Here’s how to add basic instrumentation to measure the time required to set up and resolve the subscription.
field :comment_added, :comment do arg(:post_id, non_null(:id)) config(fn %{post_id: id} = _args, %{context: context} -> Appsignal.instrument("subscription.config", "Setting up subscription", fn -> {:ok, topic: "post:#{id}"} end) end) resolve(fn comment, _, _ -> Appsignal.instrument("subscription.resolve", "Resolving subscription", fn -> {:ok, comment} end) end) end
And that's it for our whistle-stop tour of Absinthe monitoring using AppSignal!
Wrapping Up
Monitoring GraphQL APIs with AppSignal enables Elixir developers to maintain high performance, quickly diagnose errors, and leverage custom metrics for business-critical operations. Whether you're tracking query execution, debugging resolver errors, or ensuring efficient subscription handling, AppSignal equips you with the necessary tools to build and maintain robust Absinthe applications.
If you are building complex APIs with Absinthe, ensure you integrate AppSignal to enhance your observability and performance monitoring. For further reading, explore AppSignal's Absinthe documentation and this four-part series on building scalable GraphQL APIs with Absinthe.
Happy coding!
P.S. If you'd like to read Elixir Alchemy posts as soon as they get off the press, subscribe to our Elixir Alchemy newsletter and never miss a single post!