16th November 2021
Leveraging the Apollo Toolbelt with Mercurius GraphQL Server
In this article, we outline how you can use the mercurius-apollo-registry and mercurius-apollo-tracing plugins to switch from apollo-server to mercurius as your GraphQL API server.
Apollo Studio-compatible GraphQL Servers
Apollo Studio is one of the leading developer tools for documenting, monitoring and measuring the performance of GraphQL APIs. When it comes to integrating it with a Node.js GraphQL backend, the most obvious way to do it is via apollo-server. The protocols for tracing and schema reporting are available for anyone to implement, but very few GraphQL server implementations do.
apollo-server-core and its adapter packages
apollo-server-core is the backbone for all the server packages published by Apollo. It contains features shared by all of the individual packages: Express, Koa, Hapi, Lambda, even Fastify. These adapters are tiny wrappers connecting the GraphQL response handler into the HTTP handler properly for each framework. Under the hood, it’s always apollo-server-core, which has both tracing and schema reporting built in. You don’t need to install any additional packages to use it with Apollo Studio.
At Nearform we use mercurius, a GraphQL server implementation built as a Fastify plugin. Mercurius does not run on apollo-server-core; it uses its own implementation based on the canonical graphql package. We wanted to leverage the Apollo Studio as well, so we wrote two new libraries for mercurius. These are essentially Fastify plugins that integrate mercurius with Apollo Studio. They are not included by default — Fastify is governed by the minimal core principle, so these integrations are separate npm modules. They do not pollute node_modules for those who do not need to integrate with Apollo Studio.
mercurius-apollo-registry plugin enables schema reporting. This is useful as your API develops over time. Apollo Studio generates useful changelogs for any change to the API’s shape and tracks versions for you. We have written about using this plugin with a Schema registry.
First, install with
npm install mercurius-apollo-registry.
Then you can register the plugin in your Fastify app:
For a simple schema like
basicSchema (left of image below), if we add a new root query, we can see the changelog in Apollo Studio picks up on the change once we run our server:
mercurius-apollo-tracing plugin is used to collect runtime performance metrics as well as errors from your GraphQL resolvers. These get sent to the Apollo Studio’s ingress endpoint. If you have on-premise Apollo Studio or any other server compatible with the apollo tracing format, you can send your reports there just by specifying a different URL to the plugin options.
Apollo studio has a UI to explore the data collected. You can see timings for every resolver and all errors thrown in your resolvers.
Apollo tracing is defined as GraphQL extension for performance tracing. It contains the definition for GraphQL execution trace format.
This is a sample trace for a GraphQL query like this one:
We can see
endTime are recorded for each GraphQL resolver. Thanks to
process.hrtime(), we get nanosecond precision here allowing us to measure even the smallest performance gains. Each trace like this gets serialised into a protobuf using apollo-reporting-protobuf and sent to the ingress endpoint of Apollo Studio API.
Similar to the registry plugin, install the plugin from NPM with
npm install mercurius-apollo-tracing.
Next, you need to copy your Graph ref from the graph detail page in Apollo Studio. It will be in the format “yourGraphName@variant”.
Graph ref is a unique identifier for a schema deployment inside Apollo Studio.
Last, register the plugin in the following way in your existing Fastify app:
You can even trace your API running on your development machine before you deploy your API to a live environment. Simply point it to your localhost URL:
Make sure you have CORS headers enabled on the API server because Apollo Studio makes requests directly from the browser, so your GraphQL API must respond with a CORS header.
All logging/tracing inevitably slows down observed system performance, and mercurius-apollo-tracing plugin is no exception. For exact numbers we’ve measured, see the readme on GitHub, but we’ve made sure the slowdown is less than with the apollo-server-fastify package. Enabling tracing there slows the resolver’s execution even more.
With these two plugins, you can get the same level of granular reporting capability and overall developer experience in Apollo studio as you get with apollo-server. This makes the decision easier if you are on apollo-server and are considering switching to mercurius as your GraphQL api server.