Aspecto blog

On microservices, OpenTelemetry, and anything in between

OpenTelemetry Elasticsearch Instrumentation for Node.js

Share this post

At Aspecto, we use Elasticsearch as the primary tool for collecting, processing and searching telemetry traces.

Since we enjoy using Elasticsearch internally, we set out to create an Elasticsearch instrumentation for Node.js.

During our journey for instrumentation inspiration, we encountered other great instrumentations. 

But something was still missing for us. 

Something that would make this one really great (more on that later).

This post takes you through our thought process behind creating an Elasticsearch instrumentation that tracks data sent by the application to the Elasticsearch node client.

I will start by covering some of the basics first.

What is Elasticsearch?

Elasticsearch is a distributed, free, and open search and analytics engine for all types of data. It is super fast for text searching and naturally supports telemetry data.

What is Opentelemetry?

OpenTelemetry is a CNCF project, which, among other things, enables the collection of distributed traces. OpenTelemetry is an incredible collection of tools that help you understand your software’s performance and behavior.

We use OpenTelemetry at the core of our product. 

The Elasticsearch Instrumentation ?

Since Elasticsearch uses HTTP protocol, and OpenTelemetry already supports it, we debated whether this instrumentation is required at all. 

We have already gathered insights from Elasticsearch using the HTTP instrumentation but something was missing. 

We felt we could harvest more powerful data with a dedicated instrumentation. 

Our goal was to provide more granular data that would help the growing community of Elasticsearch users to get more specific insights into the interaction between their Node.js services and Elasticsearch.

For example, instead of reverse engineering this URL https://es-url/my-index/_bulk, and understand which options were supplied to the function call from query params, the instrumentation is showing exactly how the developer called the function and with which params.

What data should be collected? 

We struggled with this question during the development process. 

For inspiration, we were looking at other Elasticsearch OpenTelemetry instrumentations such as Python, Java, and the official bridge for the Elastic APM

We noticed one common theme across these instrumentations: wrapping and collecting the HTTP request function.

Although it is popular and somewhat the obvious move, this information is already collected by the HTTP spans. We wanted to find a way to provide specific information regarding the data sent by the application to the Elasticsearch client.

We noticed all API functions in the Elasticsearch client library use the same function signature (params, options, callback), so we decided to collect the exact parameters the application sends and wrap those functions.

This way, we could provide specific information regarding the data sent by the application to the Elasticsearch client, giving you better visibility and a deeper understanding of every single interaction.

The JS OpenTelemetry instrumentation for @elastic/elasticsearch is available on npm and on GitHub.

PS: Repo stars are always appreciated. ?

The Result

Here is what the end result looks like:

In this view, you can see a search request trace in the Aspecto app.

This trace allows us to search any attribute collected in the request to the Elasticsearch client library and find the exact transactions this attribute was involved in.

The combination of the data we collect with this instrumentation, and the search function, can be helpful in any debugging scenario, for example, when you want to understand which area in your system to focus on.

You can add the Elasticsearch instrumentation in any OpenTelemetry installation by following the example in README, or use Aspecto SDK which comes preconfigured with OpenTelemetry and Elasticsearch instrumentation.

This new instrumentation is included in the Aspecto SDK.

Here’s how to start using it:

  • Install our Node.js library using npm:
npm install @aspecto/opentelemetry
  • Add this call at the top of your app entry point, before any other import:
require('@aspecto/opentelemetry')({ aspectoAuth: 'enter your token' });
  • Create Aspecto account and get your aspectoAuth token.

For more information and examples check out Aspecto’s documentation.

Feel free to reach out to us with any issue or suggestion, or if you want to vote on what should be the next library instrumentation. 

Community contributions are always welcome.

This instrumentation is:

  • Vendor-neutral
  • Strictly complies with open telemetry semantic conventions
  • Up to date with the latest SDK version

As always, this instrumentation (and many others) was developed by Aspecto with ❤️

Spread the word

Subscribe for more distributed applications tutorials and insights that will help you boost microservices troubleshooting.