rollbar 2.18.2 → 2.19.0

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 (167) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +15 -0
  3. data/.travis.yml +155 -93
  4. data/Gemfile +19 -13
  5. data/README.md +12 -0
  6. data/gemfiles/rails30.gemfile +17 -10
  7. data/gemfiles/rails31.gemfile +20 -12
  8. data/gemfiles/rails32.gemfile +16 -7
  9. data/gemfiles/rails40.gemfile +16 -5
  10. data/gemfiles/rails41.gemfile +15 -5
  11. data/gemfiles/rails42.gemfile +25 -14
  12. data/gemfiles/rails50.gemfile +15 -8
  13. data/gemfiles/rails51.gemfile +15 -8
  14. data/gemfiles/rails52.gemfile +62 -0
  15. data/gemfiles/ruby_1_8_and_1_9_2.gemfile +2 -2
  16. data/lib/rails/rollbar_runner.rb +16 -1
  17. data/lib/rollbar/capistrano.rb +71 -39
  18. data/lib/rollbar/capistrano3.rb +53 -1
  19. data/lib/rollbar/capistrano_tasks.rb +131 -0
  20. data/lib/rollbar/configuration.rb +13 -4
  21. data/lib/rollbar/delay/active_job.rb +17 -0
  22. data/lib/rollbar/delay/sidekiq.rb +3 -1
  23. data/lib/rollbar/delay/thread.rb +1 -1
  24. data/lib/rollbar/deploy.rb +69 -0
  25. data/lib/rollbar/item.rb +17 -6
  26. data/lib/rollbar/middleware/js.rb +25 -3
  27. data/lib/rollbar/middleware/js/json_value.rb +26 -0
  28. data/lib/rollbar/notifier.rb +32 -13
  29. data/lib/rollbar/plugins/active_job.rb +3 -0
  30. data/lib/rollbar/plugins/rails/controller_methods.rb +2 -1
  31. data/lib/rollbar/plugins/rails/railtie_mixin.rb +7 -1
  32. data/lib/rollbar/rake_tasks.rb +126 -67
  33. data/lib/rollbar/scrubbers/params.rb +6 -0
  34. data/lib/rollbar/util.rb +75 -45
  35. data/lib/rollbar/util/hash.rb +15 -6
  36. data/lib/rollbar/version.rb +1 -1
  37. data/rollbar.gemspec +2 -3
  38. metadata +9 -261
  39. data/lib/rollbar/tasks/rollbar.cap +0 -47
  40. data/spec/cacert.pem +0 -3988
  41. data/spec/controllers/home_controller_spec.rb +0 -480
  42. data/spec/delay/sidekiq_spec.rb +0 -61
  43. data/spec/delay/sucker_punch_spec.rb +0 -25
  44. data/spec/delayed/backend/test.rb +0 -140
  45. data/spec/delayed/serialization/test.rb +0 -0
  46. data/spec/dummyapp/.gitignore +0 -73
  47. data/spec/dummyapp/Rakefile +0 -7
  48. data/spec/dummyapp/app/assets/javascripts/application.js +0 -3
  49. data/spec/dummyapp/app/assets/stylesheets/application.css.scss +0 -37
  50. data/spec/dummyapp/app/controllers/application_controller.rb +0 -3
  51. data/spec/dummyapp/app/controllers/home_controller.rb +0 -60
  52. data/spec/dummyapp/app/controllers/users_controller.rb +0 -17
  53. data/spec/dummyapp/app/helpers/.gitkeep +0 -0
  54. data/spec/dummyapp/app/mailers/.gitkeep +0 -0
  55. data/spec/dummyapp/app/models/.gitkeep +0 -0
  56. data/spec/dummyapp/app/models/book.rb +0 -5
  57. data/spec/dummyapp/app/models/post.rb +0 -9
  58. data/spec/dummyapp/app/models/user.rb +0 -9
  59. data/spec/dummyapp/app/views/devise/registrations/edit.html.erb +0 -27
  60. data/spec/dummyapp/app/views/devise/registrations/new.html.erb +0 -20
  61. data/spec/dummyapp/app/views/devise/shared/_links.html.erb +0 -25
  62. data/spec/dummyapp/app/views/home/cause_exception.html.erb +0 -1
  63. data/spec/dummyapp/app/views/home/index.html.erb +0 -4
  64. data/spec/dummyapp/app/views/home/report_exception.html.erb +0 -1
  65. data/spec/dummyapp/app/views/js/test.html.erb +0 -1
  66. data/spec/dummyapp/app/views/layouts/_messages.html.erb +0 -5
  67. data/spec/dummyapp/app/views/layouts/_navigation.html.erb +0 -21
  68. data/spec/dummyapp/app/views/layouts/application.html.erb +0 -25
  69. data/spec/dummyapp/app/views/layouts/simple.html.erb +0 -18
  70. data/spec/dummyapp/app/views/users/index.html.erb +0 -8
  71. data/spec/dummyapp/app/views/users/show.html.erb +0 -3
  72. data/spec/dummyapp/config.ru +0 -4
  73. data/spec/dummyapp/config/application.rb +0 -59
  74. data/spec/dummyapp/config/boot.rb +0 -10
  75. data/spec/dummyapp/config/database.yml +0 -25
  76. data/spec/dummyapp/config/environment.rb +0 -5
  77. data/spec/dummyapp/config/environments/development.rb +0 -37
  78. data/spec/dummyapp/config/environments/production.rb +0 -67
  79. data/spec/dummyapp/config/environments/test.rb +0 -37
  80. data/spec/dummyapp/config/initializers/backtrace_silencers.rb +0 -7
  81. data/spec/dummyapp/config/initializers/inflections.rb +0 -15
  82. data/spec/dummyapp/config/initializers/mime_types.rb +0 -5
  83. data/spec/dummyapp/config/initializers/rollbar.rb +0 -26
  84. data/spec/dummyapp/config/initializers/secret_token.rb +0 -7
  85. data/spec/dummyapp/config/initializers/session_store.rb +0 -8
  86. data/spec/dummyapp/config/initializers/wrap_parameters.rb +0 -16
  87. data/spec/dummyapp/config/locales/devise.en.yml +0 -58
  88. data/spec/dummyapp/config/locales/en.yml +0 -5
  89. data/spec/dummyapp/config/routes.rb +0 -17
  90. data/spec/dummyapp/config/secrets.yml +0 -2
  91. data/spec/dummyapp/db/migrate/20121121184652_devise_create_users.rb +0 -46
  92. data/spec/dummyapp/db/migrate/20121121184654_add_name_to_users.rb +0 -5
  93. data/spec/dummyapp/db/migrate/20161219184410_create_books.rb +0 -10
  94. data/spec/dummyapp/db/migrate/20161219185529_add_username_to_users.rb +0 -5
  95. data/spec/dummyapp/db/schema.rb +0 -41
  96. data/spec/dummyapp/db/seeds.rb +0 -12
  97. data/spec/dummyapp/lib/assets/.gitkeep +0 -0
  98. data/spec/dummyapp/public/404.html +0 -26
  99. data/spec/dummyapp/public/422.html +0 -26
  100. data/spec/dummyapp/public/500.html +0 -25
  101. data/spec/dummyapp/public/favicon.ico +0 -0
  102. data/spec/dummyapp/script/rails +0 -6
  103. data/spec/fixtures/file1 +0 -1
  104. data/spec/fixtures/file2 +0 -1
  105. data/spec/fixtures/payloads/message.json +0 -25
  106. data/spec/fixtures/payloads/sample.trace.json +0 -275
  107. data/spec/fixtures/payloads/sample.trace_chain.json +0 -530
  108. data/spec/fixtures/plugins/dummy1.rb +0 -5
  109. data/spec/fixtures/plugins/dummy2.rb +0 -5
  110. data/spec/generators/rollbar/rollbar_generator_rails30_spec.rb +0 -31
  111. data/spec/generators/rollbar/rollbar_generator_spec.rb +0 -51
  112. data/spec/requests/home_spec.rb +0 -49
  113. data/spec/rollbar/configuration_spec.rb +0 -74
  114. data/spec/rollbar/delay/delayed_job_spec.rb +0 -22
  115. data/spec/rollbar/delay/girl_friday_spec.rb +0 -41
  116. data/spec/rollbar/delay/resque_spec.rb +0 -37
  117. data/spec/rollbar/delay/shoryuken_spec.rb +0 -44
  118. data/spec/rollbar/delay/thread_spec.rb +0 -27
  119. data/spec/rollbar/encoding/encoder_spec.rb +0 -63
  120. data/spec/rollbar/item/backtrace_spec.rb +0 -26
  121. data/spec/rollbar/item/frame_spec.rb +0 -267
  122. data/spec/rollbar/item_spec.rb +0 -736
  123. data/spec/rollbar/json/oj_spec.rb +0 -18
  124. data/spec/rollbar/json_spec.rb +0 -110
  125. data/spec/rollbar/lazy_store_spec.rb +0 -99
  126. data/spec/rollbar/logger_proxy_spec.rb +0 -69
  127. data/spec/rollbar/logger_spec.rb +0 -124
  128. data/spec/rollbar/middleware/js_spec.rb +0 -428
  129. data/spec/rollbar/middleware/sinatra_spec.rb +0 -197
  130. data/spec/rollbar/notifier_spec.rb +0 -67
  131. data/spec/rollbar/plugin_spec.rb +0 -209
  132. data/spec/rollbar/plugins/active_job_spec.rb +0 -45
  133. data/spec/rollbar/plugins/delayed_job/job_data_spec.rb +0 -48
  134. data/spec/rollbar/plugins/delayed_job_spec.rb +0 -129
  135. data/spec/rollbar/plugins/rack_spec.rb +0 -152
  136. data/spec/rollbar/plugins/rails_js_spec.rb +0 -19
  137. data/spec/rollbar/plugins/rake_spec.rb +0 -34
  138. data/spec/rollbar/plugins/resque/failure_spec.rb +0 -36
  139. data/spec/rollbar/plugins/sidekiq_spec.rb +0 -169
  140. data/spec/rollbar/plugins/validations_spec.rb +0 -56
  141. data/spec/rollbar/plugins_spec.rb +0 -68
  142. data/spec/rollbar/request_data_extractor_spec.rb +0 -321
  143. data/spec/rollbar/scrubbers/params_spec.rb +0 -598
  144. data/spec/rollbar/scrubbers/url_spec.rb +0 -240
  145. data/spec/rollbar/scrubbers_spec.rb +0 -31
  146. data/spec/rollbar/sidekig/clear_scope_spec.rb +0 -19
  147. data/spec/rollbar/truncation/frames_strategy_spec.rb +0 -70
  148. data/spec/rollbar/truncation/min_body_strategy_spec.rb +0 -57
  149. data/spec/rollbar/truncation/strings_strategy_spec.rb +0 -89
  150. data/spec/rollbar/truncation_spec.rb +0 -27
  151. data/spec/rollbar/util/hash_spec.rb +0 -22
  152. data/spec/rollbar/util/ip_anonymizer_spec.rb +0 -30
  153. data/spec/rollbar/util_spec.rb +0 -80
  154. data/spec/rollbar_bc_spec.rb +0 -380
  155. data/spec/rollbar_spec.rb +0 -1737
  156. data/spec/spec_helper.rb +0 -84
  157. data/spec/support/cause_exception.rb +0 -1
  158. data/spec/support/encoding_helpers.rb +0 -8
  159. data/spec/support/encodings/iso_8859_9 +0 -1
  160. data/spec/support/fixture_helpers.rb +0 -10
  161. data/spec/support/get_ip_raising.rb +0 -7
  162. data/spec/support/helpers.rb +0 -5
  163. data/spec/support/matchers.rb +0 -23
  164. data/spec/support/notifier_helpers.rb +0 -57
  165. data/spec/support/rollbar_api.rb +0 -57
  166. data/spec/support/secure_headers_mocks.rb +0 -83
  167. data/spec/support/shared_contexts.rb +0 -12
