diff --git a/Gemfile b/Gemfile index 70e2ffc0..a4a584e1 100644 --- a/Gemfile +++ b/Gemfile @@ -23,6 +23,7 @@ group :development, :test do gem "honeybadger" gem "coveralls", "~> 0.8.15", require: false gem "newrelic_rpm" + gem "ddtrace" gem "airbrake", "~> 10.0" gem "rollbar" gem "bugsnag" diff --git a/README.md b/README.md index 84a228f3..fe05d290 100644 --- a/README.md +++ b/README.md @@ -188,6 +188,12 @@ This will enable NewRelic custom instrumentation: Hutch::Config.set(:tracer, Hutch::Tracers::NewRelic) ``` +And this will enable Datadog custom instrumentation: + +```ruby +Hutch::Config.set(:tracer, Hutch::Tracers::Datadog) +``` + Batteries included! ## Running Hutch @@ -246,7 +252,7 @@ and the consumers are not loaded in development environment you will need to trigger the autoloading in an initializer with ```ruby -::Zeitwerk::Loader.eager_load_all +::Zeitwerk::Loader.eager_load_all ``` or with something more specific like diff --git a/lib/hutch/tracers.rb b/lib/hutch/tracers.rb index fa8d9369..0fa8d7a7 100644 --- a/lib/hutch/tracers.rb +++ b/lib/hutch/tracers.rb @@ -2,5 +2,6 @@ module Hutch module Tracers autoload :NullTracer, 'hutch/tracers/null_tracer' autoload :NewRelic, 'hutch/tracers/newrelic' + autoload :Datadog, 'hutch/tracers/datadog' end end diff --git a/lib/hutch/tracers/datadog.rb b/lib/hutch/tracers/datadog.rb new file mode 100644 index 00000000..ae550a0b --- /dev/null +++ b/lib/hutch/tracers/datadog.rb @@ -0,0 +1,17 @@ +require 'ddtrace' + +module Hutch + module Tracers + class Datadog + def initialize(klass) + @klass = klass + end + + def handle(message) + ::Datadog.tracer.trace(@klass.class.name, service: 'hutch', span_type: 'rabbitmq') do + @klass.process(message) + end + end + end + end +end diff --git a/spec/hutch/tracers/datadog_spec.rb b/spec/hutch/tracers/datadog_spec.rb new file mode 100644 index 00000000..e4f28917 --- /dev/null +++ b/spec/hutch/tracers/datadog_spec.rb @@ -0,0 +1,44 @@ +require 'spec_helper' + +RSpec.describe Hutch::Tracers::Datadog do + describe "#handle" do + subject(:handle) { tracer.handle(message) } + + let(:tracer) { described_class.new(klass) } + let(:klass) do + Class.new do + attr_reader :message + + def initialize + @message = nil + end + + def class + OpenStruct.new(name: 'ClassName') + end + + def process(message) + @message = message + end + end.new + end + let(:message) { double(:message) } + + before do + allow(Datadog.tracer).to receive(:trace).and_call_original + end + + it 'uses Datadog tracer' do + handle + + expect(Datadog.tracer).to have_received(:trace).with('ClassName', + hash_including(service: 'hutch', span_type: 'rabbitmq')) + end + + it 'processes the message' do + expect { + handle + }.to change { klass.message }.from(nil).to(message) + end + end +end