Skip to content

Commit 506dd65

Browse files
authored
Merge pull request #1537 from appsignal/add-delayed-job-enqueue-instrumentation
Instrument Delayed Job enqueues
2 parents 5e9f3e1 + 723c0f6 commit 506dd65

9 files changed

Lines changed: 418 additions & 374 deletions

File tree

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
---
2+
bump: minor
3+
type: add
4+
---
5+
6+
Instrument Delayed Job enqueues. Enqueuing a job now records an
7+
`enqueue.delayed_job` event on the active transaction, so enqueues made from
8+
within a web request or another job show up in the event timeline.

.github/workflows/ci.yml

Lines changed: 190 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
# This is a generated file by the `rake build_matrix:github:generate` task.
33
# See `build_matrix.yml` for the build matrix.
44
# Generate this file with `rake build_matrix:github:generate`.
5-
# Generated job count: 234
5+
# Generated job count: 241
66
---
77
name: Ruby gem CI
88
'on':
@@ -213,6 +213,33 @@ jobs:
213213
JRUBY_OPTS: ''
214214
COV: '1'
215215
BUNDLE_GEMFILE: gemfiles/code_ownership.gemfile
216+
ruby_4-0-0__delayed_job_ubuntu-latest:
217+
name: Ruby 4.0.0 - delayed_job
218+
needs: ruby_4-0-0_ubuntu-latest
219+
runs-on: ubuntu-latest
220+
steps:
221+
- name: Check out repository
222+
uses: actions/checkout@v4
223+
- name: Install Ruby
224+
uses: ruby/setup-ruby@v1
225+
with:
226+
ruby-version: 4.0.0
227+
bundler-cache: true
228+
- name: Install gem extension
229+
run: "./script/bundler_wrapper exec rake extension:install"
230+
- name: Print extension install report
231+
run: "[ -e ext/install.report ] && cat ext/install.report || echo 'No ext/install.report
232+
file found'"
233+
- name: Print Makefile log file
234+
run: "[ -f ext/mkmf.log ] && cat ext/mkmf.log || echo 'No ext/mkmf.log file
235+
found'"
236+
- name: Run tests
237+
run: "./script/bundler_wrapper exec rake test"
238+
env:
239+
RAILS_ENV: test
240+
JRUBY_OPTS: ''
241+
COV: '1'
242+
BUNDLE_GEMFILE: gemfiles/delayed_job.gemfile
216243
ruby_4-0-0__dry-monitor_ubuntu-latest:
217244
name: Ruby 4.0.0 - dry-monitor
218245
needs: ruby_4-0-0_ubuntu-latest
@@ -1054,6 +1081,33 @@ jobs:
10541081
JRUBY_OPTS: ''
10551082
COV: '1'
10561083
BUNDLE_GEMFILE: gemfiles/code_ownership.gemfile
1084+
ruby_3-4-1__delayed_job_ubuntu-latest:
1085+
name: Ruby 3.4.1 - delayed_job
1086+
needs: ruby_3-4-1_ubuntu-latest
1087+
runs-on: ubuntu-latest
1088+
steps:
1089+
- name: Check out repository
1090+
uses: actions/checkout@v4
1091+
- name: Install Ruby
1092+
uses: ruby/setup-ruby@v1
1093+
with:
1094+
ruby-version: 3.4.1
1095+
bundler-cache: true
1096+
- name: Install gem extension
1097+
run: "./script/bundler_wrapper exec rake extension:install"
1098+
- name: Print extension install report
1099+
run: "[ -e ext/install.report ] && cat ext/install.report || echo 'No ext/install.report
1100+
file found'"
1101+
- name: Print Makefile log file
1102+
run: "[ -f ext/mkmf.log ] && cat ext/mkmf.log || echo 'No ext/mkmf.log file
1103+
found'"
1104+
- name: Run tests
1105+
run: "./script/bundler_wrapper exec rake test"
1106+
env:
1107+
RAILS_ENV: test
1108+
JRUBY_OPTS: ''
1109+
COV: '1'
1110+
BUNDLE_GEMFILE: gemfiles/delayed_job.gemfile
10571111
ruby_3-4-1__dry-monitor_ubuntu-latest:
10581112
name: Ruby 3.4.1 - dry-monitor
10591113
needs: ruby_3-4-1_ubuntu-latest
@@ -2030,6 +2084,33 @@ jobs:
20302084
JRUBY_OPTS: ''
20312085
COV: '1'
20322086
BUNDLE_GEMFILE: gemfiles/code_ownership.gemfile
2087+
ruby_3-3-4__delayed_job_ubuntu-latest:
2088+
name: Ruby 3.3.4 - delayed_job
2089+
needs: ruby_3-3-4_ubuntu-latest
2090+
runs-on: ubuntu-latest
2091+
steps:
2092+
- name: Check out repository
2093+
uses: actions/checkout@v4
2094+
- name: Install Ruby
2095+
uses: ruby/setup-ruby@v1
2096+
with:
2097+
ruby-version: 3.3.4
2098+
bundler-cache: true
2099+
- name: Install gem extension
2100+
run: "./script/bundler_wrapper exec rake extension:install"
2101+
- name: Print extension install report
2102+
run: "[ -e ext/install.report ] && cat ext/install.report || echo 'No ext/install.report
2103+
file found'"
2104+
- name: Print Makefile log file
2105+
run: "[ -f ext/mkmf.log ] && cat ext/mkmf.log || echo 'No ext/mkmf.log file
2106+
found'"
2107+
- name: Run tests
2108+
run: "./script/bundler_wrapper exec rake test"
2109+
env:
2110+
RAILS_ENV: test
2111+
JRUBY_OPTS: ''
2112+
COV: '1'
2113+
BUNDLE_GEMFILE: gemfiles/delayed_job.gemfile
20332114
ruby_3-3-4__dry-monitor_ubuntu-latest:
20342115
name: Ruby 3.3.4 - dry-monitor
20352116
needs: ruby_3-3-4_ubuntu-latest
@@ -2952,6 +3033,33 @@ jobs:
29523033
JRUBY_OPTS: ''
29533034
COV: '1'
29543035
BUNDLE_GEMFILE: gemfiles/capistrano3.gemfile
3036+
ruby_3-2-5__delayed_job_ubuntu-latest:
3037+
name: Ruby 3.2.5 - delayed_job
3038+
needs: ruby_3-2-5_ubuntu-latest
3039+
runs-on: ubuntu-latest
3040+
steps:
3041+
- name: Check out repository
3042+
uses: actions/checkout@v4
3043+
- name: Install Ruby
3044+
uses: ruby/setup-ruby@v1
3045+
with:
3046+
ruby-version: 3.2.5
3047+
bundler-cache: true
3048+
- name: Install gem extension
3049+
run: "./script/bundler_wrapper exec rake extension:install"
3050+
- name: Print extension install report
3051+
run: "[ -e ext/install.report ] && cat ext/install.report || echo 'No ext/install.report
3052+
file found'"
3053+
- name: Print Makefile log file
3054+
run: "[ -f ext/mkmf.log ] && cat ext/mkmf.log || echo 'No ext/mkmf.log file
3055+
found'"
3056+
- name: Run tests
3057+
run: "./script/bundler_wrapper exec rake test"
3058+
env:
3059+
RAILS_ENV: test
3060+
JRUBY_OPTS: ''
3061+
COV: '1'
3062+
BUNDLE_GEMFILE: gemfiles/delayed_job.gemfile
29553063
ruby_3-2-5__dry-monitor_ubuntu-latest:
29563064
name: Ruby 3.2.5 - dry-monitor
29573065
needs: ruby_3-2-5_ubuntu-latest
@@ -3874,6 +3982,33 @@ jobs:
38743982
JRUBY_OPTS: ''
38753983
COV: '1'
38763984
BUNDLE_GEMFILE: gemfiles/capistrano3.gemfile
3985+
ruby_3-1-6__delayed_job_ubuntu-latest:
3986+
name: Ruby 3.1.6 - delayed_job
3987+
needs: ruby_3-1-6_ubuntu-latest
3988+
runs-on: ubuntu-latest
3989+
steps:
3990+
- name: Check out repository
3991+
uses: actions/checkout@v4
3992+
- name: Install Ruby
3993+
uses: ruby/setup-ruby@v1
3994+
with:
3995+
ruby-version: 3.1.6
3996+
bundler-cache: true
3997+
- name: Install gem extension
3998+
run: "./script/bundler_wrapper exec rake extension:install"
3999+
- name: Print extension install report
4000+
run: "[ -e ext/install.report ] && cat ext/install.report || echo 'No ext/install.report
4001+
file found'"
4002+
- name: Print Makefile log file
4003+
run: "[ -f ext/mkmf.log ] && cat ext/mkmf.log || echo 'No ext/mkmf.log file
4004+
found'"
4005+
- name: Run tests
4006+
run: "./script/bundler_wrapper exec rake test"
4007+
env:
4008+
RAILS_ENV: test
4009+
JRUBY_OPTS: ''
4010+
COV: '1'
4011+
BUNDLE_GEMFILE: gemfiles/delayed_job.gemfile
38774012
ruby_3-1-6__dry-monitor_ubuntu-latest:
38784013
name: Ruby 3.1.6 - dry-monitor
38794014
needs: ruby_3-1-6_ubuntu-latest
@@ -4715,6 +4850,33 @@ jobs:
47154850
JRUBY_OPTS: ''
47164851
COV: '1'
47174852
BUNDLE_GEMFILE: gemfiles/capistrano3.gemfile
4853+
ruby_3-0-7__delayed_job_ubuntu-latest:
4854+
name: Ruby 3.0.7 - delayed_job
4855+
needs: ruby_3-0-7_ubuntu-latest
4856+
runs-on: ubuntu-latest
4857+
steps:
4858+
- name: Check out repository
4859+
uses: actions/checkout@v4
4860+
- name: Install Ruby
4861+
uses: ruby/setup-ruby@v1
4862+
with:
4863+
ruby-version: 3.0.7
4864+
bundler-cache: true
4865+
- name: Install gem extension
4866+
run: "./script/bundler_wrapper exec rake extension:install"
4867+
- name: Print extension install report
4868+
run: "[ -e ext/install.report ] && cat ext/install.report || echo 'No ext/install.report
4869+
file found'"
4870+
- name: Print Makefile log file
4871+
run: "[ -f ext/mkmf.log ] && cat ext/mkmf.log || echo 'No ext/mkmf.log file
4872+
found'"
4873+
- name: Run tests
4874+
run: "./script/bundler_wrapper exec rake test"
4875+
env:
4876+
RAILS_ENV: test
4877+
JRUBY_OPTS: ''
4878+
COV: '1'
4879+
BUNDLE_GEMFILE: gemfiles/delayed_job.gemfile
47184880
ruby_3-0-7__dry-monitor_ubuntu-latest:
47194881
name: Ruby 3.0.7 - dry-monitor
47204882
needs: ruby_3-0-7_ubuntu-latest
@@ -5529,6 +5691,33 @@ jobs:
55295691
JRUBY_OPTS: ''
55305692
COV: '1'
55315693
BUNDLE_GEMFILE: gemfiles/capistrano3.gemfile
5694+
ruby_2-7-8__delayed_job_ubuntu-latest:
5695+
name: Ruby 2.7.8 - delayed_job
5696+
needs: ruby_2-7-8_ubuntu-latest
5697+
runs-on: ubuntu-latest
5698+
steps:
5699+
- name: Check out repository
5700+
uses: actions/checkout@v4
5701+
- name: Install Ruby
5702+
uses: ruby/setup-ruby@v1
5703+
with:
5704+
ruby-version: 2.7.8
5705+
bundler-cache: true
5706+
- name: Install gem extension
5707+
run: "./script/bundler_wrapper exec rake extension:install"
5708+
- name: Print extension install report
5709+
run: "[ -e ext/install.report ] && cat ext/install.report || echo 'No ext/install.report
5710+
file found'"
5711+
- name: Print Makefile log file
5712+
run: "[ -f ext/mkmf.log ] && cat ext/mkmf.log || echo 'No ext/mkmf.log file
5713+
found'"
5714+
- name: Run tests
5715+
run: "./script/bundler_wrapper exec rake test"
5716+
env:
5717+
RAILS_ENV: test
5718+
JRUBY_OPTS: ''
5719+
COV: '1'
5720+
BUNDLE_GEMFILE: gemfiles/delayed_job.gemfile
55325721
ruby_2-7-8__faraday-1_ubuntu-latest:
55335722
name: Ruby 2.7.8 - faraday-1
55345723
needs: ruby_2-7-8_ubuntu-latest