@@ -1,1737 +0,0 @@
1
- # encoding: utf-8
2
-
3
- require 'logger'
4
- require 'socket'
5
- require 'girl_friday'
6
- require 'redis'
7
- require 'active_support/core_ext/object'
8
- require 'active_support/json/encoding'
9
-
10
- require 'rollbar/item'
11
- require 'ostruct'
12
-
13
- begin
14
- require 'rollbar/delay/sidekiq'
15
- require 'rollbar/delay/sucker_punch'
16
- rescue LoadError
17
- end
18
-
19
- begin
20
- require 'sucker_punch'
21
- require 'sucker_punch/testing/inline'
22
- rescue LoadError
23
- end
24
-
25
- begin
26
- require 'rollbar/delay/shoryuken'
27
- rescue LoadError
28
- end
29
-
30
- require 'spec_helper'
31
-
32
- describe Rollbar do
33
- let(:notifier) { Rollbar.notifier }
34
-
35
- before do
36
- Rollbar.clear_notifier!
37
- configure
38
- end
39
-
40
- context 'when notifier has been used before configure it' do
41
- before do
42
- Rollbar.clear_notifier!
43
- end
44
-
45
- it 'is finally reset' do
46
- Rollbar.log_debug('Testing notifier')
47
- expect(Rollbar.error('error message')).to be_eql('disabled')
48
-
49
- reconfigure_notifier
50
-
51
- expect(Rollbar.error('error message')).not_to be_eql('disabled')
52
- end
53
- end
54
-
55
- shared_examples 'stores the root notifier' do
56
-
57
- end
58
-
59
- describe '.configure' do
60
- before { Rollbar.clear_notifier! }
61
-
62
- it 'stores the root notifier' do
63
- Rollbar.configure { |c| }
64
- expect(Rollbar.root_notifier).to be(Rollbar.notifier)
65
- end
66
- end
67
-
68
- describe '.preconfigure' do
69
- before { Rollbar.clear_notifier! }
70
-
71
- it 'stores the root notifier' do
72
- Rollbar.preconfigure { |c| }
73
- expect(Rollbar.root_notifier).to be(Rollbar.notifier)
74
- end
75
- end
76
-
77
- describe '.reconfigure' do
78
- before { Rollbar.clear_notifier! }
79
-
80
- it 'stores the root notifier' do
81
- Rollbar.reconfigure { |c| }
82
- expect(Rollbar.root_notifier).to be(Rollbar.notifier)
83
- end
84
- end
85
-
86
- describe '.unconfigure' do
87
- before { Rollbar.clear_notifier! }
88
-
89
- it 'stores the root notifier' do
90
- expect(Rollbar.root_notifier).to receive(:unconfigure)
91
-
92
- Rollbar.unconfigure
93
-
94
- expect(Rollbar.root_notifier).to be(Rollbar.notifier)
95
- end
96
- end
97
-
98
- context 'Notifier' do
99
- describe '#log' do
100
- let(:exception) do
101
- begin
102
- foo = bar
103
- rescue => e
104
- e
105
- end
106
- end
107
-
108
- let(:configuration) { Rollbar.configuration }
109
-
110
- context 'executing a Thread before Rollbar is configured' do
111
- before do
112
- Rollbar.clear_notifier!
113
-
114
- Thread.new {}
115
-
116
- Rollbar.configure do |config|
117
- config.access_token = 'my-access-token'
118
- end
119
- end
120
-
121
- it 'sets correct configuration for Rollbar.notifier' do
122
- expect(Rollbar.notifier.configuration.enabled).to be_truthy
123
- end
124
- end
125
-
126
- it 'should report a simple message' do
127
- expect(notifier).to receive(:report).with('error', 'test message', nil, nil, nil)
128
- notifier.log('error', 'test message')
129
- end
130
-
131
- it 'should report a simple message with extra data' do
132
- extra_data = {:key => 'value', :hash => {:inner_key => 'inner_value'}}
133
-
134
- expect(notifier).to receive(:report).with('error', 'test message', nil, extra_data, nil)
135
- notifier.log('error', 'test message', extra_data)
136
- end
137
-
138
- it 'should report an exception' do
139
- expect(notifier).to receive(:report).with('error', nil, exception, nil, nil)
140
- notifier.log('error', exception)
141
- end
142
-
143
- it 'should report an exception with extra data' do
144
- extra_data = {:key => 'value', :hash => {:inner_key => 'inner_value'}}
145
-
146
- expect(notifier).to receive(:report).with('error', nil, exception, extra_data, nil)
147
- notifier.log('error', exception, extra_data)
148
- end
149
-
150
- it 'should report an exception with a description' do
151
- expect(notifier).to receive(:report).with('error', 'exception description', exception, nil, nil)
152
- notifier.log('error', exception, 'exception description')
153
- end
154
-
155
- it 'should report an exception with a description and extra data' do
156
- extra_data = {:key => 'value', :hash => {:inner_key => 'inner_value'}}
157
-
158
- expect(notifier).to receive(:report).with('error', 'exception description', exception, extra_data, nil)
159
- notifier.log('error', exception, extra_data, 'exception description')
160
- end
161
-
162
- context 'with :on_error_response hook configured' do
163
- let!(:notifier) { Rollbar::Notifier.new }
164
- let(:configuration) do
165
- config = Rollbar::Configuration.new
166
- config.access_token = test_access_token
167
- config.enabled = true
168
-
169
- config.hook :on_error_response do |response|
170
- return ":on_error_response executed"
171
- end
172
-
173
- config
174
- end
175
- let(:message) { 'foo' }
176
- let(:level) { 'foo' }
177
-
178
- before do
179
- notifier.configuration = configuration
180
- allow_any_instance_of(Net::HTTP).to receive(:request).and_return(OpenStruct.new(:code => 500, :body => "Error"))
181
- @uri = URI.parse(Rollbar::Configuration::DEFAULT_ENDPOINT)
182
- end
183
-
184
- it "calls the :on_error_response hook if response status is not 200" do
185
- expect(Net::HTTP).to receive(:new).with(@uri.host, @uri.port, nil, nil, nil, nil).and_call_original
186
- expect(notifier.configuration.hook(:on_error_response)).to receive(:call)
187
-
188
- notifier.log(level, message)
189
- end
190
- end
191
-
192
- context 'with :on_report_internal_error hook configured' do
193
- let!(:notifier) { Rollbar::Notifier.new }
194
- let(:configuration) do
195
- config = Rollbar::Configuration.new
196
- config.access_token = test_access_token
197
- config.enabled = true
198
-
199
- config.hook :on_report_internal_error do |response|
200
- return ":on_report_internal_error executed"
201
- end
202
-
203
- config
204
- end
205
- let(:message) { 'foo' }
206
- let(:level) { 'foo' }
207
-
208
- before do
209
- notifier.configuration = configuration
210
- end
211
-
212
- it "calls the :on_report_internal_error hook if" do
213
- expect(notifier.configuration.hook(:on_report_internal_error)).to receive(:call)
214
- expect(notifier).to receive(:report) do
215
- raise StandardError.new
216
- end
217
- notifier.log(level, message)
218
- end
219
- end
220
-
221
- context 'an item with a context' do
222
- let(:context) { { :controller => 'ExampleController' } }
223
-
224
- context 'with a custom_data_method configured' do
225
- before do
226
- Rollbar.configure do |config|
227
- config.custom_data_method = lambda do |message, exception, context|
228
- { :result => "MyApp#" + context[:controller] }
229
- end
230
- end
231
- end
232
-
233
- it 'should have access to the context data through configuration.custom_data_method' do
234
- result = notifier.log('error', "Custom message", { :custom_data_method_context => context})
235
-
236
- result[:body][:message][:extra].should_not be_nil
237
- result[:body][:message][:extra][:result].should == "MyApp#"+context[:controller]
238
- result[:body][:message][:extra][:custom_data_method_context].should be_nil
239
- end
240
- end
241
- end
242
- end
243
-
244
- context 'with before_process handlers in configuration' do
245
- let!(:notifier) { Rollbar::Notifier.new }
246
- let(:scope) { { :bar => :foo } }
247
- let(:configuration) do
248
- config = Rollbar::Configuration.new
249
- config.access_token = test_access_token
250
- config.enabled = true
251
- config
252
- end
253
- let(:message) { 'message' }
254
- let(:exception) { Exception.new }
255
- let(:extra) { {:foo => :bar } }
256
- let(:level) { 'error' }
257
-
258
- before do
259
- notifier.configuration = configuration
260
- notifier.scope!(scope)
261
- end
262
-
263
- context 'without raise Rollbar::Ignore' do
264
- let(:handler) do
265
- proc do |options|
266
-
267
- end
268
- end
269
-
270
- before do
271
- configuration.before_process = handler
272
- end
273
-
274
- it 'calls the handler with the correct options' do
275
- options = {
276
- :level => level,
277
- :scope => Rollbar::LazyStore.new(scope),
278
- :exception => exception,
279
- :message => message,
280
- :extra => extra
281
- }
282
-
283
- expect(handler).to receive(:call).with(options)
284
- expect(notifier).to receive(:report).with(level, message, exception, extra, nil)
285
-
286
- notifier.log(level, message, exception, extra)
287
- end
288
- end
289
-
290
- context 'raising Rollbar::Ignore in the handler' do
291
- let(:handler) do
292
- proc do |options|
293
- raise Rollbar::Ignore
294
- end
295
- end
296
-
297
- before do
298
- configuration.before_process = handler
299
- end
300
-
301
- it "calls the handler with correct options and doesn't call #report" do
302
- options = {
303
- :level => level,
304
- :scope => Rollbar::LazyStore.new(scope),
305
- :exception => exception,
306
- :message => message,
307
- :extra => extra
308
- }
309
- expect(handler).to receive(:call).with(options).and_call_original
310
- expect(notifier).not_to receive(:report)
311
-
312
- result = notifier.log(level, message, exception, extra)
313
-
314
- expect(result).to be_eql('ignored')
315
- end
316
- end
317
-
318
- context 'with 2 handlers, raising Rollbar::Ignore in the first one' do
319
- let(:handler1) do
320
- proc do |options|
321
- raise Rollbar::Ignore
322
- end
323
- end
324
-
325
- let(:handler2) do
326
- proc do |options|
327
-
328
- end
329
- end
330
-
331
- before do
332
- configuration.before_process << handler1
333
- configuration.before_process << handler2
334
- end
335
-
336
- it "calls only the first handler and doesn't calls #report" do
337
- options = {
338
- :level => level,
339
- :scope => Rollbar::LazyStore.new(scope),
340
- :exception => exception,
341
- :message => message,
342
- :extra => extra
343
- }
344
-
345
- expect(handler1).to receive(:call).with(options).and_call_original
346
- expect(handler2).not_to receive(:call)
347
- expect(notifier).not_to receive(:report)
348
-
349
- result = notifier.log(level, message, exception, extra)
350
-
351
- expect(result).to be_eql('ignored')
352
- end
353
-
354
- context 'if the first handler fails' do
355
- let(:exception) { StandardError.new('foo') }
356
- let(:handler1) do
357
- proc { |options| raise exception }
358
- end
359
-
360
- it 'doesnt call the second handler and logs the error' do
361
- expect(handler2).not_to receive(:call)
362
- expect(notifier).to receive(:log_error).with("[Rollbar] Error calling the `before_process` hook: #{exception}")
363
-
364
- notifier.log(level, message, exception, extra)
365
- end
366
- end
367
- end
368
- end
369
-
370
- context 'debug/info/warning/error/critical' do
371
- let(:exception) do
372
- begin
373
- foo = bar
374
- rescue => e
375
- e
376
- end
377
- end
378
-
379
- let(:extra_data) { {:key => 'value', :hash => {:inner_key => 'inner_value'}} }
380
-
381
- it 'should report with a debug level' do
382
- expect(notifier).to receive(:report).with('debug', nil, exception, nil, nil)
383
- notifier.debug(exception)
384
-
385
- expect(notifier).to receive(:report).with('debug', 'description', exception, nil, nil)
386
- notifier.debug(exception, 'description')
387
-
388
- expect(notifier).to receive(:report).with('debug', 'description', exception, extra_data, nil)
389
- notifier.debug(exception, 'description', extra_data)
390
- end
391
-
392
- it 'should report with an info level' do
393
- expect(notifier).to receive(:report).with('info', nil, exception, nil, nil)
394
- notifier.info(exception)
395
-
396
- expect(notifier).to receive(:report).with('info', 'description', exception, nil, nil)
397
- notifier.info(exception, 'description')
398
-
399
- expect(notifier).to receive(:report).with('info', 'description', exception, extra_data, nil)
400
- notifier.info(exception, 'description', extra_data)
401
- end
402
-
403
- it 'should report with a warning level' do
404
- expect(notifier).to receive(:report).with('warning', nil, exception, nil, nil)
405
- notifier.warning(exception)
406
-
407
- expect(notifier).to receive(:report).with('warning', 'description', exception, nil, nil)
408
- notifier.warning(exception, 'description')
409
-
410
- expect(notifier).to receive(:report).with('warning', 'description', exception, extra_data, nil)
411
- notifier.warning(exception, 'description', extra_data)
412
- end
413
-
414
- it 'should report with an error level' do
415
- expect(notifier).to receive(:report).with('error', nil, exception, nil, nil)
416
- notifier.error(exception)
417
-
418
- expect(notifier).to receive(:report).with('error', 'description', exception, nil, nil)
419
- notifier.error(exception, 'description')
420
-
421
- expect(notifier).to receive(:report).with('error', 'description', exception, extra_data, nil)
422
- notifier.error(exception, 'description', extra_data)
423
- end
424
-
425
- it 'should report with a critical level' do
426
- expect(notifier).to receive(:report).with('critical', nil, exception, nil, nil)
427
- notifier.critical(exception)
428
-
429
- expect(notifier).to receive(:report).with('critical', 'description', exception, nil, nil)
430
- notifier.critical(exception, 'description')
431
-
432
- expect(notifier).to receive(:report).with('critical', 'description', exception, extra_data, nil)
433
- notifier.critical(exception, 'description', extra_data)
434
- end
435
- end
436
-
437
- context 'scope' do
438
- it 'should create a new notifier object' do
439
- notifier2 = notifier.scope
440
-
441
- notifier2.should_not eq(notifier)
442
- notifier2.should be_instance_of(Rollbar::Notifier)
443
- end
444
-
445
- it 'should create a copy of the parent notifier\'s configuration' do
446
- notifier.configure do |config|
447
- config.code_version = '123'
448
- config.payload_options = {
449
- :a => 'a',
450
- :b => {:c => 'c'}
451
- }
452
- end
453
-
454
- notifier2 = notifier.scope
455
-
456
- notifier2.configuration.code_version.should == '123'
457
- notifier2.configuration.should_not equal(notifier.configuration)
458
- notifier2.configuration.payload_options.should_not equal(notifier.configuration.payload_options)
459
- notifier2.configuration.payload_options.should == notifier.configuration.payload_options
460
- notifier2.configuration.payload_options.should == {
461
- :a => 'a',
462
- :b => {:c => 'c'}
463
- }
464
- end
465
-
466
- it 'should not modify any parent notifier configuration' do
467
- Rollbar.clear_notifier!
468
- configure
469
- Rollbar.configuration.code_version.should be_nil
470
- Rollbar.configuration.payload_options.should be_empty
471
-
472
- notifier = Rollbar.notifier.scope
473
- notifier.configure do |config|
474
- config.code_version = '123'
475
- config.payload_options = {
476
- :a => 'a',
477
- :b => {:c => 'c'}
478
- }
479
- end
480
-
481
- notifier2 = notifier.scope
482
-
483
- notifier2.configure do |config|
484
- config.payload_options[:c] = 'c'
485
- end
486
-
487
- notifier.configuration.payload_options[:c].should be_nil
488
-
489
- notifier3 = notifier2.scope({
490
- :b => {:c => 3, :d => 'd'}
491
- })
492
-
493
- notifier3.configure do |config|
494
- config.code_version = '456'
495
- end
496
-
497
- notifier.configuration.code_version.should == '123'
498
- notifier.configuration.payload_options.should == {
499
- :a => 'a',
500
- :b => {:c => 'c'}
501
- }
502
- notifier2.configuration.code_version.should == '123'
503
- notifier2.configuration.payload_options.should == {
504
- :a => 'a',
505
- :b => {:c => 'c'},
506
- :c => 'c'
507
- }
508
- notifier3.configuration.code_version.should == '456'
509
- notifier3.configuration.payload_options.should == {
510
- :a => 'a',
511
- :b => {:c => 'c'},
512
- :c => 'c'
513
- }
514
-
515
- Rollbar.configuration.code_version.should be_nil
516
- Rollbar.configuration.payload_options.should be_empty
517
- end
518
- end
519
-
520
- context 'report' do
521
- let(:logger_mock) { double("Rails.logger").as_null_object }
522
-
523
- before(:each) do
524
- configure
525
- Rollbar.configure do |config|
526
- config.logger = logger_mock
527
- end
528
- end
529
-
530
- after do
531
- configure
532
- end
533
-
534
- it 'should reject input that doesn\'t contain an exception, message or extra data' do
535
- expect(logger_mock).to receive(:error).with('[Rollbar] Tried to send a report with no message, exception or extra data.')
536
- expect(notifier).not_to receive(:schedule_payload)
537
-
538
- result = notifier.send(:report, 'info', nil, nil, nil, nil)
539
- result.should == 'error'
540
- end
541
-
542
- it 'should be ignored if the person is ignored' do
543
- person_data = {
544
- :id => 1,
545
- :username => "test",
546
- :email => "test@example.com"
547
- }
548
-
549
- notifier.configure do |config|
550
- config.ignored_person_ids += [1]
551
- config.payload_options = { :person => person_data }
552
- end
553
-
554
- expect(notifier).not_to receive(:schedule_payload)
555
-
556
- result = notifier.send(:report, 'info', 'message', nil, nil, nil)
557
- result.should == 'ignored'
558
- end
559
- end
560
- end
561
-
562
- context 'reporting' do
563
- let(:exception) do
564
- begin
565
- foo = bar
566
- rescue => e
567
- e
568
- end
569
- end
570
-
571
- let(:logger_mock) { double("Rails.logger").as_null_object }
572
- let(:user) { User.create(:email => 'email@example.com', :encrypted_password => '', :created_at => Time.now, :updated_at => Time.now) }
573
-
574
- before do
575
- Rollbar.unconfigure
576
- configure
577
-
578
- Rollbar.configure do |config|
579
- config.logger = logger_mock
580
- end
581
- end
582
-
583
- it 'should report exceptions without person or request data' do
584
- logger_mock.should_receive(:info).with('[Rollbar] Success')
585
- Rollbar.error(exception)
586
- end
587
-
588
- it 'should not report anything when disabled' do
589
- logger_mock.should_not_receive(:info).with('[Rollbar] Success')
590
-
591
- Rollbar.configure do |config|
592
- config.enabled = false
593
- end
594
-
595
- Rollbar.error(exception).should == 'disabled'
596
- end
597
-
598
- it 'should report exceptions without person or request data' do
599
- logger_mock.should_receive(:info).with('[Rollbar] Success')
600
- Rollbar.error(exception)
601
- end
602
-
603
- it 'should be enabled when freshly configured' do
604
- Rollbar.configuration.enabled.should == true
605
- end
606
-
607
- it 'should not be enabled when not configured' do
608
- Rollbar.clear_notifier!
609
-
610
- Rollbar.configuration.enabled.should be_nil
611
- Rollbar.error(exception).should == 'disabled'
612
- end
613
-
614
- it 'should stay disabled if configure is called again' do
615
- # configure once, setting enabled to false.
616
- Rollbar.configure do |config|
617
- config.enabled = false
618
- end
619
-
620
- # now configure again (perhaps to change some other values)
621
- Rollbar.configure { |_| }
622
-
623
- Rollbar.configuration.enabled.should == false
624
- Rollbar.error(exception).should == 'disabled'
625
- end
626
-
627
- context 'using configuration.use_exception_level_filters_default' do
628
- before do
629
- Rollbar.configure do |config|
630
- config.use_exception_level_filters_default = true
631
- end
632
- end
633
-
634
- context 'without use_exception_level_filters argument' do
635
- it 'sends the correct filtered level' do
636
- Rollbar.configure do |config|
637
- config.exception_level_filters = { 'NameError' => 'warning' }
638
- end
639
-
640
- Rollbar.error(exception)
641
-
642
- expect(Rollbar.last_report[:level]).to be_eql('warning')
643
- end
644
-
645
- it 'ignore ignored exception classes' do
646
- Rollbar.configure do |config|
647
- config.exception_level_filters = { 'NameError' => 'ignore' }
648
- end
649
-
650
- logger_mock.should_not_receive(:info)
651
- logger_mock.should_not_receive(:warn)
652
- logger_mock.should_not_receive(:error)
653
-
654
- Rollbar.error(exception)
655
- end
656
-
657
- it 'should not use the filters if overriden at log site' do
658
- Rollbar.configure do |config|
659
- config.exception_level_filters = { 'NameError' => 'ignore' }
660
- end
661
-
662
- Rollbar.error(exception, :use_exception_level_filters => false)
663
-
664
- expect(Rollbar.last_report[:level]).to be_eql('error')
665
- end
666
- end
667
- end
668
-
669
- context 'using :use_exception_level_filters option as true' do
670
- it 'sends the correct filtered level' do
671
- Rollbar.configure do |config|
672
- config.exception_level_filters = { 'NameError' => 'warning' }
673
- end
674
-
675
- Rollbar.error(exception, :use_exception_level_filters => true)
676
- expect(Rollbar.last_report[:level]).to be_eql('warning')
677
- end
678
-
679
- it 'ignore ignored exception classes' do
680
- Rollbar.configure do |config|
681
- config.exception_level_filters = { 'NameError' => 'ignore' }
682
- end
683
-
684
- logger_mock.should_not_receive(:info)
685
- logger_mock.should_not_receive(:warn)
686
- logger_mock.should_not_receive(:error)
687
-
688
- Rollbar.error(exception, :use_exception_level_filters => true)
689
- end
690
-
691
- context 'using :use_exception_level_filters option as false' do
692
- it 'sends the correct filtered level' do
693
- Rollbar.configure do |config|
694
- config.exception_level_filters = { 'NameError' => 'warning' }
695
- end
696
-
697
- Rollbar.error(exception, :use_exception_level_filters => false)
698
- expect(Rollbar.last_report[:level]).to be_eql('error')
699
- end
700
-
701
- it 'ignore ignored exception classes' do
702
- Rollbar.configure do |config|
703
- config.exception_level_filters = { 'NameError' => 'ignore' }
704
- end
705
-
706
- Rollbar.error(exception, :use_exception_level_filters => false)
707
-
708
- expect(Rollbar.last_report[:level]).to be_eql('error')
709
- end
710
- end
711
- end
712
-
713
- context 'using :use_exception_level_filters option as true' do
714
- it 'sends the correct filtered level' do
715
- Rollbar.configure do |config|
716
- config.exception_level_filters = { 'NameError' => 'warning' }
717
- end
718
-
719
- Rollbar.error(exception, :use_exception_level_filters => true)
720
- expect(Rollbar.last_report[:level]).to be_eql('warning')
721
- end
722
-
723
- it 'ignore ignored exception classes' do
724
- Rollbar.configure do |config|
725
- config.exception_level_filters = { 'NameError' => 'ignore' }
726
- end
727
-
728
- logger_mock.should_not_receive(:info)
729
- logger_mock.should_not_receive(:warn)
730
- logger_mock.should_not_receive(:error)
731
-
732
- Rollbar.error(exception, :use_exception_level_filters => true)
733
- end
734
- end
735
-
736
- context 'if not using :use_exception_level_filters option' do
737
- it 'sends the level defined by the used method' do
738
- Rollbar.configure do |config|
739
- config.exception_level_filters = { 'NameError' => 'warning' }
740
- end
741
-
742
- Rollbar.error(exception)
743
- expect(Rollbar.last_report[:level]).to be_eql('error')
744
- end
745
-
746
- it 'ignore ignored exception classes' do
747
- Rollbar.configure do |config|
748
- config.exception_level_filters = { 'NameError' => 'ignore' }
749
- end
750
-
751
- Rollbar.error(exception)
752
-
753
- expect(Rollbar.last_report[:level]).to be_eql('error')
754
- end
755
- end
756
-
757
- # Skip jruby 1.9+ (https://github.com/jruby/jruby/issues/2373)
758
- if defined?(RUBY_ENGINE) && RUBY_ENGINE == 'jruby' && (not RUBY_VERSION =~ /^1\.9/)
759
- it "should work with an IO object as rack.errors" do
760
- logger_mock.should_receive(:info).with('[Rollbar] Success')
761
-
762
- Rollbar.error(exception, :env => { :"rack.errors" => IO.new(2, File::WRONLY) })
763
- end
764
- end
765
-
766
- it 'should ignore ignored persons' do
767
- person_data = {
768
- :id => 1,
769
- :username => "test",
770
- :email => "test@example.com"
771
- }
772
-
773
- Rollbar.configure do |config|
774
- config.payload_options = { :person => person_data }
775
- config.ignored_person_ids += [1]
776
- end
777
-
778
- logger_mock.should_not_receive(:info)
779
- logger_mock.should_not_receive(:warn)
780
- logger_mock.should_not_receive(:error)
781
-
782
- Rollbar.error(exception)
783
- end
784
-
785
- it 'should not ignore non-ignored persons' do
786
- person_data = {
787
- :id => 1,
788
- :username => "test",
789
- :email => "test@example.com"
790
- }
791
- Rollbar.configure do |config|
792
- config.payload_options = { :person => person_data }
793
- config.ignored_person_ids += [1]
794
- end
795
-
796
- Rollbar.last_report = nil
797
-
798
- Rollbar.error(exception)
799
- Rollbar.last_report.should be_nil
800
-
801
- person_data = {
802
- :id => 2,
803
- :username => "test2",
804
- :email => "test2@example.com"
805
- }
806
-
807
- new_options = {
808
- :person => person_data
809
- }
810
-
811
- Rollbar.scoped(new_options) do
812
- Rollbar.error(exception)
813
- end
814
-
815
- Rollbar.last_report.should_not be_nil
816
- end
817
-
818
- it 'should allow callables to set exception filtered level' do
819
- callable_mock = double
820
- saved_filters = Rollbar.configuration.exception_level_filters
821
-
822
- Rollbar.configure do |config|
823
- config.exception_level_filters = { 'NameError' => callable_mock }
824
- end
825
-
826
- callable_mock.should_receive(:call).with(exception).at_least(:once).and_return("info")
827
- logger_mock.should_receive(:info)
828
- logger_mock.should_not_receive(:warn)
829
- logger_mock.should_not_receive(:error)
830
-
831
- Rollbar.error(exception, :use_exception_level_filters => true)
832
- end
833
-
834
- it 'should not report exceptions when silenced' do
835
- expect_any_instance_of(Rollbar::Notifier).to_not receive(:schedule_payload)
836
-
837
- begin
838
- test_var = 1
839
- Rollbar.silenced do
840
- test_var = 2
841
- raise
842
- end
843
- rescue => e
844
- Rollbar.error(e)
845
- end
846
-
847
- test_var.should == 2
848
- end
849
-
850
- it 'should report exception objects with no backtrace' do
851
- payload = nil
852
-
853
- notifier.stub(:schedule_item) do |*args|
854
- payload = args[0]
855
- end
856
-
857
- Rollbar.error(StandardError.new("oops"))
858
-
859
- payload["data"][:body][:trace][:frames].should == []
860
- payload["data"][:body][:trace][:exception][:class].should == "StandardError"
861
- payload["data"][:body][:trace][:exception][:message].should == "oops"
862
- end
863
-
864
- it 'gets the backtrace from the caller' do
865
- Rollbar.configure do |config|
866
- config.populate_empty_backtraces = true
867
- end
868
-
869
- exception = Exception.new
870
-
871
- Rollbar.error(exception)
872
-
873
- gem_dir = Gem::Specification.find_by_name('rollbar').gem_dir
874
- gem_lib_dir = gem_dir + '/lib'
875
- last_report = Rollbar.last_report
876
-
877
- filepaths = last_report[:body][:trace][:frames].map {|frame| frame[:filename] }.reverse
878
-
879
- expect(filepaths[0]).not_to include(gem_lib_dir)
880
- expect(filepaths.any? {|filepath| filepath.include?(gem_dir) }).to eq true
881
- end
882
-
883
- it 'should return the exception data with a uuid, on platforms with SecureRandom' do
884
- if defined?(SecureRandom) and SecureRandom.respond_to?(:uuid)
885
- exception_data = Rollbar.error(StandardError.new("oops"))
886
- exception_data[:uuid].should_not be_nil
887
- end
888
- end
889
-
890
- it 'should report exception objects with nonstandard backtraces' do
891
- payload = nil
892
-
893
- notifier.stub(:schedule_item) do |*args|
894
- payload = args[0]
895
- end
896
-
897
- class CustomException < StandardError
898
- def backtrace
899
- ["custom backtrace line"]
900
- end
901
- end
902
-
903
- exception = CustomException.new("oops")
904
-
905
- notifier.error(exception)
906
-
907
- payload["data"][:body][:trace][:frames][0][:method].should == "custom backtrace line"
908
- end
909
-
910
- it 'should report exceptions with a custom level' do
911
- payload = nil
912
-
913
- notifier.stub(:schedule_item) do |*args|
914
- payload = args[0]
915
- end
916
-
917
- Rollbar.error(exception)
918
-
919
- payload['data'][:level].should == 'error'
920
-
921
- Rollbar.log('debug', exception)
922
-
923
- payload['data'][:level].should == 'debug'
924
- end
925
-
926
- context 'with invalid utf8 encoding' do
927
- let(:extra) do
928
- { :extra => force_to_ascii("bad value 1\255") }
929
- end
930
-
931
- it 'removes te invalid characteres' do
932
- Rollbar.info('removing invalid chars', extra)
933
-
934
- extra_value = Rollbar.last_report[:body][:message][:extra][:extra]
935
- expect(extra_value).to be_eql('bad value 1')
936
- end
937
- end
938
- end
939
-
940
- # Backwards
941
- context 'report_message' do
942
- before(:each) do
943
- configure
944
- Rollbar.configure do |config|
945
- config.logger = logger_mock
946
- end
947
- end
948
-
949
- let(:logger_mock) { double("Rails.logger").as_null_object }
950
- let(:user) { User.create(:email => 'email@example.com', :encrypted_password => '', :created_at => Time.now, :updated_at => Time.now) }
951
-
952
- it 'should report simple messages' do
953
- logger_mock.should_receive(:info).with('[Rollbar] Scheduling item')
954
- logger_mock.should_receive(:info).with('[Rollbar] Success')
955
- Rollbar.error('Test message')
956
- end
957
-
958
- it 'should not report anything when disabled' do
959
- logger_mock.should_not_receive(:info).with('[Rollbar] Success')
960
- Rollbar.configure do |config|
961
- config.enabled = false
962
- end
963
-
964
- Rollbar.error('Test message that should be ignored')
965
-
966
- Rollbar.configure do |config|
967
- config.enabled = true
968
- end
969
- end
970
-
971
- it 'should report messages with extra data' do
972
- logger_mock.should_receive(:info).with('[Rollbar] Success')
973
- Rollbar.debug('Test message with extra data', 'debug', :foo => "bar",
974
- :hash => { :a => 123, :b => "xyz" })
975
- end
976
-
977
- # END Backwards
978
-
979
- it 'should not crash with circular extra_data' do
980
- a = { :foo => "bar" }
981
- b = { :a => a }
982
- c = { :b => b }
983
- a[:c] = c
984
-
985
- logger_mock.should_receive(:error).with(/\[Rollbar\] Reporting internal error encountered while sending data to Rollbar./)
986
-
987
- Rollbar.error("Test message with circular extra data", a)
988
- end
989
-
990
- it 'should be able to report form validation errors when they are present' do
991
- logger_mock.should_receive(:info).with('[Rollbar] Success')
992
- user.errors.add(:example, "error")
993
- user.report_validation_errors_to_rollbar
994
- end
995
-
996
- it 'should not report form validation errors when they are not present' do
997
- logger_mock.should_not_receive(:info).with('[Rollbar] Success')
998
- user.errors.clear
999
- user.report_validation_errors_to_rollbar
1000
- end
1001
-
1002
- it 'should report messages with extra data' do
1003
- logger_mock.should_receive(:info).with('[Rollbar] Success')
1004
- Rollbar.info("Test message with extra data", :foo => "bar",
1005
- :hash => { :a => 123, :b => "xyz" })
1006
- end
1007
-
1008
- it 'should report messages with request, person data and extra data' do
1009
- logger_mock.should_receive(:info).with('[Rollbar] Scheduling item')
1010
- logger_mock.should_receive(:info).with('[Rollbar] Success')
1011
-
1012
- request_data = {
1013
- :params => {:foo => 'bar'}
1014
- }
1015
-
1016
- person_data = {
1017
- :id => 123,
1018
- :username => 'username'
1019
- }
1020
-
1021
- extra_data = {
1022
- :extra_foo => 'extra_bar'
1023
- }
1024
-
1025
- Rollbar.configure do |config|
1026
- config.payload_options = {
1027
- :request => request_data,
1028
- :person => person_data
1029
- }
1030
- end
1031
-
1032
- Rollbar.info("Test message", extra_data)
1033
-
1034
- Rollbar.last_report[:request].should == request_data
1035
- Rollbar.last_report[:person].should == person_data
1036
- Rollbar.last_report[:body][:message][:extra][:extra_foo].should == 'extra_bar'
1037
- end
1038
- end
1039
-
1040
- context 'payload_destination' do
1041
- before(:each) do
1042
- configure
1043
- Rollbar.configure do |config|
1044
- config.logger = logger_mock
1045
- config.filepath = 'test.rollbar'
1046
- end
1047
- end
1048
-
1049
- after do
1050
- configure
1051
- end
1052
-
1053
- let(:exception) do
1054
- begin
1055
- foo = bar
1056
- rescue => e
1057
- e
1058
- end
1059
- end
1060
-
1061
- let(:logger_mock) { double("Rails.logger").as_null_object }
1062
-
1063
- it 'should send the payload over the network by default' do
1064
- logger_mock.should_not_receive(:info).with('[Rollbar] Writing payload to file')
1065
- logger_mock.should_receive(:info).with('[Rollbar] Sending item').once
1066
- logger_mock.should_receive(:info).with('[Rollbar] Success').once
1067
- Rollbar.error(exception)
1068
- end
1069
-
1070
- it 'should save the payload to a file if set' do
1071
- logger_mock.should_not_receive(:info).with('[Rollbar] Sending item')
1072
- logger_mock.should_receive(:info).with('[Rollbar] Writing item to file').once
1073
- logger_mock.should_receive(:info).with('[Rollbar] Success').once
1074
-
1075
- filepath = ''
1076
-
1077
- Rollbar.configure do |config|
1078
- config.write_to_file = true
1079
- filepath = config.filepath
1080
- end
1081
-
1082
- Rollbar.error(exception)
1083
-
1084
- File.exist?(filepath).should == true
1085
- File.read(filepath).should include test_access_token
1086
- File.delete(filepath)
1087
-
1088
- Rollbar.configure do |config|
1089
- config.write_to_file = false
1090
- end
1091
- end
1092
- end
1093
-
1094
- context 'using a proxy server' do
1095
- before do
1096
- allow_any_instance_of(Net::HTTP).to receive(:request).and_return(OpenStruct.new(:code => 200, :body => "Success"))
1097
- @env_vars = clear_proxy_env_vars
1098
- end
1099
-
1100
- after do
1101
- restore_proxy_env_vars(@env_vars)
1102
- end
1103
-
1104
- context 'via environment variables' do
1105
- before do
1106
- @uri = URI.parse(Rollbar::Configuration::DEFAULT_ENDPOINT)
1107
- end
1108
-
1109
- it 'honors proxy settings in the environment' do
1110
- ENV['http_proxy'] = 'http://user:pass@example.com:80'
1111
- ENV['https_proxy'] = 'http://user:pass@example.com:80'
1112
-
1113
- expect(Net::HTTP).to receive(:new).with(@uri.host, @uri.port, 'example.com', 80, 'user', 'pass').and_call_original
1114
- Rollbar.info("proxy this")
1115
- end
1116
-
1117
- it 'does not use a proxy if no proxy settings in environemnt' do
1118
- expect(Net::HTTP).to receive(:new).with(@uri.host, @uri.port, nil, nil, nil, nil).and_call_original
1119
- Rollbar.info("proxy this")
1120
- end
1121
- end
1122
-
1123
- context 'set in configuration file' do
1124
- before do
1125
- Rollbar.configure do |config|
1126
- config.proxy = {
1127
- :host => 'http://config.com',
1128
- :port => 8080,
1129
- :user => 'foo',
1130
- :password => 'bar'
1131
- }
1132
- end
1133
-
1134
- @uri = URI.parse(Rollbar::Configuration::DEFAULT_ENDPOINT)
1135
- end
1136
-
1137
- it 'honors proxy settings in the config file' do
1138
- expect(Net::HTTP).to receive(:new).with(@uri.host, @uri.port, 'config.com', 8080, 'foo', 'bar').and_call_original
1139
- Rollbar.info("proxy this")
1140
- end
1141
-
1142
- it 'gives the configuration settings precedence over environment' do
1143
- ENV['http_proxy'] = 'http://user:pass@example.com:80'
1144
- ENV['https_proxy'] = 'http://user:pass@example.com:80'
1145
-
1146
- expect(Net::HTTP).to receive(:new).with(@uri.host, @uri.port, 'config.com', 8080, 'foo', 'bar').and_call_original
1147
- Rollbar.info("proxy this")
1148
- end
1149
-
1150
- it 'allows @-signs in passwords' do
1151
- Rollbar.configure do |config|
1152
- config.proxy[:password] = "manh@tan"
1153
- end
1154
-
1155
- expect(Net::HTTP).to receive(:new).with(@uri.host, @uri.port, 'config.com', 8080, 'foo', 'manh@tan').and_call_original
1156
- Rollbar.info("proxy this")
1157
- end
1158
- end
1159
- end
1160
-
1161
- context 'asynchronous_handling' do
1162
- before do
1163
- Rollbar.clear_notifier!
1164
- configure
1165
- Rollbar.configure do |config|
1166
- config.logger = logger_mock
1167
- end
1168
- end
1169
-
1170
- after do
1171
- configure
1172
- end
1173
-
1174
- let(:exception) do
1175
- begin
1176
- foo = bar
1177
- rescue => e
1178
- e
1179
- end
1180
- end
1181
-
1182
- let(:logger_mock) { double("Rails.logger").as_null_object }
1183
-
1184
- it 'should send the payload using the default asynchronous handler girl_friday' do
1185
- logger_mock.should_receive(:info).with('[Rollbar] Scheduling item')
1186
- logger_mock.should_receive(:info).with('[Rollbar] Sending item')
1187
- logger_mock.should_receive(:info).with('[Rollbar] Success')
1188
-
1189
- Rollbar.configure do |config|
1190
- config.use_async = true
1191
- GirlFriday::WorkQueue.immediate!
1192
- end
1193
-
1194
- Rollbar.error(exception)
1195
-
1196
- Rollbar.configure do |config|
1197
- config.use_async = false
1198
- GirlFriday::WorkQueue.queue!
1199
- end
1200
- end
1201
-
1202
- it 'should send the payload using a user-supplied asynchronous handler' do
1203
- logger_mock.should_receive(:info).with('Custom async handler called')
1204
- logger_mock.should_receive(:info).with('[Rollbar] Sending item')
1205
- logger_mock.should_receive(:info).with('[Rollbar] Success')
1206
-
1207
- Rollbar.configure do |config|
1208
- config.use_async = true
1209
- config.async_handler = Proc.new { |payload|
1210
- logger_mock.info 'Custom async handler called'
1211
- Rollbar.process_from_async_handler(payload)
1212
- }
1213
- end
1214
-
1215
- Rollbar.error(exception)
1216
- end
1217
-
1218
- # We should be able to send String payloads, generated
1219
- # by a previous version of the gem. This can happend just
1220
- # after a deploy with an gem upgrade.
1221
- context 'with a payload generated as String' do
1222
- let(:async_handler) do
1223
- proc do |payload|
1224
- # simulate previous gem version
1225
- string_payload = Rollbar::JSON.dump(payload)
1226
-
1227
- Rollbar.process_from_async_handler(string_payload)
1228
- end
1229
- end
1230
-
1231
- before do
1232
- Rollbar.configuration.stub(:use_async).and_return(true)
1233
- Rollbar.configuration.stub(:async_handler).and_return(async_handler)
1234
- end
1235
-
1236
- it 'sends a payload generated as String, not as a Hash' do
1237
- logger_mock.should_receive(:info).with('[Rollbar] Success')
1238
-
1239
- Rollbar.error(exception)
1240
- end
1241
-
1242
- context 'with async failover handlers' do
1243
- before do
1244
- Rollbar.reconfigure do |config|
1245
- config.use_async = true
1246
- config.async_handler = async_handler
1247
- config.failover_handlers = handlers
1248
- config.logger = logger_mock
1249
- end
1250
- end
1251
-
1252
- let(:exception) { StandardError.new('the error') }
1253
-
1254
- context 'if the async handler doesnt fail' do
1255
- let(:async_handler) { proc { |_| 'success' } }
1256
- let(:handler) { proc { |_| 'success' } }
1257
- let(:handlers) { [handler] }
1258
-
1259
- it 'doesnt call any failover handler' do
1260
- expect(handler).not_to receive(:call)
1261
-
1262
- Rollbar.error(exception)
1263
- end
1264
- end
1265
-
1266
- context 'if the async handler fails' do
1267
- let(:async_handler) { proc { |_| fail 'this handler will crash' } }
1268
-
1269
- context 'if any failover handlers is configured' do
1270
- let(:handlers) { [] }
1271
- let(:log_message) do
1272
- '[Rollbar] Async handler failed, and there are no failover handlers configured. See the docs for "failover_handlers"'
1273
- end
1274
-
1275
- it 'logs the error but doesnt try to report an internal error' do
1276
- expect(logger_mock).to receive(:error).with(log_message)
1277
-
1278
- Rollbar.error(exception)
1279
- end
1280
- end
1281
-
1282
- context 'if the first failover handler success' do
1283
- let(:handler) { proc { |_| 'success' } }
1284
- let(:handlers) { [handler] }
1285
-
1286
- it 'calls the failover handler and doesnt report internal error' do
1287
- expect(Rollbar).not_to receive(:report_internal_error)
1288
- expect(handler).to receive(:call)
1289
-
1290
- Rollbar.error(exception)
1291
- end
1292
- end
1293
-
1294
- context 'with two handlers, the first failing' do
1295
- let(:handler1) { proc { |_| fail 'this handler fails' } }
1296
- let(:handler2) { proc { |_| 'success' } }
1297
- let(:handlers) { [handler1, handler2] }
1298
-
1299
- it 'calls the second handler and doesnt report internal error' do
1300
- expect(handler2).to receive(:call)
1301
-
1302
- Rollbar.error(exception)
1303
- end
1304
- end
1305
-
1306
- context 'with two handlers, both failing' do
1307
- let(:handler1) { proc { |_| fail 'this handler fails' } }
1308
- let(:handler2) { proc { |_| fail 'this will also fail' } }
1309
- let(:handlers) { [handler1, handler2] }
1310
-
1311
- it 'reports internal error' do
1312
- expect(logger_mock).to receive(:error)
1313
-
1314
- Rollbar.error(exception)
1315
- end
1316
- end
1317
- end
1318
- end
1319
- end
1320
-
1321
- describe "#use_sucker_punch", :if => defined?(SuckerPunch) do
1322
- it "should send the payload to sucker_punch delayer" do
1323
- logger_mock.should_receive(:info).with('[Rollbar] Scheduling item')
1324
- expect(Rollbar::Delay::SuckerPunch).to receive(:call)
1325
-
1326
- Rollbar.configure(&:use_sucker_punch)
1327
- Rollbar.error(exception)
1328
- end
1329
- end
1330
-
1331
- describe "#use_shoryuken", :if => defined?(Shoryuken) do
1332
- it "should send the payload to shoryuken delayer" do
1333
- logger_mock.should_receive(:info).with('[Rollbar] Scheduling item')
1334
- expect(Rollbar::Delay::Shoryuken).to receive(:call)
1335
-
1336
- Rollbar.configure(&:use_shoryuken)
1337
- Rollbar.error(exception)
1338
- end
1339
- end
1340
-
1341
- describe "#use_sidekiq", :if => defined?(Sidekiq) do
1342
- it "should instanciate sidekiq delayer with custom values" do
1343
- Rollbar::Delay::Sidekiq.should_receive(:new).with('queue' => 'test_queue')
1344
- config = Rollbar::Configuration.new
1345
- config.use_sidekiq 'queue' => 'test_queue'
1346
- end
1347
-
1348
- it "should send the payload to sidekiq delayer" do
1349
- handler = double('sidekiq_handler_mock')
1350
- handler.should_receive(:call)
1351
-
1352
- Rollbar.configure do |config|
1353
- config.use_sidekiq
1354
- config.async_handler = handler
1355
- end
1356
-
1357
- Rollbar.error(exception)
1358
- end
1359
- end
1360
- end
1361
-
1362
- context 'logger' do
1363
- before(:each) do
1364
- reset_configuration
1365
- end
1366
-
1367
- it 'should have use the Rails logger when configured to do so' do
1368
- configure
1369
- expect(Rollbar.send(:logger)).to be_kind_of(Rollbar::LoggerProxy)
1370
- expect(Rollbar.send(:logger).object).to eq ::Rails.logger
1371
- end
1372
-
1373
- it 'should use the default_logger when no logger is set' do
1374
- logger = Logger.new(STDERR)
1375
-
1376
- Rollbar.configure do |config|
1377
- config.default_logger = lambda { logger }
1378
- end
1379
-
1380
- Rollbar.send(:logger).object.should == logger
1381
- end
1382
-
1383
- it 'should have a default default_logger' do
1384
- Rollbar.send(:logger).should_not be_nil
1385
- end
1386
-
1387
- after do
1388
- reset_configuration
1389
- end
1390
- end
1391
-
1392
- context "project_gems" do
1393
- it "should include gem paths for specified project gems in the payload" do
1394
- gems = ['rack', 'rspec-rails']
1395
- gem_paths = []
1396
-
1397
- Rollbar.configure do |config|
1398
- config.project_gems = gems
1399
- end
1400
-
1401
- gem_paths = gems.map do |gem|
1402
- gem_spec = Gem::Specification.find_all_by_name(gem)[0]
1403
- gem_spec.gem_dir if gem_spec
1404
- end.compact
1405
-
1406
- data = notifier.send(:build_item, 'info', 'test', nil, {}, nil)['data']
1407
- data[:project_package_paths].kind_of?(Array).should == true
1408
- data[:project_package_paths].length.should == gem_paths.length
1409
-
1410
- data[:project_package_paths].each_with_index{|path, index|
1411
- path.should == gem_paths[index]
1412
- }
1413
- end
1414
-
1415
- it "should handle regex gem patterns" do
1416
- gems = ["rack", /rspec/, /roll/]
1417
- gem_paths = []
1418
-
1419
- Rollbar.configure do |config|
1420
- config.project_gems = gems
1421
- end
1422
-
1423
- gem_paths = gems.map{|gem| Gem::Specification.find_all_by_name(gem).map(&:gem_dir) }.flatten.compact.uniq
1424
- gem_paths.length.should > 1
1425
-
1426
- gem_paths.any?{|path| path.include? 'rollbar-gem'}.should == true
1427
- gem_paths.any?{|path| path.include? 'rspec-rails'}.should == true
1428
-
1429
- data = notifier.send(:build_item, 'info', 'test', nil, {}, nil)['data']
1430
- data[:project_package_paths].kind_of?(Array).should == true
1431
- data[:project_package_paths].length.should == gem_paths.length
1432
- (data[:project_package_paths] - gem_paths).length.should == 0
1433
- end
1434
-
1435
- it "should not break on non-existent gems" do
1436
- gems = ["this_gem_does_not_exist", "rack"]
1437
-
1438
- Rollbar.configure do |config|
1439
- config.project_gems = gems
1440
- end
1441
-
1442
- data = notifier.send(:build_item, 'info', 'test', nil, {}, nil)['data']
1443
- data[:project_package_paths].kind_of?(Array).should == true
1444
- data[:project_package_paths].length.should == 1
1445
- end
1446
- end
1447
-
1448
- context 'report_internal_error', :reconfigure_notifier => true do
1449
- it "should not crash when given an exception object" do
1450
- begin
1451
- 1 / 0
1452
- rescue => e
1453
- notifier.send(:report_internal_error, e)
1454
- end
1455
- end
1456
- end
1457
-
1458
- context "send_failsafe" do
1459
- let(:exception) { StandardError.new }
1460
-
1461
- it "doesn't crash when given a message and exception" do
1462
- sent_payload = notifier.send(:send_failsafe, "test failsafe", exception)
1463
-
1464
- expected_message = 'Failsafe from rollbar-gem. StandardError: test failsafe'
1465
- expect(sent_payload['data'][:body][:message][:body]).to be_eql(expected_message)
1466
- end
1467
-
1468
- it "doesn't crash when given all nils" do
1469
- notifier.send(:send_failsafe, nil, nil)
1470
- end
1471
-
1472
- context 'with a non default exception message' do
1473
- let(:exception) { StandardError.new 'Something is wrong' }
1474
-
1475
- it 'adds it to exception info' do
1476
- sent_payload = notifier.send(:send_failsafe, "test failsafe", exception)
1477
-
1478
- expected_message = 'Failsafe from rollbar-gem. StandardError: "Something is wrong": test failsafe'
1479
- expect(sent_payload['data'][:body][:message][:body]).to be_eql(expected_message)
1480
- end
1481
- end
1482
-
1483
- context 'without exception object' do
1484
- it 'just sends the given message' do
1485
- sent_payload = notifier.send(:send_failsafe, "test failsafe", nil)
1486
-
1487
- expected_message = 'Failsafe from rollbar-gem. test failsafe'
1488
- expect(sent_payload['data'][:body][:message][:body]).to be_eql(expected_message)
1489
- end
1490
- end
1491
-
1492
- context 'if the exception has a backtrace' do
1493
- let(:backtrace) { ['func3', 'func2', 'func1'] }
1494
- let(:failsafe_reason) { 'StandardError in func3: test failsafe' }
1495
- let(:expected_body) { "Failsafe from rollbar-gem. #{failsafe_reason}" }
1496
- let(:expected_log_message) do
1497
- "[Rollbar] Sending failsafe response due to #{failsafe_reason}"
1498
- end
1499
-
1500
- before { exception.set_backtrace(backtrace) }
1501
-
1502
- it 'adds the nearest frame to the message' do
1503
- expect(notifier).to receive(:log_error).with(expected_log_message)
1504
-
1505
- sent_payload = notifier.send(:send_failsafe, "test failsafe", exception)
1506
-
1507
- expect(sent_payload['data'][:body][:message][:body]).to be_eql(expected_body)
1508
- end
1509
- end
1510
-
1511
- context 'with uuid and host' do
1512
- let(:host) { 'the-host' }
1513
- let(:uuid) { 'the-uuid' }
1514
- it 'sets the uuid and host in correct keys' do
1515
- sent_payload = notifier.send(:send_failsafe, 'testing uuid and host',
1516
- exception, uuid, host)
1517
-
1518
- expect(sent_payload['data'][:custom][:orig_uuid]).to be_eql('the-uuid')
1519
- expect(sent_payload['data'][:custom][:orig_host]).to be_eql('the-host')
1520
- end
1521
- end
1522
- end
1523
-
1524
- context 'when reporting internal error with nil context' do
1525
- let(:context_proc) { proc {} }
1526
- let(:scoped_notifier) { notifier.scope(:context => context_proc) }
1527
- let(:exception) { Exception.new }
1528
- let(:logger_mock) { double("Rails.logger").as_null_object }
1529
-
1530
- it 'reports successfully' do
1531
- configure
1532
-
1533
- Rollbar.configure do |config|
1534
- config.logger = logger_mock
1535
- end
1536
-
1537
- logger_mock.should_receive(:info).with('[Rollbar] Sending item').once
1538
- logger_mock.should_receive(:info).with('[Rollbar] Success').once
1539
- scoped_notifier.send(:report_internal_error, exception)
1540
- end
1541
- end
1542
-
1543
- context "request_data_extractor" do
1544
- before(:each) do
1545
- class DummyClass
1546
- end
1547
- @dummy_class = DummyClass.new
1548
- @dummy_class.extend(Rollbar::RequestDataExtractor)
1549
- end
1550
-
1551
- context "rollbar_headers" do
1552
- it "should not include cookies" do
1553
- env = {"HTTP_USER_AGENT" => "test", "HTTP_COOKIE" => "cookie"}
1554
- headers = @dummy_class.send(:rollbar_headers, env)
1555
- headers.should have_key "User-Agent"
1556
- headers.should_not have_key "Cookie"
1557
- end
1558
- end
1559
- end
1560
-
1561
- describe '.scoped' do
1562
- let(:scope_options) do
1563
- { :foo => 'bar' }
1564
- end
1565
-
1566
- it 'changes data in scope_object inside the block' do
1567
- Rollbar.clear_notifier!
1568
- configure
1569
-
1570
- current_notifier_id = Rollbar.notifier.object_id
1571
-
1572
- Rollbar.scoped(scope_options) do
1573
- scope_object = Rollbar.notifier.scope_object
1574
-
1575
- expect(Rollbar.notifier.object_id).not_to be_eql(current_notifier_id)
1576
- expect(scope_object).to be_eql(scope_options)
1577
- end
1578
-
1579
- expect(Rollbar.notifier.object_id).to be_eql(current_notifier_id)
1580
- end
1581
-
1582
- context 'if the block fails' do
1583
- let(:crashing_block) { proc { fail } }
1584
-
1585
- it 'restores the old notifier' do
1586
- notifier = Rollbar.notifier
1587
-
1588
- expect { Rollbar.scoped(&crashing_block) }.to raise_error
1589
- expect(notifier).to be_eql(Rollbar.notifier)
1590
- end
1591
- end
1592
-
1593
- context 'if the block creates a new thread' do
1594
- let(:block) do
1595
- proc do
1596
- Thread.new do
1597
- scope = Rollbar.notifier.scope_object
1598
- Thread.main[:inner_scope] = scope
1599
- end.join
1600
- end
1601
- end
1602
-
1603
- let(:scope) do
1604
- { :foo => 'bar' }
1605
- end
1606
-
1607
- it 'maintains the parent thread notifier scope' do
1608
- Rollbar.scoped(scope, &block)
1609
-
1610
- expect(Thread.main[:inner_scope]).to be_eql(scope)
1611
- end
1612
- end
1613
- end
1614
-
1615
- describe '.scope!' do
1616
- let(:new_scope) do
1617
- { :person => { :id => 1 } }
1618
- end
1619
-
1620
- before { reconfigure_notifier }
1621
-
1622
- it 'adds the new scope to the payload options' do
1623
- scope_object = Rollbar.notifier.scope_object
1624
- Rollbar.scope!(new_scope)
1625
-
1626
- expect(scope_object).to be_eql(new_scope)
1627
- end
1628
- end
1629
-
1630
- describe '.clear_notifier' do
1631
- before { Rollbar.notifier }
1632
-
1633
- it 'resets the notifier' do
1634
- Rollbar.clear_notifier!
1635
- expect(Rollbar.instance_variable_get('@notifier')).to be_nil
1636
- expect(Rollbar.instance_variable_get('@root_notifier')).to be_nil
1637
- end
1638
- end
1639
-
1640
- describe '.process_item' do
1641
- context 'if there is an exception sending the payload' do
1642
- let(:exception) { StandardError.new('error message') }
1643
- let(:payload) { Rollbar::Item.build_with({ :foo => :bar }) }
1644
-
1645
- it 'logs the error and the payload' do
1646
- allow(Rollbar.notifier).to receive(:send_item).and_raise(exception)
1647
- expect(Rollbar.notifier).to receive(:log_error)
1648
-
1649
- expect { Rollbar.notifier.process_item(payload) }.to raise_error(exception)
1650
- end
1651
- end
1652
- end
1653
-
1654
- describe '.process_from_async_handler' do
1655
- context 'with errors' do
1656
- let(:exception) { StandardError.new('the error') }
1657
-
1658
- it 'raises anything and sends internal error' do
1659
- allow(Rollbar.notifier).to receive(:process_item).and_raise(exception)
1660
- expect(Rollbar.notifier).to receive(:report_internal_error).with(exception)
1661
-
1662
- expect do
1663
- Rollbar.notifier.process_from_async_handler({})
1664
- end.to raise_error(exception)
1665
-
1666
- rollbar_do_not_report = exception.instance_variable_get(:@_rollbar_do_not_report)
1667
- expect(rollbar_do_not_report).to be_eql(true)
1668
- end
1669
- end
1670
- end
1671
-
1672
- describe '.preconfigure'do
1673
- before do
1674
- Rollbar.clear_notifier!
1675
- end
1676
-
1677
- it 'resets the notifier' do
1678
- Rollbar.configure do |config|
1679
- config.access_token = 'foo'
1680
- end
1681
-
1682
- Thread.new {}
1683
-
1684
- Rollbar.preconfigure do |config|
1685
- config.root = 'bar'
1686
- end
1687
-
1688
- notifier_config = Rollbar.notifier.configuration
1689
- expect(notifier_config.root).to be_eql('bar')
1690
- end
1691
- end
1692
-
1693
- context 'having timeout issues (for ruby > 1.9.3)' do
1694
- before do
1695
- skip if Rollbar::LanguageSupport.ruby_18? || Rollbar::LanguageSupport.ruby_19?
1696
- end
1697
-
1698
- let(:exception_class) do
1699
- Rollbar::LanguageSupport.timeout_exceptions.first
1700
- end
1701
- let(:net_exception) do
1702
- exception_class.new
1703
- end
1704
-
1705
- before do
1706
- allow_any_instance_of(Net::HTTP).to receive(:request).and_raise(net_exception)
1707
- end
1708
-
1709
- it 'retries the request' do
1710
- expect_any_instance_of(Net::HTTP).to receive(:request).exactly(3)
1711
- expect(Rollbar.notifier).to receive(:report_internal_error).with(net_exception)
1712
-
1713
- Rollbar.info('foo')
1714
- end
1715
- end
1716
-
1717
- describe '.with_config' do
1718
- let(:new_config) do
1719
- { 'environment' => 'foo' }
1720
- end
1721
-
1722
- it 'uses the new config and restores the old one' do
1723
- config1 = described_class.configuration
1724
-
1725
- subject.with_config(:environment => 'bar') do
1726
- expect(described_class.configuration).not_to be(config1)
1727
- end
1728
-
1729
- expect(described_class.configuration).to be(config1)
1730
- end
1731
- end
1732
-
1733
- # configure with some basic params
1734
- def configure
1735
- reconfigure_notifier
1736
- end
1737
- end