appsignal 4.0.6 → 4.0.8

Sign up to get free protection for your applications and to get access to all the features.
Files changed (202) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +20 -0
  3. data/Rakefile +9 -9
  4. data/appsignal.gemspec +22 -1
  5. data/ext/agent.rb +27 -27
  6. data/lib/appsignal/check_in.rb +1 -1
  7. data/lib/appsignal/config.rb +1 -3
  8. data/lib/appsignal/integrations/resque.rb +1 -6
  9. data/lib/appsignal/utils/hash_sanitizer.rb +4 -0
  10. data/lib/appsignal/version.rb +1 -1
  11. data/lib/appsignal.rb +10 -8
  12. metadata +2 -192
  13. data/.github/ISSUE_TEMPLATE/bug_report.md +0 -31
  14. data/.github/ISSUE_TEMPLATE/chore.md +0 -14
  15. data/.github/workflows/ci.yml +0 -3285
  16. data/.github/workflows/create_release_from_tag.yml +0 -62
  17. data/.gitignore +0 -35
  18. data/.gitmodules +0 -3
  19. data/.rspec +0 -4
  20. data/.yardopts +0 -8
  21. data/benchmark.rake +0 -139
  22. data/gemfiles/capistrano2.gemfile +0 -6
  23. data/gemfiles/capistrano3.gemfile +0 -7
  24. data/gemfiles/dry-monitor.gemfile +0 -5
  25. data/gemfiles/grape.gemfile +0 -5
  26. data/gemfiles/hanami-2.0.gemfile +0 -7
  27. data/gemfiles/hanami-2.1.gemfile +0 -7
  28. data/gemfiles/http5.gemfile +0 -5
  29. data/gemfiles/no_dependencies.gemfile +0 -10
  30. data/gemfiles/padrino.gemfile +0 -7
  31. data/gemfiles/psych-3.gemfile +0 -5
  32. data/gemfiles/psych-4.gemfile +0 -5
  33. data/gemfiles/que-1.gemfile +0 -5
  34. data/gemfiles/que-2.gemfile +0 -5
  35. data/gemfiles/rails-6.0.gemfile +0 -10
  36. data/gemfiles/rails-6.1.gemfile +0 -11
  37. data/gemfiles/rails-7.0.gemfile +0 -11
  38. data/gemfiles/rails-7.1.gemfile +0 -11
  39. data/gemfiles/rails-7.2.gemfile +0 -11
  40. data/gemfiles/redis-4.gemfile +0 -5
  41. data/gemfiles/redis-5.gemfile +0 -6
  42. data/gemfiles/resque-2.gemfile +0 -6
  43. data/gemfiles/sequel.gemfile +0 -10
  44. data/gemfiles/sinatra.gemfile +0 -5
  45. data/gemfiles/webmachine1.gemfile +0 -7
  46. data/gemfiles/webmachine2.gemfile +0 -6
  47. data/mono.yml +0 -16
  48. data/spec/.rubocop.yml +0 -7
  49. data/spec/lib/appsignal/auth_check_spec.rb +0 -84
  50. data/spec/lib/appsignal/capistrano2_spec.rb +0 -227
  51. data/spec/lib/appsignal/capistrano3_spec.rb +0 -284
  52. data/spec/lib/appsignal/check_in/cron_spec.rb +0 -210
  53. data/spec/lib/appsignal/check_in/scheduler_spec.rb +0 -557
  54. data/spec/lib/appsignal/cli/demo_spec.rb +0 -46
  55. data/spec/lib/appsignal/cli/diagnose/paths_spec.rb +0 -16
  56. data/spec/lib/appsignal/cli/diagnose/utils_spec.rb +0 -86
  57. data/spec/lib/appsignal/cli/diagnose_spec.rb +0 -1553
  58. data/spec/lib/appsignal/cli/helpers_spec.rb +0 -179
  59. data/spec/lib/appsignal/cli/install_spec.rb +0 -848
  60. data/spec/lib/appsignal/cli_spec.rb +0 -56
  61. data/spec/lib/appsignal/config_spec.rb +0 -1380
  62. data/spec/lib/appsignal/demo_spec.rb +0 -83
  63. data/spec/lib/appsignal/environment_spec.rb +0 -190
  64. data/spec/lib/appsignal/event_formatter/action_view/render_formatter_spec.rb +0 -60
  65. data/spec/lib/appsignal/event_formatter/active_record/instantiation_formatter_spec.rb +0 -21
  66. data/spec/lib/appsignal/event_formatter/active_record/sql_formatter_spec.rb +0 -21
  67. data/spec/lib/appsignal/event_formatter/elastic_search/search_formatter_spec.rb +0 -52
  68. data/spec/lib/appsignal/event_formatter/faraday/request_formatter_spec.rb +0 -21
  69. data/spec/lib/appsignal/event_formatter/mongo_ruby_driver/query_formatter_spec.rb +0 -84
  70. data/spec/lib/appsignal/event_formatter/rom/sql_formatter_spec.rb +0 -22
  71. data/spec/lib/appsignal/event_formatter/sequel/sql_formatter_spec.rb +0 -30
  72. data/spec/lib/appsignal/event_formatter/view_component/render_formatter_spec.rb +0 -41
  73. data/spec/lib/appsignal/event_formatter_spec.rb +0 -193
  74. data/spec/lib/appsignal/extension/jruby_spec.rb +0 -46
  75. data/spec/lib/appsignal/extension_install_failure_spec.rb +0 -20
  76. data/spec/lib/appsignal/extension_spec.rb +0 -178
  77. data/spec/lib/appsignal/garbage_collection_spec.rb +0 -98
  78. data/spec/lib/appsignal/hooks/action_cable_spec.rb +0 -345
  79. data/spec/lib/appsignal/hooks/action_mailer_spec.rb +0 -55
  80. data/spec/lib/appsignal/hooks/active_support_notifications/finish_with_state_shared_examples.rb +0 -23
  81. data/spec/lib/appsignal/hooks/active_support_notifications/instrument_shared_examples.rb +0 -99
  82. data/spec/lib/appsignal/hooks/active_support_notifications/start_finish_shared_examples.rb +0 -47
  83. data/spec/lib/appsignal/hooks/active_support_notifications_spec.rb +0 -47
  84. data/spec/lib/appsignal/hooks/activejob_spec.rb +0 -650
  85. data/spec/lib/appsignal/hooks/at_exit_spec.rb +0 -105
  86. data/spec/lib/appsignal/hooks/celluloid_spec.rb +0 -40
  87. data/spec/lib/appsignal/hooks/data_mapper_spec.rb +0 -40
  88. data/spec/lib/appsignal/hooks/delayed_job_spec.rb +0 -38
  89. data/spec/lib/appsignal/hooks/dry_monitor_spec.rb +0 -83
  90. data/spec/lib/appsignal/hooks/excon_spec.rb +0 -67
  91. data/spec/lib/appsignal/hooks/gvl_spec.rb +0 -145
  92. data/spec/lib/appsignal/hooks/http_spec.rb +0 -37
  93. data/spec/lib/appsignal/hooks/mongo_ruby_driver_spec.rb +0 -46
  94. data/spec/lib/appsignal/hooks/mri_spec.rb +0 -23
  95. data/spec/lib/appsignal/hooks/net_http_spec.rb +0 -18
  96. data/spec/lib/appsignal/hooks/passenger_spec.rb +0 -30
  97. data/spec/lib/appsignal/hooks/puma_spec.rb +0 -80
  98. data/spec/lib/appsignal/hooks/que_spec.rb +0 -19
  99. data/spec/lib/appsignal/hooks/rake_spec.rb +0 -144
  100. data/spec/lib/appsignal/hooks/redis_client_spec.rb +0 -218
  101. data/spec/lib/appsignal/hooks/redis_spec.rb +0 -124
  102. data/spec/lib/appsignal/hooks/resque_spec.rb +0 -27
  103. data/spec/lib/appsignal/hooks/sequel_spec.rb +0 -44
  104. data/spec/lib/appsignal/hooks/shoryuken_spec.rb +0 -29
  105. data/spec/lib/appsignal/hooks/sidekiq_spec.rb +0 -115
  106. data/spec/lib/appsignal/hooks/unicorn_spec.rb +0 -63
  107. data/spec/lib/appsignal/hooks/webmachine_spec.rb +0 -24
  108. data/spec/lib/appsignal/hooks_spec.rb +0 -124
  109. data/spec/lib/appsignal/integrations/data_mapper_spec.rb +0 -74
  110. data/spec/lib/appsignal/integrations/delayed_job_plugin_spec.rb +0 -454
  111. data/spec/lib/appsignal/integrations/http_spec.rb +0 -111
  112. data/spec/lib/appsignal/integrations/mongo_ruby_driver_spec.rb +0 -154
  113. data/spec/lib/appsignal/integrations/net_http_spec.rb +0 -33
  114. data/spec/lib/appsignal/integrations/object_spec.rb +0 -347
  115. data/spec/lib/appsignal/integrations/puma_spec.rb +0 -150
  116. data/spec/lib/appsignal/integrations/que_spec.rb +0 -187
  117. data/spec/lib/appsignal/integrations/railtie_spec.rb +0 -457
  118. data/spec/lib/appsignal/integrations/resque_spec.rb +0 -155
  119. data/spec/lib/appsignal/integrations/shoryuken_spec.rb +0 -165
  120. data/spec/lib/appsignal/integrations/sidekiq_spec.rb +0 -640
  121. data/spec/lib/appsignal/integrations/webmachine_spec.rb +0 -136
  122. data/spec/lib/appsignal/loaders/grape_spec.rb +0 -12
  123. data/spec/lib/appsignal/loaders/hanami_spec.rb +0 -92
  124. data/spec/lib/appsignal/loaders/padrino_spec.rb +0 -273
  125. data/spec/lib/appsignal/loaders/sinatra_spec.rb +0 -44
  126. data/spec/lib/appsignal/loaders_spec.rb +0 -144
  127. data/spec/lib/appsignal/logger_spec.rb +0 -205
  128. data/spec/lib/appsignal/marker_spec.rb +0 -51
  129. data/spec/lib/appsignal/probes/gvl_spec.rb +0 -164
  130. data/spec/lib/appsignal/probes/mri_spec.rb +0 -162
  131. data/spec/lib/appsignal/probes/sidekiq_spec.rb +0 -333
  132. data/spec/lib/appsignal/probes_spec.rb +0 -414
  133. data/spec/lib/appsignal/rack/abstract_middleware_spec.rb +0 -370
  134. data/spec/lib/appsignal/rack/body_wrapper_spec.rb +0 -319
  135. data/spec/lib/appsignal/rack/event_handler_spec.rb +0 -441
  136. data/spec/lib/appsignal/rack/grape_middleware_spec.rb +0 -201
  137. data/spec/lib/appsignal/rack/hanami_middleware_spec.rb +0 -36
  138. data/spec/lib/appsignal/rack/instrumentation_middleware_spec.rb +0 -38
  139. data/spec/lib/appsignal/rack/rails_instrumentation_spec.rb +0 -126
  140. data/spec/lib/appsignal/rack/sinatra_instrumentation_spec.rb +0 -217
  141. data/spec/lib/appsignal/rack_spec.rb +0 -243
  142. data/spec/lib/appsignal/sample_data_spec.rb +0 -238
  143. data/spec/lib/appsignal/span_spec.rb +0 -141
  144. data/spec/lib/appsignal/system_spec.rb +0 -126
  145. data/spec/lib/appsignal/transaction_spec.rb +0 -2115
  146. data/spec/lib/appsignal/transmitter_spec.rb +0 -198
  147. data/spec/lib/appsignal/utils/data_spec.rb +0 -166
  148. data/spec/lib/appsignal/utils/hash_sanitizer_spec.rb +0 -182
  149. data/spec/lib/appsignal/utils/integration_logger_spec.rb +0 -21
  150. data/spec/lib/appsignal/utils/integration_memory_logger_spec.rb +0 -153
  151. data/spec/lib/appsignal/utils/json_spec.rb +0 -44
  152. data/spec/lib/appsignal/utils/query_params_sanitizer_spec.rb +0 -192
  153. data/spec/lib/appsignal_spec.rb +0 -1919
  154. data/spec/lib/puma/appsignal_spec.rb +0 -334
  155. data/spec/spec_helper.rb +0 -179
  156. data/spec/support/fixtures/generated_config.yml +0 -24
  157. data/spec/support/fixtures/projects/broken/config/appsignal.yml +0 -1
  158. data/spec/support/fixtures/projects/valid/config/appsignal.yml +0 -57
  159. data/spec/support/fixtures/projects/valid/log/.gitkeep +0 -0
  160. data/spec/support/fixtures/projects/valid_with_rails_app/config/application.rb +0 -16
  161. data/spec/support/fixtures/projects/valid_with_rails_app/config/appsignal.yml +0 -56
  162. data/spec/support/fixtures/projects/valid_with_rails_app/config/environment.rb +0 -10
  163. data/spec/support/fixtures/projects/valid_with_rails_app/log/.gitkeep +0 -0
  164. data/spec/support/fixtures/uploaded_file.txt +0 -0
  165. data/spec/support/hanami/hanami_app.rb +0 -29
  166. data/spec/support/helpers/action_mailer_helpers.rb +0 -25
  167. data/spec/support/helpers/activejob_helpers.rb +0 -27
  168. data/spec/support/helpers/api_request_helper.rb +0 -60
  169. data/spec/support/helpers/cli_helpers.rb +0 -40
  170. data/spec/support/helpers/config_helpers.rb +0 -66
  171. data/spec/support/helpers/dependency_helper.rb +0 -155
  172. data/spec/support/helpers/directory_helper.rb +0 -27
  173. data/spec/support/helpers/env_helpers.rb +0 -41
  174. data/spec/support/helpers/environment_metdata_helper.rb +0 -16
  175. data/spec/support/helpers/example_exception.rb +0 -13
  176. data/spec/support/helpers/example_standard_error.rb +0 -13
  177. data/spec/support/helpers/loader_helper.rb +0 -21
  178. data/spec/support/helpers/log_helpers.rb +0 -36
  179. data/spec/support/helpers/rails_helper.rb +0 -28
  180. data/spec/support/helpers/std_streams_helper.rb +0 -94
  181. data/spec/support/helpers/system_helpers.rb +0 -8
  182. data/spec/support/helpers/take_at_most_helper.rb +0 -21
  183. data/spec/support/helpers/time_helpers.rb +0 -11
  184. data/spec/support/helpers/transaction_helpers.rb +0 -122
  185. data/spec/support/helpers/wait_for_helper.rb +0 -39
  186. data/spec/support/matchers/contains_log.rb +0 -26
  187. data/spec/support/matchers/have_colorized_text.rb +0 -28
  188. data/spec/support/matchers/transaction.rb +0 -200
  189. data/spec/support/mocks/appsignal_mock.rb +0 -18
  190. data/spec/support/mocks/dummy_app.rb +0 -20
  191. data/spec/support/mocks/fake_gc_profiler.rb +0 -19
  192. data/spec/support/mocks/fake_gvl_tools.rb +0 -28
  193. data/spec/support/mocks/hash_like.rb +0 -10
  194. data/spec/support/mocks/mock_probe.rb +0 -13
  195. data/spec/support/mocks/puma_mock.rb +0 -43
  196. data/spec/support/shared_examples/instrument.rb +0 -48
  197. data/spec/support/stubs/appsignal/loaders/loader_stub.rb +0 -7
  198. data/spec/support/stubs/delayed_job.rb +0 -0
  199. data/spec/support/stubs/sidekiq/api.rb +0 -4
  200. data/spec/support/testing.rb +0 -203
  201. data/support/bundler_wrapper +0 -12
  202. data/support/install_deps +0 -33
