appsignal 3.12.6-java → 4.0.0.beta.1-java

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (123) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ci.yml +499 -487
  3. data/CHANGELOG.md +151 -0
  4. data/Rakefile +31 -7
  5. data/benchmark.rake +4 -6
  6. data/build_matrix.yml +45 -39
  7. data/ext/agent.rb +27 -27
  8. data/ext/appsignal_extension.c +25 -0
  9. data/gemfiles/rails-7.2.gemfile +11 -0
  10. data/lib/appsignal/check_in/cron.rb +67 -0
  11. data/lib/appsignal/check_in.rb +46 -0
  12. data/lib/appsignal/cli/diagnose.rb +37 -28
  13. data/lib/appsignal/cli/install.rb +5 -1
  14. data/lib/appsignal/config.rb +57 -119
  15. data/lib/appsignal/demo.rb +2 -2
  16. data/lib/appsignal/extension/jruby.rb +14 -0
  17. data/lib/appsignal/helpers/instrumentation.rb +139 -414
  18. data/lib/appsignal/helpers/metrics.rb +0 -16
  19. data/lib/appsignal/hooks/action_cable.rb +8 -8
  20. data/lib/appsignal/hooks/active_job.rb +2 -2
  21. data/lib/appsignal/hooks/at_exit.rb +37 -0
  22. data/lib/appsignal/hooks.rb +1 -16
  23. data/lib/appsignal/integrations/action_cable.rb +2 -2
  24. data/lib/appsignal/integrations/capistrano/appsignal.cap +2 -4
  25. data/lib/appsignal/integrations/capistrano/capistrano_2_tasks.rb +1 -4
  26. data/lib/appsignal/integrations/delayed_job_plugin.rb +3 -3
  27. data/lib/appsignal/integrations/http.rb +2 -7
  28. data/lib/appsignal/integrations/que.rb +2 -2
  29. data/lib/appsignal/integrations/railtie.rb +26 -59
  30. data/lib/appsignal/integrations/rake.rb +2 -2
  31. data/lib/appsignal/integrations/resque.rb +2 -2
  32. data/lib/appsignal/integrations/shoryuken.rb +4 -4
  33. data/lib/appsignal/integrations/sidekiq.rb +3 -3
  34. data/lib/appsignal/integrations/webmachine.rb +2 -2
  35. data/lib/appsignal/loaders.rb +1 -1
  36. data/lib/appsignal/probes.rb +0 -9
  37. data/lib/appsignal/rack/abstract_middleware.rb +4 -26
  38. data/lib/appsignal/rack/event_handler.rb +4 -4
  39. data/lib/appsignal/rack/rails_instrumentation.rb +1 -1
  40. data/lib/appsignal/rack.rb +0 -25
  41. data/lib/appsignal/sample_data.rb +95 -0
  42. data/lib/appsignal/transaction.rb +235 -361
  43. data/lib/appsignal/utils/rails_helper.rb +4 -0
  44. data/lib/appsignal/version.rb +1 -1
  45. data/lib/appsignal.rb +20 -62
  46. data/spec/lib/appsignal/auth_check_spec.rb +1 -1
  47. data/spec/lib/appsignal/capistrano2_spec.rb +1 -1
  48. data/spec/lib/appsignal/capistrano3_spec.rb +53 -13
  49. data/spec/lib/appsignal/{heartbeat_spec.rb → check_in_spec.rb} +45 -36
  50. data/spec/lib/appsignal/cli/demo_spec.rb +7 -27
  51. data/spec/lib/appsignal/cli/diagnose_spec.rb +145 -110
  52. data/spec/lib/appsignal/config_spec.rb +304 -379
  53. data/spec/lib/appsignal/extension_install_failure_spec.rb +5 -1
  54. data/spec/lib/appsignal/extension_spec.rb +5 -1
  55. data/spec/lib/appsignal/hooks/active_support_notifications/instrument_shared_examples.rb +1 -1
  56. data/spec/lib/appsignal/hooks/active_support_notifications/start_finish_shared_examples.rb +1 -2
  57. data/spec/lib/appsignal/hooks/active_support_notifications_spec.rb +1 -0
  58. data/spec/lib/appsignal/hooks/activejob_spec.rb +7 -12
  59. data/spec/lib/appsignal/hooks/at_exit_spec.rb +72 -0
  60. data/spec/lib/appsignal/hooks/gvl_spec.rb +10 -5
  61. data/spec/lib/appsignal/hooks/http_spec.rb +3 -3
  62. data/spec/lib/appsignal/hooks/net_http_spec.rb +3 -3
  63. data/spec/lib/appsignal/hooks/rake_spec.rb +6 -9
  64. data/spec/lib/appsignal/hooks/redis_client_spec.rb +5 -10
  65. data/spec/lib/appsignal/hooks/redis_spec.rb +4 -7
  66. data/spec/lib/appsignal/hooks/resque_spec.rb +3 -5
  67. data/spec/lib/appsignal/hooks_spec.rb +0 -41
  68. data/spec/lib/appsignal/integrations/data_mapper_spec.rb +29 -20
  69. data/spec/lib/appsignal/integrations/delayed_job_plugin_spec.rb +4 -9
  70. data/spec/lib/appsignal/integrations/http_spec.rb +0 -21
  71. data/spec/lib/appsignal/integrations/railtie_spec.rb +179 -157
  72. data/spec/lib/appsignal/integrations/shoryuken_spec.rb +3 -5
  73. data/spec/lib/appsignal/integrations/sidekiq_spec.rb +48 -62
  74. data/spec/lib/appsignal/loaders/hanami_spec.rb +6 -9
  75. data/spec/lib/appsignal/loaders/padrino_spec.rb +6 -10
  76. data/spec/lib/appsignal/loaders/sinatra_spec.rb +6 -9
  77. data/spec/lib/appsignal/loaders_spec.rb +8 -1
  78. data/spec/lib/appsignal/marker_spec.rb +1 -1
  79. data/spec/lib/appsignal/probes_spec.rb +4 -83
  80. data/spec/lib/appsignal/rack/abstract_middleware_spec.rb +4 -63
  81. data/spec/lib/appsignal/rack/event_handler_spec.rb +18 -15
  82. data/spec/lib/appsignal/rack/rails_instrumentation_spec.rb +3 -11
  83. data/spec/lib/appsignal/rack/sinatra_instrumentation_spec.rb +4 -5
  84. data/spec/lib/appsignal/sample_data_spec.rb +174 -0
  85. data/spec/lib/appsignal/transaction_spec.rb +791 -1031
  86. data/spec/lib/appsignal/transmitter_spec.rb +6 -8
  87. data/spec/lib/appsignal_spec.rb +294 -643
  88. data/spec/spec_helper.rb +1 -3
  89. data/spec/support/fixtures/projects/valid/config/appsignal.yml +4 -7
  90. data/spec/support/fixtures/projects/valid_with_rails_app/config/application.rb +16 -0
  91. data/spec/support/fixtures/projects/valid_with_rails_app/config/appsignal.yml +56 -0
  92. data/spec/support/fixtures/projects/valid_with_rails_app/config/environment.rb +5 -0
  93. data/spec/support/helpers/api_request_helper.rb +3 -2
  94. data/spec/support/helpers/config_helpers.rb +41 -11
  95. data/spec/support/helpers/dependency_helper.rb +8 -0
  96. data/spec/support/helpers/log_helpers.rb +1 -0
  97. data/spec/support/helpers/rails_helper.rb +6 -6
  98. data/spec/support/helpers/transaction_helpers.rb +2 -24
  99. data/spec/support/matchers/transaction.rb +3 -3
  100. data/spec/support/mocks/appsignal_mock.rb +3 -3
  101. data/spec/support/mocks/mock_probe.rb +2 -0
  102. data/spec/support/testing.rb +2 -2
  103. metadata +14 -23
  104. data/gemfiles/que_beta.gemfile +0 -5
  105. data/lib/appsignal/heartbeat.rb +0 -59
  106. data/lib/appsignal/helpers/heartbeats.rb +0 -44
  107. data/lib/appsignal/integrations/grape.rb +0 -35
  108. data/lib/appsignal/integrations/hanami.rb +0 -13
  109. data/lib/appsignal/integrations/padrino.rb +0 -13
  110. data/lib/appsignal/integrations/sinatra.rb +0 -13
  111. data/lib/appsignal/rack/generic_instrumentation.rb +0 -22
  112. data/lib/appsignal/rack/streaming_listener.rb +0 -28
  113. data/spec/lib/appsignal/integrations/grape_spec.rb +0 -36
  114. data/spec/lib/appsignal/integrations/hanami_spec.rb +0 -17
  115. data/spec/lib/appsignal/integrations/padrino_spec.rb +0 -15
  116. data/spec/lib/appsignal/integrations/sinatra_spec.rb +0 -15
  117. data/spec/lib/appsignal/rack/generic_instrumentation_spec.rb +0 -81
  118. data/spec/lib/appsignal/rack/streaming_listener_spec.rb +0 -69
  119. data/spec/support/fixtures/projects/valid/config/environments/development.rb +0 -0
  120. data/spec/support/fixtures/projects/valid/config/environments/production.rb +0 -0
  121. data/spec/support/fixtures/projects/valid/config/environments/test.rb +0 -0
  122. data/spec/support/rails/my_app.rb +0 -6
  123. /data/spec/support/fixtures/projects/{valid/config/application.rb → valid_with_rails_app/log/.gitkeep} +0 -0
