Monitoring Rails using OpenTelemetry and Uptrace
Tags: rails, webdev, opensource, monitoring
Published: 2023-07-26 12:52:16

Monitoring Ruby on Rails applications using OpenTelemetry provides deep insights into the application's performance, user experience, and resource usage, leading to better-informed decisions, faster issue resolution, and improved overall application quality.

## What is tracing?

OpenTelemetry offers [distributed tracing](<(https://uptrace.dev/opentelemetry/distributed-tracing.html)>) capabilities, which are essential for modern microservices-based architectures. With distributed tracing, you can track requests as they traverse multiple services, helping you understand the end-to-end flow and performance of the entire system.

Tracing provides insights into your app performance along with any errors and logs. You immediately see what conditions cause errors and how particular error affects app performance.

![Distributed tracing](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/fmm95e3niz8jive6t476.png)

Using tracing, you can break down requests into [spans](https://uptrace.dev/opentelemetry/distributed-tracing.html#spans). **Span** is an operation (unit of work) your app performs handling a request, for example, a database query or a network call.

**Trace** is a tree of spans that shows the path that a request makes through an app. Root span is the first span in a trace.

![Spans and trace](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/khnbmqbvyt6ph1m58iq7.png)

To learn more about tracing, see [Distributed Tracing using OpenTelemetry](https://uptrace.dev/opentelemetry/distributed-tracing.html).

## What is OpenTelemetry?

[OpenTelemetry](https://uptrace.dev/opentelemetry/) is an open source observability framework for [OpenTelemetry tracing](https://uptrace.dev/opentelemetry/distributed-tracing.html), [logs](https://uptrace.dev/opentelemetry/logs.html), and [metrics](https://uptrace.dev/opentelemetry/metrics.html).

OpenTelemetry allows developers to collect and export telemetry data in a vendor-agnostic manner. With OpenTelemetry, you can instrument your application once and then add or change vendors without changing the instrumentation, for example, here is a list of popular [DataDog alternatives](https://uptrace.dev/blog/datadog-alternatives.html) that support OpenTelemetry.

OpenTelemetry provides language-specific APIs for popular programming languages like Java, JavaScript, Python, Go, Ruby, and more. These APIs allow developers to instrument their code to capture telemetry data without being tied to any specific monitoring platform.

## Creating spans

To measure performance of database queries or HTTP requests, you can create a span using OpenTelemetry Ruby API:

```ruby
require 'opentelemetry'

tracer = OpenTelemetry.tracer_provider.tracer('my_app_or_gem', '1.0.0')

def some_func()
  tracer.in_span('some-func') do |span|
    # the code you are measuring
  end
end
```

To record contextual information, you can annotate spans with [attributes](https://uptrace.dev/opentelemetry/distributed-tracing.html#attributes):

```ruby
def create_user(name, email)
  tracer.in_span('insert-user', kind: :server) do |span|
    if span.recording?
      span.set_attribute('enduser.name', name)
      span.set_attribute('enduser.email', email)
    end

    User.create(name: name, email: email)
  end
end
```

See [OpenTelemetry Ruby tracing](https://uptrace.dev/opentelemetry/ruby-tracing.html) for details.

## What is Uptrace?

Uptrace is an [OpenTelemetry backend](https://uptrace.dev/blog/opentelemetry-backend.html) with an intuitive query builder, rich dashboards, alerting rules, and integrations for most languages and frameworks. It can process billions of spans and metrics on a single server and allows you to monitor your applications at 10x lower cost.

Uptrace uses ClickHouse database to store traces, metrics, and logs. You can use it to monitor applications and set up automatic alerts to receive notifications via email, Slack, Telegram, and more.

You can [get started](https://uptrace.dev/get/get-started.html) with Uptrace by downloading a DEB/RPM package or a pre-compiled Go binary.

## Example application

In this tutorial, you will be instrumenting a [toy app](https://github.com/uptrace/uptrace/tree/master/example/rails) that uses Rails and ActiveRecord with sqlite3 database. You can retrieve the source code with the following command:

```shell
git clone git@github.com:uptrace/uptrace.git
cd example/rails
```

The app comes with some dependencies that you can install with:

```shell
bundle install
```

## Configuring OpenTelemetry

Uptrace provides [OpenTelemetry Ruby](https://uptrace.dev/get/opentelemetry-ruby.html) distro that configures OpenTelemetry SDK for you. To install the distro:

```shell
gem install uptrace
```

Then you need to initialize OpenTelemetry whenever the app is started:

```ruby
require 'uptrace'

# copy your project DSN here or use UPTRACE_DSN env var
Uptrace.configure_opentelemetry(dsn: '') do |c|
  c.use_all

  c.service_name = 'myservice'
  c.service_version = '1.0.0'
end
```

See [OpenTelemetry Ruby](https://uptrace.dev/get/opentelemetry-ruby.html) documentation for details.

## Instrumenting Rails

To instrument Ruby on Rails app, you need a corresponding [OpenTelemetry Rails](https://uptrace.dev/get/instrument/opentelemetry-rails.html) instrumentation:

```shell
gem install opentelemetry-instrumentation-rails
```

To instrument Rails app, call `use` with the name of the instrumentation:

```ruby
require 'uptrace'
require 'opentelemetry-instrumentation-rails'

Uptrace.configure_opentelemetry(dsn: '') do |c|
  c.use 'OpenTelemetry::Instrumentation::Rails'
end
```

Alternatively, you can call `use_all` to install all available instrumentations:

```ruby
require 'uptrace'
require 'opentelemetry-instrumentation-rails'

Uptrace.configure_opentelemetry(dsn: '') do |c|
  c.use_all
end
```

## Instrumenting ActiveRecord

Just like with Rails, you need to install ActiveRecord instrumentation:

```shell
gem install opentelemetry-instrumentation-active_record
```

And call `use` with the name of the instrumentation:

```ruby
require 'uptrace'
require 'opentelemetry-instrumentation-active_record'

Uptrace.configure_opentelemetry(dsn: '') do |c|
  c.use 'OpenTelemetry::Instrumentation::ActiveRecord'
end
```

## What's next?

OpenTelemetry provides detailed instrumentation of Ruby on Rails applications, allowing developers to identify performance bottlenecks, slow database queries, and inefficient code paths.

By monitoring the application's performance, developers can optimize critical components, leading to better overall application performance and improved user experience.

- [OpenMetrics vs OpenTelemetry](https://uptrace.dev/blog/openmetrics-vs-opentelemetry.html)
- [OpenTelemetry Sinatra](https://uptrace.dev/get/instrument/opentelemetry-sinatra.html)