build_matrix.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -141,6 +141,7 @@ matrix:
141141
- "3.4.1"
142142
- "3.3.4"
143143
- "jruby-9.4.7.0"
144+
- gem: "delayed_job"
144145
- gem: "dry-monitor"
145146
only:
146147
ruby:

gemfiles/delayed_job.gemfile

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
source "https://rubygems.org"
2+
3+
gem "delayed_job"
4+
gem "ostruct"
5+
6+
gemspec :path => "../"

lib/appsignal/integrations/delayed_job_plugin.rb

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,10 @@ class DelayedJobPlugin < ::Delayed::Plugin
77
extend Appsignal::Hooks::Helpers
88

99
callbacks do |lifecycle|
10+
lifecycle.around(:enqueue) do |job, &block|
11+
enqueue_with_instrumentation(job, block)
12+
end
13+
1014
lifecycle.around(:invoke_job) do |job, &block|
1115
invoke_with_instrumentation(job, block)
1216
end
@@ -16,6 +20,37 @@ class DelayedJobPlugin < ::Delayed::Plugin
1620
end
1721
end
1822

23+
# Records an `enqueue.delayed_job` event so the enqueue shows up under the
24+
# active transaction (e.g. when enqueuing from within a web request or
25+
# another job). An enqueue with no active transaction is a transparent
26+
# pass-through.
27+
def self.enqueue_with_instrumentation(job, block)
28+
# Under Active Job the enqueue is already recorded as an
29+
# `enqueue.active_job` event, so skip recording it again here.
30+
if Appsignal::Transaction.current? &&
31+
Appsignal::Transaction.current.job_enqueue_events_suppressed?
32+
return block.call(job)
33+
end
34+
35+
Appsignal.instrument("enqueue.delayed_job", "enqueue #{enqueue_name(job)} job") do
36+
block.call(job)
37+
end
38+
end
39+
40+
# Titles the enqueue event after the job. The `appsignal_name` override is
41+
# honored verbatim, as it is when naming the perform action. That override
42+
# is a full action name, so an enqueue that uses it reads as
43+
# `enqueue Class#method job` rather than the bare `enqueue Class job`. We
44+
# accept that inconsistency so the enqueue and perform events stay tied to
45+
# the same name for the rare job that sets it.
46+
def self.enqueue_name(job)
47+
payload = job.payload_object
48+
appsignal_name = extract_value(payload, :appsignal_name, nil)
49+
return appsignal_name if appsignal_name.is_a?(String)
50+
51+
job.name
52+
end
53+
1954
def self.invoke_with_instrumentation(job, block)
2055
transaction =
2156
Appsignal::Transaction.create(Appsignal::Transaction::BACKGROUND_JOB)

spec/lib/appsignal/hooks/delayed_job_spec.rb

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,10 @@ def self.plugins
3131
end
3232

3333
context "without delayed job" do
34+
# Hide the constant so this passes whether or not the gem is loaded (it is
35+
# under the `delayed_job` gemfile).
36+
before { hide_const "Delayed::Plugin" }
37+
3438
describe "#dependencies_present?" do
3539
subject { described_class.new.dependencies_present? }
3640

0 commit comments

Comments
 (0)