@@ -6,7 +6,11 @@ describe Appsignal::Extension, :extension_installation_failure do
6
6
  expect(stderr).to include("ERROR: AppSignal failed to load extension")
7
7
  error_message =
8
8
  if DependencyHelper.running_jruby?
9
- "cannot open shared object file"
9
+ if DependencyHelper.macos?
10
+ "Could not open library"
11
+ else
12
+ "cannot open shared object file"
13
+ end
10
14
  else
11
15
  "LoadError: cannot load such file"
12
16
  end
@@ -49,7 +49,7 @@ describe Appsignal::Extension do
49
49
 
50
50
  context "with a valid config" do
51
51
  before do
52
- project_fixture_config.write_to_environment
52
+ build_config.write_to_environment
53
53
  end
54
54
 
55
55
  it "should have a start and stop method" do
@@ -100,6 +100,10 @@ describe Appsignal::Extension do
100
100
  subject.finish(0)
101
101
  end
102
102
 
103
+ it "should have a duplicate method" do
104
+ subject.duplicate("request_id")
105
+ end
106
+
103
107
  it "should have a complete method" do
104
108
  subject.complete
105
109
  end
@@ -88,12 +88,12 @@ shared_examples "activesupport instrument override" do
88
88
 
89
89
  context "when a transaction is completed in an instrumented block" do
