SignalFx-Tracing Library for Ruby: An OpenTracing Auto-Instrumentor
This utility provides users with the ability of automatically configuring OpenTracing community-contributed instrumentation libraries for their Ruby application via a single function.
require 'signalfx/tracing'
SignalFx::Tracing::Instrumenter.configure(auto_instrument:true)
Installation
General installation
$ gem install signalfx-tracing
The SignalFx Tracing Library for Ruby requires just enough dependencies to allow custom instrumentation for your application, with target library instrumentations needing to be installed manually.
The basic installation provides an sfx-rb-trace-bootstrap
executable to assist with this process, which allows you to specify the desired libraries for instrumentation as a comma-separated list:
$ sfx-rb-trace-bootstrap --install-deps rack,rails,activerecord,restclient
$ # use the --list option to see all available instrumentations
$ sfx-rb-trace-bootstrap --list
Available target libraries:
{"activerecord"=>["activerecord-opentracing", "~> 0.2.1"],
< ... >
"sinatra"=>["sinatra-instrumentation", "~> 0.1.2"]}
If you'd prefer to install all the available instrumentations without the assistance of the sfx-rb-trace-bootstrap
utility, please install the provided gem dependencies.
$ # Run from a cloned and updated https://github.com/signalfx/signalfx-ruby-tracing.git
$ cd signalfx-ruby-tracing
$ bundle install
$ gem install -g
Installation in existing application
Specify the desired dependency by adding this line to your application's Gemfile:
gem 'signalfx-tracing'
Then execute the following (or use your desired installation method for your application).
$ bundle install
Usage
Configure the instrumentation anywhere in the setup portion of your code or before doing anything that needs to be traced.
For Rails, this would go in config/initializer/tracing.rb
.
The instrumentation can be done automatically, where the auto-instrumenter will check for modules defined in the code and instrument them if available:
require 'signalfx/tracing'
SignalFx::Tracing::Instrumenter.configure(auto_instrument:true)
Manual configuration may be desirable when only some libraries should be traced. These instrumentations to can be selected in a block:
SignalFx::Tracing::Instrumenter.configure do |patcher|
patcher.instrument(:LibName)
...
end
Valid lib names are listed below with the instrumentation documentation.
configure
accepts several optional parameters:
tracer
: a preconfigured OpenTracing tracer to use. If one is not provided, a new tracer will be initialized.- Default:
nil
- Default:
ingest_url
: this is the Smart Agent or Smart Gateway endpoint to which spans are sent by the tracer.- Default:
http://localhost:9080/v1/trace
- Default:
service_name
: service name to send spans under.- Default:
signalfx-ruby-tracing
- Default:
access_token
: SignalFx access token for authentication. Unnecessary for most deployments.- Default:
''
- Default:
Environment variables can be used to configure service_name
and access_token
if not given to the configure
method.
export SIGNALFX_SERVICE_NAME="<service_name>"
export SIGNALFX_ENDPOINT_URL="<url>"
export SIGNALFX_ACCESS_TOKEN="<token>"
If these environment variables are not set, the values will default to the ones listed above.
Instrumentation
This section contains details and configuration for specific frameworks.
Runtimes
- MRI Ruby (CRuby) 2.0+
Web servers
- Puma >= 3.0.0
- Passenger >= 5.0.25
Instrumentation for routes using these web servers is provided through Rack. If using a framework that builds on top of Rack, such as Rails or Sinatra, our instrumentation includes Rack instrumentation. In these cases, the routes through the web server will be automatically traced.
When interfacing with these web servers as a Rack application, please configure Rack instrumentation and insert it as middleware.
Libraries/Frameworks
Library | Versions Supported |
---|---|
ActiveRecord | ~> 5.0 |
Elasticsearch | >= 6.0.2 |
Faraday | >= 0.9.0 |
Grape | >= 0.13.0 |
Mongo | >= 2.1.0 |
Mysql2 | >= 0.4.0 |
Net::HTTP | Ruby >= 2.0 |
Pg | >= 0.18.0 |
Rack | >= 0.1 |
Rails | >= 3.0.0 |
Redis | >= 4.0.0 |
RestClient | >= 1.5.0 |
Sequel | >= 3.47.0 |
Sidekiq | >= 0.7.0 |
Sinatra | >= 1.0.0 |
Active Record
This instrumentation creates spans for each Active Record query using the Active Support notifications framework.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i activerecord
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:ActiveRecord)
end
Elasticsearch
Elasticsearch queries through the Ruby client are traced using a wrapper around the transport.
The forked source for the instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i elasticsearch
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Elasticsearch, auto_instrument: true)
end
When the auto_instrument
option is true
, it will allow all new Elasticsearch
clients to automatically wrap the default or configured transport and get
traces for queries. No additional configuration is necessary.
Alternatively, the instrumentation can be used selectively by setting a custom transport on the clients to be traced manually:
require 'elasticsearch'
require 'elasticsearch-tracer'
client = Elasticsearch::TracingClient.new
client.transport = Elasticsearch::Tracer::Transport.new(tracer: OpenTracing.global_tracer,
active_span: -> { OpenTracing.global_tracer.active_span },
transport: client.transport)
Faraday
Faraday HTTP client instrumentation automatically creates spans for outgoing requests. If the remote service has instrumentation that is aware of Rack, those spans will be automatically nested with Faraday's spans.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i faraday
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Faraday)
end
To use the instrumentation directly without patching, the Faraday middleware must be inserted for each new connection:
conn = Faraday.new(url: 'http://localhost:3000/') do |faraday|
faraday.use Faraday::Tracer
end
For more detailed usage, please check the instrumentation's page.
Grape
This instrumentation subscribes to ActiveSupport notifications emitted by the
Grape API. It patches Grape::API
to automatically insert the Rack::Tracer
middleware and trace requests.
The source for this instrumentation is located here
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i grape
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Grape)
end
instrument
takes these optional arguments:
tracer
: custom tracer to use. Defaults toOpenTracing.global_tracer
parent_span
: parent span to group spans or block that returns a span. Default:nil
disable_patching
: disable patching if managing the middleware stack manually. Default:false
If patching is disabled, but spans nested by request are still desired, then the Rack middleware must be manually added to the API class.
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i rack
require 'rack/tracer'
class MyAPI << Grape::API
insert 0, Rack::Tracer
...
end
Please see the instrumentation's page for more details.
Mongo
Mongo driver instrumentation traces queries performed through the Ruby Mongodb driver.
The source for this instrumentation is located here
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i mongodb
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:MongoDB)
end
Mysql2
Mysql2 instrumentation traces all queries performed with the Mysql2 client.
The source for this instrumentation is located here
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i mysql2
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Mysql2)
end
Net::HTTP
This automatically traces all requests using Net::HTTP.
The source for this instrumentation is located here.
Usage
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:NetHttp, tracer: tracer)
end
An optional tracer
named argument can be provided to use a custom tracer. It will default to OpenTracing.global_tracer
if not provided.
Pg
Pg instrumentation traces all queries performed with the pg client.
The source for this instrumentation is located here
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i pg
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:pg)
end
Rack
Rack spans are created using the rack-tracer
gem. This is enabled
automatically for other frameworks that are built on top of Rack, but it can
also be separately enabled.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i rack
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Rack)
end
use Rack::Tracer
Rails
Rails applications can be traced using the notifications provided by ActiveSupport.
It will use rack-tracer
to trace by requests.
The forked source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i rails
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Rails)
end
Optionally, to disable Rack instrumentation, set the rack_tracer
field to false.
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Rails, rack_tracer: false, exclude_events: [])
end
By default, all Rails ActiveSupport notifications are traced. However, if this
is too noisy, events to ignore can be passed as an array as exclude_events
.
A full list of events can be seen on the instrumentation's Readme.
Note that if rack_tracer
is set to false
, requests propagated to the Rails
app will not be extracted. For example, if a traced service makes a request to
an endpoint served by the Rails app, it will not be automatically nested.
Redis
This instrumentation traces commands performed using the Redis client.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i redis
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Redis, tracer: tracer)
end
Arguments:
tracer
: Optional custom tracer to use for this instrumentation- Default:
OpenTracing.global_tracer
- Default:
RestClient
RestClient requests can be patched to automatically be wrapped in a span. It will also inject the span context so remote services can extract it.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i restclient
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:RestClient, tracer: tracer, propagate: true)
end
Arguments:
tracer
: Optional custom tracer to use for this instrumentation- Default:
OpenTracing.global_tracer
- Default:
propagate
: Propagate spans to the request endpoint.- Default:
false
- Default:
Sequel
Sequel instrumentation adds extensions to the Database and Dataset to trace queries.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i sequel
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Sequel)
end
Arguments:
tracer
: Optional custom tracer for this instrumentation- Default:
OpenTracing.global_tracer
- Default:
Sidekiq
Sidekiq instrumentation traces worker job submissions and execution via Sidekiq middleware. The instrumenter registers both client and server middleware that use job metadata to represent all job submissions and their invocations. Trace context propagation adds to this job metadata to unifiy distributed client and server requests and processing.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i sidekiq
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Sidekiq, propagate: false)
end
Arguments:
tracer
: Optional custom tracer for this instrumentation- Default:
OpenTracing.global_tracer
- Default:
propagate
: Optional boolean to enable/disable trace context injection via job metadata- Default:
true
- Default:
Sinatra
Sinatra instrumentation traces requests and template rendering. The instrumenter
registers a Sinatra extension that uses rack-tracer
to trace requests and
monkey-patches to trace view rendering. Rack instrumentation is automatically
enabled when using Sinatra instrumentation.
The source for this instrumentation is located here.
Usage
$ # install the instrumentation if not done previously
$ sfx-rb-trace-bootstrap -i sinatra
SignalFx::Tracing::Instrumenter.configure do |p|
p.instrument(:Sinatra)
end
Configuring the Logger
The logger, based on the Ruby Logger, can be configured by setting the following environment variables:
Environmental Variable Name | Description | Default |
---|---|---|
SIGNALFX_LOG_PATH |
The path to the desired file where the instrumentation logs will be written. Besides customized paths, output options also include STDOUT and STDERR . |
/var/log/signalfx/signalfx-ruby-tracing.log |
SIGNALFX_LOG_SHIFT_AGE |
The desired number of old log files to keep, or frequency of rotation. Options include: daily , weekly or monthly ) |
0 |
SIGNALFX_LOG_SHIFT_SIZE |
The desired maximum size of log files (this only applies when. A new one would be created when the maximum is reached. | 1048576 (1 MB) |
SIGNALFX_LOG_LEVEL |
The severity criteria for recording logs (from least to most severe). Options: debug , info , warn , error , fatal , unknown |
warn |
More information regarding the logging configuration may be found here.
NB:
- If the default path for
SIGNALFX_LOG_PATH
(that is,/var/log/signalfx/signalfx-ruby-tracing.log
) is to be used, then please create the directory and or file (if necessary) and grant the relevant access permissions to the instrumentation user process. If there are permission issues, the instrumentation will default to logging to the standard error (STDERR) handle, until the path is provided to which logs can be written without any access issues.