Ruby
Ruby uses the OpenTelemetry Ruby SDK plus
opentelemetry-instrumentation-all, which instruments Rails, Rack, Sinatra, ActiveRecord,
Net::HTTP, Faraday, Redis, Sidekiq and
more.
You add a few lines of setup; the rest needs no code changes.
Use this page when you run a Ruby or Rails service and want it in FuseScope.
| Signal | Status | What is sent |
|---|---|---|
| Traces | Stable | Spans for requests, HTTP calls, database and jobs. |
| Metrics | Development | Your own metrics, through separate pre-1.0 gems. |
| Logs | Development | Ruby Logger and Rails logger records with trace IDs, through separate pre-1.0 gems. |
Metrics and logs work, but their gems are still 0.x and can change between releases.
Traces alone need only the first three gems below.
Prerequisites
Section titled “Prerequisites”- CRuby 3.3 or later (current gems require it). JRuby and TruffleRuby are best effort.
- Bundler.
- A FuseScope collector you can reach on port 4318. See OTLP.
Install
Section titled “Install”bundle add opentelemetry-sdk opentelemetry-exporter-otlp opentelemetry-instrumentation-all# Optional: metrics and logsbundle add opentelemetry-metrics-sdk opentelemetry-exporter-otlp-metricsbundle add opentelemetry-logs-sdk opentelemetry-exporter-otlp-logs opentelemetry-instrumentation-loggerSet up the SDK
Section titled “Set up the SDK”-
Configure the SDK as early as possible. In Rails, use an initializer:
config/initializers/opentelemetry.rb require "opentelemetry/sdk"require "opentelemetry/exporter/otlp"require "opentelemetry/instrumentation/all"# Optional: metrics and logs. Load them before configure.require "opentelemetry-metrics-sdk"require "opentelemetry/exporter/otlp_metrics"require "opentelemetry-logs-sdk"require "opentelemetry/exporter/otlp_logs"require "opentelemetry/instrumentation/logger"OpenTelemetry::SDK.configure do |c|c.use_allenduse_allturns on every instrumentation whose library is loaded. Outside Rails, put this at the top of your entry point (for exampleconfig.ru), before the app is built. -
Configure the exporter:
Terminal window export OTEL_SERVICE_NAME=checkoutexport OTEL_RESOURCE_ATTRIBUTES=deployment.environment.name=production,service.version=1.4.2export OTEL_EXPORTER_OTLP_ENDPOINT=http://fusescope-collector.example.com:4318export OTEL_EXPORTER_OTLP_PROTOCOL=http/protobufTraces, metrics and logs default to
otlponce their gems are loaded. SetOTEL_METRICS_EXPORTER=noneorOTEL_LOGS_EXPORTER=noneto turn one off. -
Run the app as usual:
Terminal window bundle exec rails server
Send to FuseScope
Section titled “Send to FuseScope”Not supported by the Ruby SDK. Use Direct (HTTP 4318), or send to a local collector over HTTP and let it forward over gRPC.
OTEL_EXPORTER_OTLP_ENDPOINT=http://fusescope-collector.example.com:4318OTEL_EXPORTER_OTLP_PROTOCOL=http/protobufBehind the chart ingress, use https://otlp.example.com. See
from outside the cluster.
OTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:4318OTEL_EXPORTER_OTLP_PROTOCOL=http/protobufRun the collector with Docker, on a VM or in Kubernetes.
Docker
Section titled “Docker”The gems are in the Gemfile, so bundle install adds them:
FROM ruby:3.3-slimRUN apt-get update && apt-get install -y --no-install-recommends build-essential \ && rm -rf /var/lib/apt/lists/*WORKDIR /appCOPY Gemfile Gemfile.lock ./RUN bundle installCOPY . .CMD ["bundle", "exec", "rails", "server", "-b", "0.0.0.0"]docker run \ -e OTEL_SERVICE_NAME=checkout \ -e OTEL_RESOURCE_ATTRIBUTES=deployment.environment.name=production \ -e OTEL_EXPORTER_OTLP_ENDPOINT=http://fusescope-collector.example.com:4318 \ -e OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf \ checkout:latestKubernetes
Section titled “Kubernetes”Set the variables in the pod spec. The downward API adds the pod name and namespace:
env: - name: OTEL_SERVICE_NAME value: checkout - name: OTEL_EXPORTER_OTLP_ENDPOINT value: http://fusescope-otel-collector.fusescope.svc.cluster.local:4318 - name: OTEL_EXPORTER_OTLP_PROTOCOL value: http/protobuf - name: K8S_POD_NAME valueFrom: fieldRef: fieldPath: metadata.name - name: K8S_NAMESPACE_NAME valueFrom: fieldRef: fieldPath: metadata.namespace - name: OTEL_RESOURCE_ATTRIBUTES value: deployment.environment.name=production,k8s.pod.name=$(K8S_POD_NAME),k8s.namespace.name=$(K8S_NAMESPACE_NAME)$(VAR) only expands variables defined earlier in the list, so keep
OTEL_RESOURCE_ATTRIBUTES last.
With opentelemetry-logs-sdk, opentelemetry-exporter-otlp-logs and
opentelemetry-instrumentation-logger installed, use_all patches Ruby’s Logger and the
Rails logger. Each record is still written where it was before, and is also exported over
OTLP with the trace and span IDs of the active span.
Logs support is in development: the gems are 0.x. If a collector already reads your
stdout, set OTEL_LOGS_EXPORTER=none so each line is stored once.
Check that data arrives
Section titled “Check that data arrives”- Send a few requests to the service.
- Open Services. The service appears under its
OTEL_SERVICE_NAMEwithin a minute. - Open the Traces explorer and filter by
service.name.
Nothing arrives? Run with OTEL_TRACES_EXPORTER=console to print spans to stdout, and look
for warnings from OpenTelemetry at boot, such as a missing exporter gem or an unsupported
protocol.