@@ -1,154 +0,0 @@
1
- require "appsignal/integrations/mongo_ruby_driver"
2
- describe Appsignal::Hooks::MongoMonitorSubscriber do
3
- let(:subscriber) { Appsignal::Hooks::MongoMonitorSubscriber.new }
4
-
5
- context "with transaction" do
6
- let(:transaction) { http_request_transaction }
7
- before do
8
- start_agent
9
- set_current_transaction(transaction)
10
- end
11
-
12
- describe "#started" do
13
- let(:event) do
14
- double(
15
- :request_id => 1,
16
- :command_name => "find",
17
- :command => { "foo" => "bar" }
18
- )
19
- end
20
-
21
- it "should sanitize command" do
22
- # TODO: additional curly brackets required for issue
23
- # https://github.com/rspec/rspec-mocks/issues/1460
24
- expect(Appsignal::EventFormatter::MongoRubyDriver::QueryFormatter)
25
- .to receive(:format).with("find", { "foo" => "bar" })
26
- subscriber.started(event)
27
- end
28
-
29
- it "should store command on the transaction" do
30
- subscriber.started(event)
31
-
32
- expect(transaction.store("mongo_driver")).to eq(1 => { "foo" => "?" })
33
- end
34
-
35
- it "should start an event in the extension" do
36
- expect(transaction).to receive(:start_event)
37
-
38
- subscriber.started(event)
39
- end
40
- end
41
-
42
- describe "#succeeded" do
43
- let(:event) { double }
44
-
45
- it "should finish the event" do
46
- expect(subscriber).to receive(:finish).with("SUCCEEDED", event)
47
-
48
- subscriber.succeeded(event)
49
- end
50
- end
51
-
52
- describe "#failed" do
53
- let(:event) { double }
54
-
55
- it "should finish the event" do
56
- expect(subscriber).to receive(:finish).with("FAILED", event)
57
-
58
- subscriber.failed(event)
59
- end
60
- end
61
-
62
- describe "#finish" do
63
- let(:command) { { "foo" => "?" } }
64
- let(:event) do
65
- double(
66
- :request_id => 2,
67
- :command_name => :find,
68
- :database_name => "test",
69
- :duration => 0.9919
70
- )
71
- end
72
-
73
- before do
74
- store = transaction.store("mongo_driver")
75
- store[2] = command
76
- end
77
-
78
- it "should emit a measurement" do
79
- expect(Appsignal).to receive(:add_distribution_value).with(
80
- "mongodb_query_duration",
81
- 0.9919,
82
- :database => "test"
83
- ).and_call_original
84
-
85
- subscriber.finish("SUCCEEDED", event)
86
- end
87
-
88
- it "should get the query from the store" do
89
- expect(transaction).to receive(:store).with("mongo_driver").and_return(command)
90
-
91
- subscriber.finish("SUCCEEDED", event)
92
- end
93
-
94
- it "should finish the transaction in the extension" do
95
- expect(transaction).to receive(:finish_event).with(
96
- "query.mongodb",
97
- "find | test | SUCCEEDED",
98
- Appsignal::Utils::Data.generate("foo" => "?"),
99
- 0
100
- )
101
-
102
- subscriber.finish("SUCCEEDED", event)
103
- end
104
- end
105
- end
106
-
107
- context "without transaction" do
108
- before do
109
- allow(Appsignal::Transaction).to receive(:current)
110
- .and_return(Appsignal::Transaction::NilTransaction.new)
111
- end
112
-
113
- it "should not attempt to start an event" do
114
- expect(Appsignal::Extension).to_not receive(:start_event)
115
-
116
- subscriber.started(double)
117
- end
118
-
119
- it "should not attempt to finish an event" do
120
- expect(Appsignal::Extension).to_not receive(:finish_event)
121
-
122
- subscriber.finish("SUCCEEDED", double)
123
- end
124
-
125
- it "should not attempt to send duration metrics" do
126
- expect(Appsignal).to_not receive(:add_distribution_value)
127
-
128
- subscriber.finish("SUCCEEDED", double)
129
- end
130
- end
131
-
132
- context "when appsignal is paused" do
133
- let(:transaction) { double(:paused? => true, :nil_transaction? => false) }
134
- before { allow(Appsignal::Transaction).to receive(:current).and_return(transaction) }
135
-
136
- it "should not attempt to start an event" do
137
- expect(Appsignal::Extension).to_not receive(:start_event)
138
-
139
- subscriber.started(double)
140
- end
141
-
142
- it "should not attempt to finish an event" do
143
- expect(Appsignal::Extension).to_not receive(:finish_event)
144
-
145
- subscriber.finish("SUCCEEDED", double)
146
- end
147
-
148
- it "should not attempt to send duration metrics" do
149
- expect(Appsignal).to_not receive(:add_distribution_value)
150
-
151
- subscriber.finish("SUCCEEDED", double)
152
- end
153
- end
154
- end
@@ -1,33 +0,0 @@
1
- require "appsignal/integrations/net_http"
2
-
3
- describe Appsignal::Integrations::NetHttpIntegration do
4
- let(:transaction) { http_request_transaction }
5
- before { start_agent }
6
- before { set_current_transaction transaction }
7
- around { |example| keep_transactions { example.run } }
8
-
9
- it "instruments a http request" do
10
- stub_request(:any, "http://www.google.com/")
11
-
12
- Net::HTTP.get_response(URI.parse("http://www.google.com"))
13
-
14
- expect(transaction).to include_event(
15
- "name" => "request.net_http",
16
- "title" => "GET http://www.google.com"
17
- )
18
- end
19
-
20
- it "instruments a https request" do
21
- stub_request(:any, "https://www.google.com/")
22
-
23
- uri = URI.parse("https://www.google.com")
24
- http = Net::HTTP.new(uri.host, uri.port)
25
- http.use_ssl = true
26
- http.get(uri.request_uri)
27
-
28
- expect(transaction).to include_event(
29
- "name" => "request.net_http",
30
- "title" => "GET https://www.google.com"
31
- )
32
- end
33
- end
@@ -1,347 +0,0 @@
1
- require "appsignal/integrations/object"
2
-
3
- describe Object do
4
- around { |example| keep_transactions { example.run } }
5
-
6
- describe "#instrument_method" do
7
- context "with instance method" do
8
- let(:klass) do
9
- Class.new do
10
- def foo(param1, options = {}, keyword_param: 1)
11
- [param1, options, keyword_param]
12
- end
13
- appsignal_instrument_method :foo
14
- end
15
- end
16
- let(:instance) { klass.new }
17
-
18
- def call_with_arguments
19
- instance.foo(
20
- "abc",
21
- { :foo => "bar" },
22
- :keyword_param => 2
23
- )
24
- end
25
-
26
- context "when active" do
27
- let(:transaction) { http_request_transaction }
28
- before do
29
- start_agent
30
- set_current_transaction(transaction)
31
- end
32
-
33
- context "with different kind of arguments" do
34
- let(:klass) do
35
- Class.new do
36
- def positional_arguments(param1, param2)
37
- [param1, param2]
38
- end
39
- appsignal_instrument_method :positional_arguments
40
-
41
- def positional_arguments_splat(*params)
42
- params
43
- end
44
- appsignal_instrument_method :positional_arguments_splat
45
-
46
- # rubocop:disable Naming/MethodParameterName
47
- def keyword_arguments(a: nil, b: nil)
48
- [a, b]
49
- end
50
- # rubocop:enable Naming/MethodParameterName
51
- appsignal_instrument_method :keyword_arguments
52
-
53
- def keyword_arguments_splat(**kwargs)
54
- kwargs
55
- end
56
- appsignal_instrument_method :keyword_arguments_splat
57
-
58
- def splat(*args, **kwargs)
59
- [args, kwargs]
60
- end
61
- appsignal_instrument_method :splat
62
- end
63
- end
64
-
65
- it "instruments the method and calls it" do
66
- expect(instance.positional_arguments("abc", "def")).to eq(["abc", "def"])
67
- expect(instance.positional_arguments_splat("abc", "def")).to eq(["abc", "def"])
68
- expect(instance.keyword_arguments(:a => "a", :b => "b")).to eq(["a", "b"])
69
- expect(instance.keyword_arguments_splat(:a => "a", :b => "b"))
70
- .to eq(:a => "a", :b => "b")
71
-
72
- expect(instance.splat).to eq([[], {}])
73
- expect(instance.splat(:a => "a", :b => "b")).to eq([[], { :a => "a", :b => "b" }])
74
- expect(instance.splat("abc", "def")).to eq([["abc", "def"], {}])
75
- expect(instance.splat("abc", "def", :a => "a", :b => "b"))
76
- .to eq([["abc", "def"], { :a => "a", :b => "b" }])
77
- end
78
- end
79
-
80
- context "with anonymous class" do
81
- it "instruments the method and calls it" do
82
- expect(call_with_arguments).to eq(["abc", { :foo => "bar" }, 2])
83
-
84
- expect(transaction).to include_event("name" => "foo.AnonymousClass.other")
85
- end
86
- end
87
-
88
- context "with named class" do
89
- before do
90
- class NamedClass
91
- def foo
92
- 1
93
- end
94
- appsignal_instrument_method :foo
95
- end
96
- end
97
- after { Object.send(:remove_const, :NamedClass) }
98
- let(:klass) { NamedClass }
99
-
100
- it "instruments the method and calls it" do
101
- expect(instance.foo).to eq(1)
102
-
103
- expect(transaction).to include_event("name" => "foo.NamedClass.other")
104
- end
105
- end
106
-
107
- context "with nested named class" do
108
- before do
109
- module MyModule
110
- module NestedModule
111
- class NamedClass
112
- def bar
113
- 2
114
- end
115
- appsignal_instrument_method :bar
116
- end
117
- end
118
- end
119
- end
120
- after { Object.send(:remove_const, :MyModule) }
121
- let(:klass) { MyModule::NestedModule::NamedClass }
122
-
123
- it "instruments the method and calls it" do
124
- expect(instance.bar).to eq(2)
125
-
126
- expect(transaction).to include_event(
127
- "name" => "bar.NamedClass.NestedModule.MyModule.other"
128
- )
129
- end
130
- end
131
-
132
- context "with custom name" do
133
- let(:klass) do
134
- Class.new do
135
- def foo
136
- 1
137
- end
138
- appsignal_instrument_method :foo, :name => "my_method.group"
139
- end
140
- end
141
-
142
- it "instruments with custom name" do
143
- expect(instance.foo).to eq(1)
144
-
145
- expect(transaction).to include_event(
146
- "name" => "my_method.group"
147
- )
148
- end
149
- end
150
-
151
- context "with a method given a block" do
152
- let(:klass) do
153
- Class.new do
154
- def foo
155
- yield
156
- end
157
- appsignal_instrument_method :foo
158
- end
159
- end
160
-
161
- it "yields the block" do
162
- expect(instance.foo { 42 }).to eq(42)
163
- end
164
- end
165
- end
166
-
167
- context "when not active" do
168
- let(:transaction) { Appsignal::Transaction.current }
169
-
170
- it "does not instrument, but still calls the method" do
171
- expect(Appsignal.active?).to be_falsy
172
- expect(call_with_arguments).to eq(["abc", { :foo => "bar" }, 2])
173
- end
174
- end
175
- end
176
-
177
- context "with class method" do
178
- let(:klass) do
179
- Class.new do
180
- def self.bar(param1, options = {}, keyword_param: 1)
181
- [param1, options, keyword_param]
182
- end
183
- appsignal_instrument_class_method :bar
184
- end
185
- end
186
- def call_with_arguments
187
- klass.bar(
188
- "abc",
189
- { :foo => "bar" },
190
- :keyword_param => 2
191
- )
192
- end
193
-
194
- context "when active" do
195
- let(:transaction) { http_request_transaction }
196
- before do
197
- start_agent
198
- set_current_transaction(transaction)
199
- end
200
-
201
- context "with different kind of arguments" do
202
- let(:klass) do
203
- Class.new do
204
- def self.positional_arguments(param1, param2)
205
- [param1, param2]
206
- end
207
- appsignal_instrument_class_method :positional_arguments
208
-
209
- def self.positional_arguments_splat(*params)
210
- params
211
- end
212
- appsignal_instrument_class_method :positional_arguments_splat
213
-
214
- # rubocop:disable Naming/MethodParameterName
215
- def self.keyword_arguments(a: nil, b: nil)
216
- [a, b]
217
- end
218
- # rubocop:enable Naming/MethodParameterName
219
- appsignal_instrument_class_method :keyword_arguments
220
-
221
- def self.keyword_arguments_splat(**kwargs)
222
- kwargs
223
- end
224
- appsignal_instrument_class_method :keyword_arguments_splat
225
-
226
- def self.splat(*args, **kwargs)
227
- [args, kwargs]
228
- end
229
- appsignal_instrument_class_method :splat
230
- end
231
- end
232
-
233
- it "instruments the method and calls it" do
234
- expect(klass.positional_arguments("abc", "def")).to eq(["abc", "def"])
235
- expect(klass.positional_arguments_splat("abc", "def")).to eq(["abc", "def"])
236
- expect(klass.keyword_arguments(:a => "a", :b => "b")).to eq(["a", "b"])
237
- expect(klass.keyword_arguments_splat(:a => "a", :b => "b"))
238
- .to eq(:a => "a", :b => "b")
239
-
240
- expect(klass.splat).to eq([[], {}])
241
- expect(klass.splat(:a => "a", :b => "b")).to eq([[], { :a => "a", :b => "b" }])
242
- expect(klass.splat("abc", "def")).to eq([["abc", "def"], {}])
243
- expect(klass.splat("abc", "def", :a => "a", :b => "b"))
244
- .to eq([["abc", "def"], { :a => "a", :b => "b" }])
245
- end
246
- end
247
-
248
- context "with anonymous class" do
249
- it "instruments the method and calls it" do
250
- expect(Appsignal.active?).to be_truthy
251
- expect(call_with_arguments).to eq(["abc", { :foo => "bar" }, 2])
252
-
253
- transaction._sample
254
- expect(transaction).to include_event("name" => "bar.class_method.AnonymousClass.other")
255
- end
256
- end
257
-
258
- context "with named class" do
259
- before do
260
- class NamedClass
261
- def self.bar
262
- 2
263
- end
264
- appsignal_instrument_class_method :bar
265
- end
266
- end
267
- after { Object.send(:remove_const, :NamedClass) }
268
- let(:klass) { NamedClass }
269
-
270
- it "instruments the method and calls it" do
271
- expect(Appsignal.active?).to be_truthy
272
- expect(klass.bar).to eq(2)
273
-
274
- expect(transaction).to include_event("name" => "bar.class_method.NamedClass.other")
275
- end
276
-
277
- context "with nested named class" do
278
- before do
279
- module MyModule
280
- module NestedModule
281
- class NamedClass
282
- def self.bar
283
- 2
284
- end
285
- appsignal_instrument_class_method :bar
286
- end
287
- end
288
- end
289
- end
290
- after { Object.send(:remove_const, :MyModule) }
291
- let(:klass) { MyModule::NestedModule::NamedClass }
292
-
293
- it "instruments the method and calls it" do
294
- expect(Appsignal.active?).to be_truthy
295
- expect(klass.bar).to eq(2)
296
- expect(transaction).to include_event(
297
- "name" => "bar.class_method.NamedClass.NestedModule.MyModule.other"
298
- )
299
- end
300
- end
301
- end
302
-
303
- context "with custom name" do
304
- let(:klass) do
305
- Class.new do
306
- def self.bar
307
- 2
308
- end
309
- appsignal_instrument_class_method :bar, :name => "my_method.group"
310
- end
311
- end
312
-
313
- it "instruments with custom name" do
314
- expect(Appsignal.active?).to be_truthy
315
- expect(klass.bar).to eq(2)
316
-
317
- expect(transaction).to include_event("name" => "my_method.group")
318
- end
319
- end
320
-
321
- context "with a method given a block" do
322
- let(:klass) do
323
- Class.new do
324
- def self.bar
325
- yield
326
- end
327
- appsignal_instrument_class_method :bar
328
- end
329
- end
330
-
331
- it "yields the block" do
332
- expect(klass.bar { 42 }).to eq(42)
333
- end
334
- end
335
- end
336
-
337
- context "when not active" do
338
- let(:transaction) { Appsignal::Transaction.current }
339
-
340
- it "does not instrument, but still call the method" do
341
- expect(Appsignal.active?).to be_falsy
342
- expect(call_with_arguments).to eq(["abc", { :foo => "bar" }, 2])
343
- end
344
- end
345
- end
346
- end
347
- end
@@ -1,150 +0,0 @@
1
- require "appsignal/integrations/puma"
2
-
3
- describe Appsignal::Integrations::PumaServer do
4
- describe "#lowlevel_error" do
5
- before do
6
- stub_const("Puma", PumaMock)
7
- stub_const("Puma::Server", puma_server)
8
- start_agent
9
- end
10
- let(:queue_start_time) { fixed_time * 1_000 }
11
- let(:env) do
12
- Rack::MockRequest.env_for(
13
- "/some/path",
14
- "REQUEST_METHOD" => "GET",
15
- :params => { "page" => 2, "query" => "lorem" },
16
- "rack.session" => { "session" => "data", "user_id" => 123 },
17
- "HTTP_X_REQUEST_START" => "t=#{queue_start_time.to_i}" # in milliseconds
18
- )
19
- end
20
- let(:server) { Puma::Server.new }
21
- let(:error) { ExampleException.new("error message") }
22
- around { |example| keep_transactions { example.run } }
23
- before { Appsignal::Hooks::PumaHook.new.install }
24
-
25
- def lowlevel_error(error, env, status = nil)
26
- result =
27
- if status
28
- server.lowlevel_error(error, env, status)
29
- else
30
- server.lowlevel_error(error, env)
31
- end
32
- # Transaction is normally closed by the EventHandler's RACK_AFTER_REPLY hook
33
- last_transaction&.complete
34
- result
35
- end
36
-
37
- describe "error reporting" do
38
- let(:puma_server) { default_puma_server_mock }
39
-
40
- context "with active transaction" do
41
- before { create_transaction }
42
-
43
- it "reports the error to the transaction" do
44
- expect do
45
- lowlevel_error(error, env)
46
- end.to_not(change { created_transactions.count })
47
-
48
- expect(last_transaction).to have_error("ExampleException", "error message")
49
- expect(last_transaction).to include_tags("reported_by" => "puma_lowlevel_error")
50
- end
51
- end
52
-
53
- # This shouldn't happen if the EventHandler is set up correctly, but if
54
- # it's not it will create a new transaction.
55
- context "without active transaction" do
56
- it "creates a new transaction with the error" do
57
- expect do
58
- lowlevel_error(error, env)
59
- end.to change { created_transactions.count }.by(1)
60
-
61
- expect(last_transaction).to have_error("ExampleException", "error message")
62
- expect(last_transaction).to include_tags("reported_by" => "puma_lowlevel_error")
63
- end
64
- end
65
-
66
- it "doesn't report internal Puma errors" do
67
- expect do
68
- lowlevel_error(Puma::MiniSSL::SSLError.new("error message"), env)
69
- lowlevel_error(Puma::HttpParserError.new("error message"), env)
70
- lowlevel_error(Puma::HttpParserError501.new("error message"), env)
71
- end.to_not(change { created_transactions.count })
72
- end
73
-
74
- describe "request metadata" do
75
- it "sets request metadata" do
76
- lowlevel_error(error, env)
77
-
78
- expect(last_transaction).to include_metadata(
79
- "request_method" => "GET",
80
- "method" => "GET",
81
- "request_path" => "/some/path",
82
- "path" => "/some/path"
83
- )
84
- expect(last_transaction).to include_environment(
85
- "REQUEST_METHOD" => "GET",
86
- "PATH_INFO" => "/some/path"
87
- # and more, but we don't need to test Rack mock defaults
88
- )
89
- end
90
-
91
- it "sets request parameters" do
92
- lowlevel_error(error, env)
93
-
94
- expect(last_transaction).to include_params(
95
- "page" => "2",
96
- "query" => "lorem"
97
- )
98
- end
99
-
100
- it "sets session data" do
101
- lowlevel_error(error, env)
102
-
103
- expect(last_transaction).to include_session_data("session" => "data", "user_id" => 123)
104
- end
105
-
106
- it "sets the queue start" do
107
- lowlevel_error(error, env)
108
-
109
- expect(last_transaction).to have_queue_start(queue_start_time)
110
- end
111
- end
112
- end
113
-
114
- context "with Puma::Server#lowlevel_error accepting 3 arguments" do
115
- let(:puma_server) { default_puma_server_mock }
116
-
117
- it "calls the super class with 3 arguments" do
118
- result = lowlevel_error(error, env, 501)
119
- expect(result).to eq([501, {}, ""])
120
-
121
- expect(last_transaction).to include_tags("response_status" => 501)
122
- end
123
- end
124
-
125
- context "with Puma::Server#lowlevel_error accepting 2 arguments" do
126
- let(:puma_server) do
127
- Class.new do
128
- def lowlevel_error(_error, _env)
129
- [500, {}, ""]
130
- end
131
- end
132
- end
133
-
134
- it "calls the super class with 3 arguments" do
135
- result = lowlevel_error(error, env)
136
- expect(result).to eq([500, {}, ""])
137
-
138
- expect(last_transaction).to include_tags("response_status" => 500)
139
- end
140
- end
141
- end
142
-
143
- def default_puma_server_mock
144
- Class.new do
145
- def lowlevel_error(_error, _env, status = 500)
146
- [status, {}, ""]
147
- end
148
- end
149
- end
150
- end