90
90
  it "does not complete the ActiveSupport::Notifications.instrument event" do
91
- expect(transaction).to receive(:complete)
92
91
  as.instrument("sql.active_record", :sql => "SQL") do
93
92
  Appsignal::Transaction.complete_current!
94
93
  end
95
94
 
96
95
  expect(transaction).to_not include_events
96
+ expect(transaction).to be_completed
97
97
  end
98
98
  end
99
99
  end
@@ -36,13 +36,12 @@ shared_examples "activesupport start finish override" do
36
36
 
37
37
  context "when a transaction is completed in an instrumented block" do
38
38
  it "does not complete the ActiveSupport::Notifications.instrument event" do
39
- expect(transaction).to receive(:complete)
40
-
41
39
  instrumenter.start("sql.active_record", {})
42
40
  Appsignal::Transaction.complete_current!
43
41
  instrumenter.finish("sql.active_record", {})
44
42
 
45
43
  expect(transaction).to_not include_events
44
+ expect(transaction).to be_completed
46
45
  end
47
46
  end
48
47
  end
@@ -10,6 +10,7 @@ describe Appsignal::Hooks::ActiveSupportNotificationsHook do
10
10
  set_current_transaction(transaction)
11
11
  as.notifier = notifier
12
12
  end
13
+ around { |example| keep_transactions { example.run } }
13
14
 
14
15
  describe "#dependencies_present?" do
15
16
  subject { described_class.new.dependencies_present? }
@@ -34,7 +34,6 @@ if DependencyHelper.active_job_present?
34
34
  let(:time) { Time.parse("2001-01-01 10:00:00UTC") }
35
35
  let(:namespace) { Appsignal::Transaction::BACKGROUND_JOB }
36
36
  let(:queue) { "default" }
37
- let(:log) { StringIO.new }
38
37
  let(:parameterized_given_args) do
39
38
  {
40
39
  :foo => "Foo",
@@ -72,11 +71,11 @@ if DependencyHelper.active_job_present?
72
71
  ["perform_start.active_job", "perform.active_job"]
73
72
  end
74
73
  end
74
+ let(:options) { {} }
75
75
  before do
76
76
  ActiveJob::Base.queue_adapter = :inline
77
77
 
78
- start_agent
79
- Appsignal.internal_logger = test_logger(log)
78
+ start_agent(:options => options)
80
79
  class ActiveJobTestJob < ActiveJob::Base
81
80
  def perform(*_args)
82
81
  end
@@ -209,10 +208,9 @@ if DependencyHelper.active_job_present?
209
208
  end
210
209
 
211
210
  context "with activejob_report_errors set to none" do
212
- it "does not report the error" do
213
- start_agent("production")
214
- Appsignal.config[:activejob_report_errors] = "none"
211
+ let(:options) { { :activejob_report_errors => "none" } }
215
212
 
213
+ it "does not report the error" do
216
214
  allow(Appsignal).to receive(:increment_counter)
217
215
  tags = { :queue => queue }
218
216
  expect(Appsignal).to receive(:increment_counter)
@@ -228,10 +226,7 @@ if DependencyHelper.active_job_present?
228
226
 
229
227
  if DependencyHelper.rails_version >= Gem::Version.new("7.1.0")
230
228
  context "with activejob_report_errors set to discard" do
231
- before do
232
- start_agent("production")
233
- Appsignal.config[:activejob_report_errors] = "discard"
234
- end
229
+ let(:options) { { :activejob_report_errors => "discard" } }
235
230
 
236
231
  it "does not report error on first failure" do
237
232
  with_test_adapter do
@@ -351,9 +346,9 @@ if DependencyHelper.active_job_present?
351
346
  end
352
347
 
353
348
  context "with params" do
349
+ let(:options) { { :filter_parameters => ["foo"] } }
350
+
354
351
  it "filters the configured params" do
355
- start_agent("production")
356
- Appsignal.config[:filter_parameters] = ["foo"]
357
352
  queue_job(ActiveJobTestJob, method_given_args)
358
353
 
359
354
  transaction = last_transaction
@@ -0,0 +1,72 @@
1
+ describe Appsignal::Hooks::AtExit do
2
+ describe ".install" do
3
+ before { start_agent(:options => options) }
4
+
5
+ context "with :enable_at_exit_reporter == true" do
6
+ let(:options) { { :enable_at_exit_reporter => true } }
7
+
8
+ it "installs the at_exit hook" do
9
+ expect(Appsignal::Hooks::AtExit::AtExitCallback).to receive(:call)
10
+
11
+ expect(Kernel).to receive(:at_exit).with(no_args) do |*_args, &block|
12
+ block.call
13
+ end
14
+
15
+ described_class.new.install
16
+ end
17
+ end
18
+
19
+ context "with :enable_at_exit_reporter == false" do
20
+ let(:options) { { :enable_at_exit_reporter => false } }
21
+
22
+ it "doesn't install the at_exit hook" do
23
+ expect(Kernel).to_not receive(:at_exit)
24
+ end
25
+ end
26
+ end
27
+ end
28
+
29
+ describe Appsignal::Hooks::AtExit::AtExitCallback do
30
+ around { |example| keep_transactions { example.run } }
31
+ before { start_agent(:options => { :enable_at_exit_reporter => true }) }
32
+
33
+ def with_error(error_class, error_message)
34
+ raise error_class, error_message
35
+ rescue error_class => error
36
+ yield error
37
+ end
38
+
39
+ def call_callback
40
+ Appsignal::Hooks::AtExit::AtExitCallback.call
41
+ end
42
+
43
+ it "reports an error if there's an unhandled error" do
44
+ expect do
45
+ with_error(ExampleException, "error message") do
46
+ call_callback
47
+ end
48
+ end.to change { created_transactions.count }.by(1)
49
+
50
+ transaction = last_transaction
51
+ expect(transaction).to have_namespace("unhandled")
52
+ expect(transaction).to have_error("ExampleException", "error message")
53
+ end
54
+
55
+ it "calls Appsignal.stop" do
56
+ expect(Appsignal).to receive(:stop).with("at_exit")
57
+ with_error(ExampleException, "error message") do
58
+ call_callback
59
+ end
60
+ end
61
+
62
+ it "doesn't report the error if is also the last error reported" do
63
+ with_error(ExampleException, "error message") do |error|
64
+ Appsignal.report_error(error)
65
+ expect(created_transactions.count).to eq(1)
66
+
67
+ expect do
68
+ call_callback
69
+ end.to_not change { created_transactions.count }.from(1)
70
+ end
71
+ end
72
+ end
@@ -7,8 +7,9 @@ describe Appsignal::Hooks::GvlHook do
7
7
  end
8
8
  end
9
9
  else
10
+ let(:options) { {} }
10
11
  before do
11
- start_agent
12
+ start_agent(:options => options)
12
13
  end
13
14
 
14
15
  def expect_gvltools_require
@@ -100,8 +101,9 @@ describe Appsignal::Hooks::GvlHook do
100
101
 
101
102
  describe "#install" do
102
103
  context "with enable_gvl_global_timer" do
104
+ let(:options) { { :enable_gvl_global_timer => true } }
105
+
103
106
  it "enables the GVL global timer" do
104
- Appsignal.config[:enable_gvl_global_timer] = true
105
107
  expect(::GVLTools::GlobalTimer).to receive(:enable)
106
108
 
107
109
  described_class.new.install
@@ -109,8 +111,9 @@ describe Appsignal::Hooks::GvlHook do
109
111
  end
110
112
 
111
113
  context "without enable_gvl_global_timer" do
114
+ let(:options) { { :enable_gvl_global_timer => false } }
115
+
112
116
  it "does not enable the GVL global timer" do
113
- Appsignal.config[:enable_gvl_global_timer] = false
114
117
  expect(::GVLTools::GlobalTimer).not_to receive(:enable)
115
118
 
116
119
  described_class.new.install
@@ -118,8 +121,9 @@ describe Appsignal::Hooks::GvlHook do
118
121
  end
119
122
 
120
123
  context "with enable_gvl_waiting_threads" do
124
+ let(:options) { { :enable_gvl_waiting_threads => true } }
125
+
121
126
  it "enables the GVL waiting threads" do
122
- Appsignal.config[:enable_gvl_global_timer] = true
123
127
  expect(::GVLTools::WaitingThreads).to receive(:enable)
124
128
 
125
129
  described_class.new.install
@@ -127,8 +131,9 @@ describe Appsignal::Hooks::GvlHook do
127
131
  end
128
132
 
129
133
  context "without enable_gvl_waiting_threads" do
134
+ let(:options) { { :enable_gvl_waiting_threads => false } }
135
+
130
136
  it "does not enable the GVL waiting threads" do
131
- Appsignal.config[:enable_gvl_waiting_threads] = false
132
137
  expect(::GVLTools::WaitingThreads).not_to receive(:enable)
133
138
 
134
139
  described_class.new.install
@@ -1,7 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  describe Appsignal::Hooks::HttpHook do
4
- before { start_agent }
4
+ let(:options) { {} }
5
+ before { start_agent(:options => options) }
5
6
 
6
7
  if DependencyHelper.http_present?
7
8
  context "with instrument_http_rb set to true" do
@@ -18,8 +19,7 @@ describe Appsignal::Hooks::HttpHook do
18
19
  end
19
20
 
20
21
  context "with instrument_http_rb set to false" do
21
- before { Appsignal.config.config_hash[:instrument_http_rb] = false }
22
- after { Appsignal.config.config_hash[:instrument_http_rb] = true }
22
+ let(:options) { { :instrument_http_rb => false } }
23
23
 
24
24
  describe "#dependencies_present?" do
25
25
  subject { described_class.new.dependencies_present? }
@@ -1,5 +1,6 @@
1
1
  describe Appsignal::Hooks::NetHttpHook do
2
- before { start_agent }
2
+ let(:options) { {} }
3
+ before { start_agent(:options => options) }
3
4
 
4
5
  describe "#dependencies_present?" do
5
6
  subject { described_class.new.dependencies_present? }
@@ -9,8 +10,7 @@ describe Appsignal::Hooks::NetHttpHook do
9
10
  end
10
11
 
11
12
  context "with Net::HTTP instrumentation disabled" do
12
- before { Appsignal.config.config_hash[:instrument_net_http] = false }
13
- after { Appsignal.config.config_hash[:instrument_net_http] = true }
13
+ let(:options) { { :instrument_net_http => false } }
14
14
 
15
15
  it { is_expected.to be_falsy }
16
16
  end
@@ -4,8 +4,9 @@ describe Appsignal::Hooks::RakeHook do
4
4
  let(:helper) { Appsignal::Integrations::RakeIntegrationHelper }
5
5
  let(:task) { Rake::Task.new("task:name", Rake::Application.new) }
6
6
  let(:arguments) { Rake::TaskArguments.new(["foo"], ["bar"]) }
7
+ let(:options) { {} }
7
8
  before do
8
- start_agent
9
+ start_agent(:options => options)
9
10
  allow(Kernel).to receive(:at_exit)
10
11
  end
11
12
  around { |example| keep_transactions { example.run } }
@@ -30,9 +31,7 @@ describe Appsignal::Hooks::RakeHook do
30
31
  end
31
32
 
32
33
  context "with :enable_rake_performance_instrumentation == false" do
33
- before do
34
- Appsignal.config[:enable_rake_performance_instrumentation] = false
35
- end
34
+ let(:options) { { :enable_rake_performance_instrumentation => false } }
36
35
 
37
36
  it "creates no transaction" do
38
37
  expect { perform }.to_not(change { created_transactions.count })
@@ -49,16 +48,14 @@ describe Appsignal::Hooks::RakeHook do
49
48
  end
50
49
 
51
50
  context "with :enable_rake_performance_instrumentation == true" do
52
- before do
53
- Appsignal.config[:enable_rake_performance_instrumentation] = true
54
- end
51
+ let(:options) { { :enable_rake_performance_instrumentation => true } }
55
52
 
56
53
  it "creates a transaction" do
57
54
  expect { perform }.to(change { created_transactions.count }.by(1))
58
55
 
59
56
  transaction = last_transaction
60
57
  expect(transaction).to have_id
61
- expect(transaction).to have_namespace(Appsignal::Transaction::BACKGROUND_JOB)
58
+ expect(transaction).to have_namespace("rake")
62
59
  expect(transaction).to have_action("task:name")
63
60
  expect(transaction).to_not have_error
64
61
  expect(transaction).to include_params("foo" => "bar")
@@ -91,7 +88,7 @@ describe Appsignal::Hooks::RakeHook do
91
88
 
92
89
  transaction = last_transaction
93
90
  expect(transaction).to have_id
94
- expect(transaction).to have_namespace(Appsignal::Transaction::BACKGROUND_JOB)
91
+ expect(transaction).to have_namespace("rake")
95
92
  expect(transaction).to have_action("task:name")
96
93
  expect(transaction).to have_error("ExampleException", "error message")
97
94
  expect(transaction).to include_params("foo" => "bar")
@@ -1,6 +1,7 @@
1
1
  describe Appsignal::Hooks::RedisClientHook do
2
+ let(:options) { {} }
2
3
  before do
3
- start_agent
4
+ start_agent(:options => options)
4
5
  end
5
6
 
6
7
  if DependencyHelper.redis_client_present?
@@ -30,9 +31,7 @@ describe Appsignal::Hooks::RedisClientHook do
30
31
 
31
32
  context "with rest-client gem" do
32
33
  describe "integration" do
33
- before do
34
- Appsignal.config.config_hash[:instrument_redis] = true
35
- end
34
+ let(:options) { { :instrument_redis => true } }
36
35
 
37
36
  context "install" do
38
37
  before do
@@ -115,9 +114,7 @@ describe Appsignal::Hooks::RedisClientHook do
115
114
  if DependencyHelper.hiredis_client_present?
116
115
  context "with hiredis driver" do
117
116
  describe "integration" do
118
- before do
119
- Appsignal.config.config_hash[:instrument_redis] = true
120
- end
117
+ let(:options) { { :instrument_redis => true } }
121
118
 
122
119
  context "install" do
123
120
  before do
@@ -200,9 +197,7 @@ describe Appsignal::Hooks::RedisClientHook do
200
197
  end
201
198
 
202
199
  context "with instrumentation disabled" do
203
- before do
204
- Appsignal.config.config_hash[:instrument_redis] = false
205
- end
200
+ let(:options) { { :instrument_redis => false } }
206
201
 
207
202
  describe "#dependencies_present?" do
208
203
  subject { described_class.new.dependencies_present? }
@@ -1,5 +1,6 @@
1
1
  describe Appsignal::Hooks::RedisHook do
2
- before { start_agent }
2
+ let(:options) { {} }
3
+ before { start_agent(:options => options) }
3
4
 
4
5
  if DependencyHelper.redis_present?
5
6
  context "with redis" do
@@ -22,9 +23,7 @@ describe Appsignal::Hooks::RedisHook do
22
23
  end
23
24
 
24
25
  describe "integration" do
25
- before do
26
- Appsignal.config.config_hash[:instrument_redis] = true
27
- end
26
+ let(:options) { { :instrument_redis => true } }
28
27
 
29
28
  context "install" do
30
29
  before do
@@ -103,9 +102,7 @@ describe Appsignal::Hooks::RedisHook do
103
102
  end
104
103
 
105
104
  context "with instrumentation disabled" do
106
- before do
107
- Appsignal.config.config_hash[:instrument_redis] = false
108
- end
105
+ let(:options) { { :instrument_redis => false } }
109
106
 
110
107
  describe "#dependencies_present?" do
111
108
  subject { described_class.new.dependencies_present? }
@@ -25,8 +25,9 @@ describe Appsignal::Hooks::ResqueHook do
25
25
 
26
26
  let(:queue) { "default" }
27
27
  let(:namespace) { Appsignal::Transaction::BACKGROUND_JOB }
28
+ let(:options) { {} }
28
29
  before do
29
- start_agent
30
+ start_agent(:options => options)
30
31
 
31
32
  class ResqueTestJob
32
33
  def self.perform(*_args)
@@ -82,10 +83,7 @@ describe Appsignal::Hooks::ResqueHook do
82
83
  end
83
84
 
84
85
  context "with arguments" do
85
- before do
86
- start_agent("production")
87
- Appsignal.config[:filter_parameters] = ["foo"]
88
- end
86
+ let(:options) { { :filter_parameters => ["foo"] } }
89
87
 
90
88
  it "filters out configured arguments" do
91
89
  perform_rescue_job(
@@ -82,47 +82,6 @@ describe Appsignal::Hooks do
82
82
  expect(Appsignal::Hooks.hooks[:mock_error_hook].installed?).to be_falsy
83
83
  Appsignal::Hooks.hooks.delete(:mock_error_hook)
84
84
  end
85
-
86
- describe "missing constants" do
87
- let(:err_stream) { std_stream }
88
- let(:stderr) { err_stream.read }
89
- let(:log_stream) { std_stream }
90
- let(:log) { log_contents(log_stream) }
91
- before do
92
- Appsignal.internal_logger = test_logger(log_stream)
93
- end
94
-
95
- def call_constant(&block)
96
- capture_std_streams(std_stream, err_stream, &block)
97
- end
98
-
99
- describe "SidekiqPlugin" do
100
- it "logs a deprecation message and returns the new constant" do
101
- constant = call_constant { Appsignal::Hooks::SidekiqPlugin }
102
-
103
- expect(constant).to eql(Appsignal::Integrations::SidekiqMiddleware)
104
- expect(constant.name).to eql("Appsignal::Integrations::SidekiqMiddleware")
105
-
106
- deprecation_message =
107
- "The constant Appsignal::Hooks::SidekiqPlugin has been deprecated. " \
108
- "Please update the constant name to Appsignal::Integrations::SidekiqMiddleware " \
109
- "in the following file to remove this message.\n#{__FILE__}:"
110
- expect(stderr).to include "appsignal WARNING: #{deprecation_message}"
111
- expect(log).to contains_log :warn, deprecation_message
112
- end
113
- end
114
-
115
- describe "other constant" do
116
- it "raises a NameError like Ruby normally does" do
117
- expect do
118
- call_constant { Appsignal::Hooks::Unknown }
119
- end.to raise_error(NameError)
120
-
121
- expect(stderr).to be_empty
122
- expect(log).to be_empty
123
- end
124
- end
125
- end
126
85
  end
127
86
 
128
87
  describe Appsignal::Hooks::Helpers do
@@ -7,11 +7,11 @@ describe Appsignal::Hooks::DataMapperLogListener do
7
7
  end
8
8
 
9
9
  describe "#log" do
10
- let(:transaction) { double }
10
+ let(:transaction) { http_request_transaction }
11
11
  let(:message) do
12
12
  double(
13
13
  :query => "SELECT * from users",
14
- :duration => 100
14
+ :duration => 100_000_000 # nanoseconds
15
15
  )
16
16
  end
17
17
  let(:connection_class) do
@@ -24,20 +24,29 @@ describe Appsignal::Hooks::DataMapperLogListener do
24
24
  end
25
25
  end
26
26
  end
27
+ before do
28
+ start_agent
29
+ set_current_transaction(transaction)
30
+ end
31
+ around { |example| keep_transactions { example.run } }
32
+
33
+ def log_message
34
+ connection_class.new.log(message)
35
+ end
27
36
 
28
- before { allow(Appsignal::Transaction).to receive(:current) { transaction } }
37
+ it "records the log entry in an event" do
38
+ log_message
29
39
 
30
- it "should record the log entry in an event" do
31
- expect(transaction).to receive(:record_event).with(
32
- "query.data_mapper",
33
- "DataMapper Query",
34
- "SELECT * from users",
35
- 100,
36
- Appsignal::EventFormatter::SQL_BODY_FORMAT
40
+ expect(transaction).to include_event(
41
+ "name" => "query.data_mapper",
42
+ "title" => "DataMapper Query",
43
+ "body" => "SELECT * from users",
44
+ "body_format" => Appsignal::EventFormatter::SQL_BODY_FORMAT,
45
+ "duration" => 100.0
37
46
  )
38
47
  end
39
48
 
40
- context "when scheme is not sql-like" do
49
+ context "when the scheme is not sql-like" do
41
50
  let(:connection_class) do
42
51
  module DataObjects
43
52
  module MongoDB
@@ -49,17 +58,17 @@ describe Appsignal::Hooks::DataMapperLogListener do
49
58
  end
50
59
  end
51
60
 
52
- it "should record the log entry in an event without body" do
53
- expect(transaction).to receive(:record_event).with(
54
- "query.data_mapper",
55
- "DataMapper Query",
56
- "",
57
- 100,
58
- Appsignal::EventFormatter::DEFAULT
61
+ it "records the log entry in an event without body" do
62
+ log_message
63
+
64
+ expect(transaction).to include_event(
65
+ "name" => "query.data_mapper",
66
+ "title" => "DataMapper Query",
67
+ "body" => "",
68
+ "body_format" => Appsignal::EventFormatter::DEFAULT,
69
+ "duration" => 100.0
59
70
  )
60
71
  end
61
72
  end
62
-
63
- after { connection_class.new.log(message) }
64
73
  end
65
74
  end
@@ -15,7 +15,8 @@ describe "Appsignal::Integrations::DelayedJobHook" do
15
15
  require "appsignal/integrations/delayed_job_plugin"
16
16
  end
17
17
  after(:context) { Object.send(:remove_const, :Delayed) }
18
- before { start_agent }
18
+ let(:options) { {} }
19
+ before { start_agent(:options => options) }
19
20
 
20
21
  # We haven't found a way to test the hooks, we'll have to do that manually
21
22
 
@@ -82,10 +83,7 @@ describe "Appsignal::Integrations::DelayedJobHook" do
82
83
  end
83
84
 
84
85
  context "with parameter filtering" do
85
- before do
86
- start_agent("production")
87
- Appsignal.config[:filter_parameters] = ["foo"]
88
- end
86
+ let(:options) { { :filter_parameters => ["foo"] } }
89
87
 
90
88
  it "filters selected arguments" do
91
89
  perform
@@ -271,10 +269,7 @@ describe "Appsignal::Integrations::DelayedJobHook" do
271
269
  end
272
270
 
273
271
  context "with parameter filtering" do
274
- before do
275
- start_agent("production")
276
- Appsignal.config[:filter_parameters] = ["foo"]
277
- end
272
+ let(:options) { { :filter_parameters => ["foo"] } }
278
273
 
279
274
  it "filters selected arguments" do
280
275
  perform
@@ -67,27 +67,6 @@ if DependencyHelper.http_present?
67
67
  end
68
68
  end
69
69
 
70
- context "with an HTTP exception" do
71
- let(:error) { ExampleException.new("oh no!") }
72
-
73
- it "reports the exception and re-raises it" do
74
- stub_request(:get, "https://www.google.com").and_raise(error)
75
-
76
- expect do
77
- HTTP.get("https://www.google.com")
78
- end.to raise_error(ExampleException)
79
-
80
- expect(transaction).to have_namespace(Appsignal::Transaction::HTTP_REQUEST)
81
- expect(transaction).to include_event(
82
- "body" => "",
83
- "body_format" => Appsignal::EventFormatter::DEFAULT,
84
- "name" => "request.http_rb",
85
- "title" => "GET https://www.google.com"
86
- )
87
- expect(transaction).to have_error(error.class.name, error.message)
88
- end
89
- end
90
-
91
70
  context "with various URI objects" do
92
71
  it "parses an object responding to #to_s" do
93
72
  request_uri = Struct.new(:uri) do