sentry-raven 3.1.1 → 3.1.2

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 (163) hide show
  1. checksums.yaml +4 -4
  2. data/.craft.yml +9 -5
  3. data/.scripts/bump-version.rb +5 -0
  4. data/CHANGELOG.md +11 -0
  5. data/Gemfile +5 -1
  6. data/Makefile +3 -0
  7. data/README.md +19 -7
  8. data/lib/raven/base.rb +1 -0
  9. data/lib/raven/configuration.rb +0 -1
  10. data/lib/raven/event.rb +5 -1
  11. data/lib/raven/instance.rb +7 -1
  12. data/lib/raven/integrations/delayed_job.rb +1 -1
  13. data/lib/raven/integrations/rack.rb +2 -14
  14. data/lib/raven/transports/http.rb +2 -1
  15. data/lib/raven/utils/request_id.rb +16 -0
  16. data/lib/raven/version.rb +1 -1
  17. data/sentry-raven.gemspec +7 -0
  18. metadata +10 -148
  19. data/.github/ISSUE_TEMPLATE/bug_report.md +0 -32
  20. data/.github/pull_request_template.md +0 -16
  21. data/.github/workflows/test.yml +0 -92
  22. data/.github/workflows/zeus_upload.yml +0 -32
  23. data/.gitignore +0 -16
  24. data/.gitmodules +0 -0
  25. data/.rspec +0 -1
  26. data/.rubocop.yml +0 -112
  27. data/.scripts/bump-version.sh +0 -9
  28. data/CONTRIBUTING.md +0 -71
  29. data/sentry-ruby/.gitignore +0 -11
  30. data/sentry-ruby/.rspec +0 -3
  31. data/sentry-ruby/.travis.yml +0 -6
  32. data/sentry-ruby/CODE_OF_CONDUCT.md +0 -74
  33. data/sentry-ruby/Gemfile +0 -9
  34. data/sentry-ruby/LICENSE.txt +0 -21
  35. data/sentry-ruby/README.md +0 -44
  36. data/sentry-ruby/Rakefile +0 -6
  37. data/sentry-ruby/bin/console +0 -14
  38. data/sentry-ruby/bin/setup +0 -8
  39. data/sentry-ruby/examples/rails-6.0/.browserslistrc +0 -1
  40. data/sentry-ruby/examples/rails-6.0/.gitignore +0 -35
  41. data/sentry-ruby/examples/rails-6.0/Gemfile +0 -58
  42. data/sentry-ruby/examples/rails-6.0/README.md +0 -23
  43. data/sentry-ruby/examples/rails-6.0/Rakefile +0 -6
  44. data/sentry-ruby/examples/rails-6.0/app/assets/config/manifest.js +0 -2
  45. data/sentry-ruby/examples/rails-6.0/app/assets/images/.keep +0 -0
  46. data/sentry-ruby/examples/rails-6.0/app/assets/stylesheets/application.css +0 -15
  47. data/sentry-ruby/examples/rails-6.0/app/channels/application_cable/channel.rb +0 -4
  48. data/sentry-ruby/examples/rails-6.0/app/channels/application_cable/connection.rb +0 -4
  49. data/sentry-ruby/examples/rails-6.0/app/controllers/application_controller.rb +0 -2
  50. data/sentry-ruby/examples/rails-6.0/app/controllers/concerns/.keep +0 -0
  51. data/sentry-ruby/examples/rails-6.0/app/controllers/welcome_controller.rb +0 -23
  52. data/sentry-ruby/examples/rails-6.0/app/helpers/application_helper.rb +0 -2
  53. data/sentry-ruby/examples/rails-6.0/app/javascript/channels/consumer.js +0 -6
  54. data/sentry-ruby/examples/rails-6.0/app/javascript/channels/index.js +0 -5
  55. data/sentry-ruby/examples/rails-6.0/app/javascript/packs/application.js +0 -17
  56. data/sentry-ruby/examples/rails-6.0/app/jobs/application_job.rb +0 -7
  57. data/sentry-ruby/examples/rails-6.0/app/mailers/application_mailer.rb +0 -4
  58. data/sentry-ruby/examples/rails-6.0/app/models/application_record.rb +0 -3
  59. data/sentry-ruby/examples/rails-6.0/app/models/concerns/.keep +0 -0
  60. data/sentry-ruby/examples/rails-6.0/app/views/layouts/application.html.erb +0 -15
  61. data/sentry-ruby/examples/rails-6.0/app/views/layouts/mailer.html.erb +0 -13
  62. data/sentry-ruby/examples/rails-6.0/app/views/layouts/mailer.text.erb +0 -1
  63. data/sentry-ruby/examples/rails-6.0/app/views/welcome/report_demo.html.erb +0 -22
  64. data/sentry-ruby/examples/rails-6.0/app/views/welcome/view_error.html.erb +0 -1
  65. data/sentry-ruby/examples/rails-6.0/app/workers/error_worker.rb +0 -7
  66. data/sentry-ruby/examples/rails-6.0/babel.config.js +0 -72
  67. data/sentry-ruby/examples/rails-6.0/bin/bundle +0 -114
  68. data/sentry-ruby/examples/rails-6.0/bin/rails +0 -9
  69. data/sentry-ruby/examples/rails-6.0/bin/rake +0 -9
  70. data/sentry-ruby/examples/rails-6.0/bin/setup +0 -36
  71. data/sentry-ruby/examples/rails-6.0/bin/spring +0 -17
  72. data/sentry-ruby/examples/rails-6.0/bin/webpack +0 -18
  73. data/sentry-ruby/examples/rails-6.0/bin/webpack-dev-server +0 -18
  74. data/sentry-ruby/examples/rails-6.0/bin/yarn +0 -11
  75. data/sentry-ruby/examples/rails-6.0/config.ru +0 -5
  76. data/sentry-ruby/examples/rails-6.0/config/application.rb +0 -28
  77. data/sentry-ruby/examples/rails-6.0/config/boot.rb +0 -4
  78. data/sentry-ruby/examples/rails-6.0/config/cable.yml +0 -10
  79. data/sentry-ruby/examples/rails-6.0/config/credentials.yml.enc +0 -1
  80. data/sentry-ruby/examples/rails-6.0/config/database.yml +0 -25
  81. data/sentry-ruby/examples/rails-6.0/config/environment.rb +0 -5
  82. data/sentry-ruby/examples/rails-6.0/config/environments/development.rb +0 -62
  83. data/sentry-ruby/examples/rails-6.0/config/environments/production.rb +0 -112
  84. data/sentry-ruby/examples/rails-6.0/config/environments/test.rb +0 -48
  85. data/sentry-ruby/examples/rails-6.0/config/initializers/application_controller_renderer.rb +0 -8
  86. data/sentry-ruby/examples/rails-6.0/config/initializers/assets.rb +0 -14
  87. data/sentry-ruby/examples/rails-6.0/config/initializers/backtrace_silencers.rb +0 -7
  88. data/sentry-ruby/examples/rails-6.0/config/initializers/content_security_policy.rb +0 -30
  89. data/sentry-ruby/examples/rails-6.0/config/initializers/cookies_serializer.rb +0 -5
  90. data/sentry-ruby/examples/rails-6.0/config/initializers/filter_parameter_logging.rb +0 -4
  91. data/sentry-ruby/examples/rails-6.0/config/initializers/inflections.rb +0 -16
  92. data/sentry-ruby/examples/rails-6.0/config/initializers/mime_types.rb +0 -4
  93. data/sentry-ruby/examples/rails-6.0/config/initializers/wrap_parameters.rb +0 -14
  94. data/sentry-ruby/examples/rails-6.0/config/locales/en.yml +0 -33
  95. data/sentry-ruby/examples/rails-6.0/config/puma.rb +0 -38
  96. data/sentry-ruby/examples/rails-6.0/config/routes.rb +0 -10
  97. data/sentry-ruby/examples/rails-6.0/config/spring.rb +0 -6
  98. data/sentry-ruby/examples/rails-6.0/config/storage.yml +0 -34
  99. data/sentry-ruby/examples/rails-6.0/config/webpack/development.js +0 -5
  100. data/sentry-ruby/examples/rails-6.0/config/webpack/environment.js +0 -3
  101. data/sentry-ruby/examples/rails-6.0/config/webpack/production.js +0 -5
  102. data/sentry-ruby/examples/rails-6.0/config/webpack/test.js +0 -5
  103. data/sentry-ruby/examples/rails-6.0/config/webpacker.yml +0 -96
  104. data/sentry-ruby/examples/rails-6.0/db/seeds.rb +0 -7
  105. data/sentry-ruby/examples/rails-6.0/lib/assets/.keep +0 -0
  106. data/sentry-ruby/examples/rails-6.0/lib/tasks/.keep +0 -0
  107. data/sentry-ruby/examples/rails-6.0/package.json +0 -15
  108. data/sentry-ruby/examples/rails-6.0/postcss.config.js +0 -12
  109. data/sentry-ruby/examples/rails-6.0/public/404.html +0 -67
  110. data/sentry-ruby/examples/rails-6.0/public/422.html +0 -67
  111. data/sentry-ruby/examples/rails-6.0/public/500.html +0 -66
  112. data/sentry-ruby/examples/rails-6.0/public/apple-touch-icon-precomposed.png +0 -0
  113. data/sentry-ruby/examples/rails-6.0/public/apple-touch-icon.png +0 -0
  114. data/sentry-ruby/examples/rails-6.0/public/favicon.ico +0 -0
  115. data/sentry-ruby/examples/rails-6.0/public/robots.txt +0 -1
  116. data/sentry-ruby/examples/rails-6.0/storage/.keep +0 -0
  117. data/sentry-ruby/examples/rails-6.0/test/application_system_test_case.rb +0 -5
  118. data/sentry-ruby/examples/rails-6.0/test/channels/application_cable/connection_test.rb +0 -11
  119. data/sentry-ruby/examples/rails-6.0/test/controllers/.keep +0 -0
  120. data/sentry-ruby/examples/rails-6.0/test/fixtures/.keep +0 -0
  121. data/sentry-ruby/examples/rails-6.0/test/fixtures/files/.keep +0 -0
  122. data/sentry-ruby/examples/rails-6.0/test/helpers/.keep +0 -0
  123. data/sentry-ruby/examples/rails-6.0/test/integration/.keep +0 -0
  124. data/sentry-ruby/examples/rails-6.0/test/mailers/.keep +0 -0
  125. data/sentry-ruby/examples/rails-6.0/test/models/.keep +0 -0
  126. data/sentry-ruby/examples/rails-6.0/test/system/.keep +0 -0
  127. data/sentry-ruby/examples/rails-6.0/test/test_helper.rb +0 -13
  128. data/sentry-ruby/examples/rails-6.0/vendor/.keep +0 -0
  129. data/sentry-ruby/examples/rails-6.0/yarn.lock +0 -7508
  130. data/sentry-ruby/lib/sentry.rb +0 -16
  131. data/sentry-ruby/lib/sentry/backtrace.rb +0 -128
  132. data/sentry-ruby/lib/sentry/client.rb +0 -162
  133. data/sentry-ruby/lib/sentry/client/state.rb +0 -40
  134. data/sentry-ruby/lib/sentry/configuration.rb +0 -533
  135. data/sentry-ruby/lib/sentry/event.rb +0 -209
  136. data/sentry-ruby/lib/sentry/interface.rb +0 -31
  137. data/sentry-ruby/lib/sentry/interfaces/exception.rb +0 -15
  138. data/sentry-ruby/lib/sentry/interfaces/http.rb +0 -16
  139. data/sentry-ruby/lib/sentry/interfaces/message.rb +0 -18
  140. data/sentry-ruby/lib/sentry/interfaces/single_exception.rb +0 -14
  141. data/sentry-ruby/lib/sentry/interfaces/stack_trace.rb +0 -69
  142. data/sentry-ruby/lib/sentry/linecache.rb +0 -44
  143. data/sentry-ruby/lib/sentry/logger.rb +0 -20
  144. data/sentry-ruby/lib/sentry/transports.rb +0 -19
  145. data/sentry-ruby/lib/sentry/transports/dummy.rb +0 -16
  146. data/sentry-ruby/lib/sentry/transports/http.rb +0 -66
  147. data/sentry-ruby/lib/sentry/transports/stdout.rb +0 -20
  148. data/sentry-ruby/lib/sentry/utils/deep_merge.rb +0 -22
  149. data/sentry-ruby/lib/sentry/utils/exception_cause_chain.rb +0 -20
  150. data/sentry-ruby/lib/sentry/version.rb +0 -3
  151. data/sentry-ruby/sentry-ruby.gemspec +0 -26
  152. data/sentry-ruby/spec/sentry/backtrace_spec.rb +0 -38
  153. data/sentry-ruby/spec/sentry/client_spec.rb +0 -443
  154. data/sentry-ruby/spec/sentry/configuration_spec.rb +0 -400
  155. data/sentry-ruby/spec/sentry/event_spec.rb +0 -238
  156. data/sentry-ruby/spec/sentry/interface_spec.rb +0 -38
  157. data/sentry-ruby/spec/sentry/interfaces/stack_trace_spec.rb +0 -11
  158. data/sentry-ruby/spec/sentry/linecache_spec.rb +0 -40
  159. data/sentry-ruby/spec/sentry/transports/http_spec.rb +0 -57
  160. data/sentry-ruby/spec/sentry/transports/stdout_spec.rb +0 -11
  161. data/sentry-ruby/spec/sentry_spec.rb +0 -9
  162. data/sentry-ruby/spec/spec_helper.rb +0 -49
  163. data/sentry-ruby/spec/support/linecache.txt +0 -6
@@ -1,19 +0,0 @@
1
- module Sentry
2
- module Transports
3
- class Transport
4
- attr_accessor :configuration
5
-
6
- def initialize(configuration)
7
- @configuration = configuration
8
- end
9
-
10
- def send_event # (auth_header, data, options = {})
11
- raise NotImplementedError, 'Abstract method not implemented'
12
- end
13
- end
14
- end
15
- end
16
-
17
- require "sentry/transports/dummy"
18
- require "sentry/transports/http"
19
- require "sentry/transports/stdout"
@@ -1,16 +0,0 @@
1
- module Sentry
2
- module Transports
3
- class Dummy < Transport
4
- attr_accessor :events
5
-
6
- def initialize(*)
7
- super
8
- @events = []
9
- end
10
-
11
- def send_event(auth_header, data, options = {})
12
- @events << [auth_header, data, options]
13
- end
14
- end
15
- end
16
- end
@@ -1,66 +0,0 @@
1
- require 'faraday'
2
-
3
- module Sentry
4
- module Transports
5
- class HTTP < Transport
6
- attr_accessor :conn, :adapter
7
-
8
- def initialize(*args)
9
- super
10
- self.adapter = configuration.http_adapter || Faraday.default_adapter
11
- self.conn = set_conn
12
- end
13
-
14
- def send_event(auth_header, data, options = {})
15
- unless configuration.sending_allowed?
16
- logger.debug("Event not sent: #{configuration.error_messages}")
17
- end
18
-
19
- project_id = configuration[:project_id]
20
- path = configuration[:path] + "/"
21
-
22
- conn.post "#{path}api/#{project_id}/store/" do |req|
23
- req.headers['Content-Type'] = options[:content_type]
24
- req.headers['X-Sentry-Auth'] = auth_header
25
- req.body = data
26
- end
27
- rescue Faraday::Error => e
28
- error_info = e.message
29
- if e.response && e.response[:headers]['x-sentry-error']
30
- error_info += " Error in headers is: #{e.response[:headers]['x-sentry-error']}"
31
- end
32
- raise Sentry::Error, error_info
33
- end
34
-
35
- private
36
-
37
- def set_conn
38
- configuration.logger.debug "Sentry HTTP Transport connecting to #{configuration.server}"
39
-
40
- proxy = configuration.public_send(:proxy)
41
-
42
- Faraday.new(configuration.server, :ssl => ssl_configuration, :proxy => proxy) do |builder|
43
- configuration.faraday_builder&.call(builder)
44
- builder.response :raise_error
45
- builder.options.merge! faraday_opts
46
- builder.headers[:user_agent] = "sentry-ruby/#{Sentry::VERSION}"
47
- builder.adapter(*adapter)
48
- end
49
- end
50
-
51
- # TODO: deprecate and replace where possible w/Faraday Builder
52
- def faraday_opts
53
- [:timeout, :open_timeout].each_with_object({}) do |opt, memo|
54
- memo[opt] = configuration.public_send(opt) if configuration.public_send(opt)
55
- end
56
- end
57
-
58
- def ssl_configuration
59
- (configuration.ssl || {}).merge(
60
- :verify => configuration.ssl_verification,
61
- :ca_file => configuration.ssl_ca_file
62
- )
63
- end
64
- end
65
- end
66
- end
@@ -1,20 +0,0 @@
1
- module Sentry
2
- module Transports
3
- class Stdout < Transport
4
- attr_accessor :events
5
-
6
- def initialize(*)
7
- super
8
- end
9
-
10
- def send_event(_auth_header, data, _options = {})
11
- unless configuration.sending_allowed?
12
- logger.debug("Event not sent: #{configuration.error_messages}")
13
- end
14
-
15
- $stdout.puts data
16
- $stdout.flush
17
- end
18
- end
19
- end
20
- end
@@ -1,22 +0,0 @@
1
- module Sentry
2
- module Utils
3
- # ported from ActiveSupport
4
- module DeepMergeHash
5
- def self.deep_merge(hash, other_hash, &block)
6
- deep_merge!(hash, other_hash, &block)
7
- end
8
-
9
- def self.deep_merge!(hash, other_hash, &block)
10
- hash.merge!(other_hash) do |key, this_val, other_val|
11
- if this_val.is_a?(Hash) && other_val.is_a?(Hash)
12
- deep_merge(this_val, other_val, &block)
13
- elsif block_given?
14
- block.call(key, this_val, other_val)
15
- else
16
- other_val
17
- end
18
- end
19
- end
20
- end
21
- end
22
- end
@@ -1,20 +0,0 @@
1
- module Sentry
2
- module Utils
3
- module ExceptionCauseChain
4
- def self.exception_to_array(exception)
5
- if exception.respond_to?(:cause) && exception.cause
6
- exceptions = [exception]
7
- while exception.cause
8
- exception = exception.cause
9
- break if exceptions.any? { |e| e.object_id == exception.object_id }
10
-
11
- exceptions << exception
12
- end
13
- exceptions
14
- else
15
- [exception]
16
- end
17
- end
18
- end
19
- end
20
- end
@@ -1,3 +0,0 @@
1
- module Sentry
2
- VERSION = "0.1.0"
3
- end
@@ -1,26 +0,0 @@
1
- require_relative 'lib/sentry/version'
2
-
3
- Gem::Specification.new do |spec|
4
- spec.name = "sentry-ruby"
5
- spec.version = Sentry::VERSION
6
- spec.authors = ["Sentry Team"]
7
- spec.description = spec.summary = "A gem that provides a client interface for the Sentry error logger"
8
- spec.email = "accounts@sentry.io"
9
- spec.license = 'Apache-2.0'
10
- spec.homepage = "https://github.com/getsentry/raven-ruby"
11
-
12
- spec.platform = Gem::Platform::RUBY
13
- spec.required_ruby_version = '>= 2.4'
14
- spec.extra_rdoc_files = ["README.md", "LICENSE"]
15
- spec.files = `git ls-files | grep -Ev '^(spec|benchmarks|examples)'`.split("\n")
16
-
17
- spec.metadata["homepage_uri"] = spec.homepage
18
- spec.metadata["source_code_uri"] = spec.homepage
19
- spec.metadata["changelog_uri"] = "#{spec.homepage}/blob/master/CHANGELOG.md"
20
-
21
- spec.bindir = "exe"
22
- spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
23
- spec.require_paths = ["lib"]
24
-
25
- spec.add_dependency "faraday", ">= 1.0"
26
- end
@@ -1,38 +0,0 @@
1
- require 'spec_helper'
2
-
3
- RSpec.describe Sentry::Backtrace do
4
- let(:configuration) { Sentry::Configuration.new }
5
-
6
- before(:each) do
7
- @backtrace = Sentry::Backtrace.parse(Thread.current.backtrace, configuration: configuration)
8
- end
9
-
10
- it "calls backtrace_cleanup_callback if it's present in the configuration" do
11
- called = false
12
- callback = proc do |backtrace|
13
- called = true
14
- backtrace
15
- end
16
- configuration.backtrace_cleanup_callback = callback
17
- Sentry::Backtrace.parse(Thread.current.backtrace, configuration: configuration)
18
-
19
- expect(called).to eq(true)
20
- end
21
-
22
- it "#lines" do
23
- expect(@backtrace.lines.first).to be_a(Sentry::Backtrace::Line)
24
- end
25
-
26
- it "#inspect" do
27
- expect(@backtrace.inspect).to match(/Backtrace: .*>$/)
28
- end
29
-
30
- it "#to_s" do
31
- expect(@backtrace.to_s).to match(/backtrace_spec.rb:\d/)
32
- end
33
-
34
- it "==" do
35
- @backtrace2 = Sentry::Backtrace.new(@backtrace.lines)
36
- expect(@backtrace).to be == @backtrace2
37
- end
38
- end
@@ -1,443 +0,0 @@
1
- require 'spec_helper'
2
-
3
- class ExceptionWithContext < StandardError
4
- def sentry_context
5
- { extra: {
6
- 'context_event_key' => 'context_value',
7
- 'context_key' => 'context_value'
8
- } }
9
- end
10
- end
11
-
12
- RSpec.describe Sentry::Client do
13
- let(:configuration) do
14
- Sentry::Configuration.new.tap do |config|
15
- config.server = 'http://12345:67890@sentry.localdomain/sentry/42'
16
- end
17
- end
18
- let(:fake_time) { Time.now }
19
-
20
- subject { Sentry::Client.new(configuration) }
21
-
22
- before do
23
- allow(Time).to receive(:now).and_return fake_time
24
- end
25
-
26
- describe "#generate_auth_header" do
27
- it "generates an auth header" do
28
- expect(subject.send(:generate_auth_header)).to eq(
29
- "Sentry sentry_version=5, sentry_client=sentry-ruby/#{Sentry::VERSION}, sentry_timestamp=#{fake_time.to_i}, " \
30
- "sentry_key=12345, sentry_secret=67890"
31
- )
32
- end
33
-
34
- it "generates an auth header without a secret (Sentry 9)" do
35
- configuration.server = "https://66260460f09b5940498e24bb7ce093a0@sentry.io/42"
36
-
37
- expect(subject.send(:generate_auth_header)).to eq(
38
- "Sentry sentry_version=5, sentry_client=sentry-ruby/#{Sentry::VERSION}, sentry_timestamp=#{fake_time.to_i}, " \
39
- "sentry_key=66260460f09b5940498e24bb7ce093a0"
40
- )
41
- end
42
- end
43
-
44
- describe "#send_event" do
45
- let(:event) { subject.event_from_exception(ZeroDivisionError.new("divided by 0")) }
46
-
47
- context "when success" do
48
- before do
49
- allow(subject.transport).to receive(:send_event)
50
- end
51
-
52
- it "sends Event object" do
53
- expect(subject).not_to receive(:failed_send)
54
-
55
- expect(subject.send_event(event)).to eq(event.to_hash)
56
- end
57
-
58
- it "sends Event hash" do
59
- expect(subject).not_to receive(:failed_send)
60
-
61
- expect(subject.send_event(event.to_json_compatible)).to eq(event.to_json_compatible)
62
- end
63
- end
64
-
65
- context "when failed" do
66
- let(:logger) { spy }
67
-
68
- before do
69
- configuration.logger = logger
70
- allow(subject.transport).to receive(:send_event).and_raise(StandardError)
71
-
72
- expect(logger).to receive(:warn).exactly(2)
73
- end
74
-
75
- it "sends Event object" do
76
- expect(subject.send_event(event)).to eq(nil)
77
- end
78
-
79
- it "sends Event hash" do
80
- expect(subject.send_event(event.to_json_compatible)).to eq(nil)
81
- end
82
- end
83
- end
84
-
85
- describe "#transport" do
86
- context "when scheme is not set" do
87
- it "returns HTTP transport object" do
88
- expect(subject.transport).to be_a(Sentry::Transports::HTTP)
89
- end
90
- end
91
-
92
- context "when scheme is http" do
93
- before do
94
- configuration.scheme = "http"
95
- end
96
-
97
- it "returns HTTP transport object" do
98
- expect(subject.transport).to be_a(Sentry::Transports::HTTP)
99
- end
100
- end
101
-
102
- context "when scheme is https" do
103
- before do
104
- configuration.scheme = "https"
105
- end
106
-
107
- it "returns HTTP transport object" do
108
- expect(subject.transport).to be_a(Sentry::Transports::HTTP)
109
- end
110
- end
111
-
112
- context "when scheme is dummy" do
113
- before do
114
- configuration.scheme = "dummy"
115
- end
116
-
117
- it "returns Dummy transport object" do
118
- expect(subject.transport).to be_a(Sentry::Transports::Dummy)
119
- end
120
- end
121
-
122
- context "when scheme is stdout" do
123
- before do
124
- configuration.scheme = "stdout"
125
- end
126
-
127
- it "returns Stdout transport object" do
128
- expect(subject.transport).to be_a(Sentry::Transports::Stdout)
129
- end
130
- end
131
- end
132
-
133
- shared_examples "options" do
134
- let(:options) do
135
- {
136
- checksum: 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa',
137
- release: '1.0',
138
- fingerprint: ['{{ default }}', 'foo'],
139
- backtrace: ["/path/to/some/file:22:in `function_name'", "/some/other/path:1412:in `other_function'"]
140
- }
141
- end
142
-
143
- let(:event) do
144
- subject.event_from_exception(Exception.new, **options)
145
- end
146
-
147
- it 'takes and sets all available options' do
148
- expect(event.checksum).to eq('aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa')
149
- expect(event.release).to eq('1.0')
150
- expect(event.fingerprint).to eq(['{{ default }}', 'foo'])
151
- end
152
-
153
- it "contains given backtrace" do
154
- expect(event[:stacktrace]).to be_a(Sentry::StacktraceInterface)
155
-
156
- frames = event[:stacktrace].to_hash[:frames]
157
- expect(frames.length).to eq(2)
158
- expect(frames[0][:lineno]).to eq(1412)
159
- expect(frames[0][:function]).to eq('other_function')
160
- expect(frames[0][:filename]).to eq('/some/other/path')
161
-
162
- expect(frames[1][:lineno]).to eq(22)
163
- expect(frames[1][:function]).to eq('function_name')
164
- expect(frames[1][:filename]).to eq('/path/to/some/file')
165
- end
166
- end
167
-
168
- describe '#event_from_message' do
169
- let(:message) { 'This is a message' }
170
-
171
- it 'returns an event' do
172
- event = subject.event_from_message(message)
173
- hash = event.to_hash
174
-
175
- expect(event).to be_a(Sentry::Event)
176
- expect(hash[:message]).to eq(message)
177
- expect(hash[:level]).to eq(:error)
178
- end
179
-
180
- it "doesn't change the option hash" do
181
- h_int = { abc: :abc }
182
- h = { k1: h_int, k2: h_int }
183
- subject.event_from_message "Test extra", extra: { h1: h, h2: h_int }
184
-
185
- expect(h).to eq({ k1: h_int, k2: h_int })
186
- end
187
-
188
- it_behaves_like "options"
189
- end
190
-
191
- describe "#event_from_exception" do
192
- let(:message) { 'This is a message' }
193
- let(:exception) { Exception.new(message) }
194
- let(:event) { subject.event_from_exception(exception) }
195
- let(:hash) { event.to_hash }
196
-
197
- before do
198
- configuration.scheme = "dummy"
199
- end
200
-
201
- it "sets the message to the exception's value and type" do
202
- expect(hash[:exception][:values][0][:type]).to eq("Exception")
203
- expect(hash[:exception][:values][0][:value]).to eq(message)
204
- end
205
-
206
- it 'has level ERROR' do
207
- expect(hash[:level]).to eq(:error)
208
- end
209
-
210
- it 'does not belong to a module' do
211
- expect(hash[:exception][:values][0][:module]).to eq('')
212
- end
213
-
214
- it 'returns an event' do
215
- event = subject.event_from_exception(ZeroDivisionError.new("divided by 0"))
216
- expect(event).to be_a(Sentry::Event)
217
- expect(subject.send(:get_message_from_exception, event.to_hash)).to eq("ZeroDivisionError: divided by 0")
218
- end
219
-
220
- it_behaves_like "options"
221
-
222
- describe "options - message" do
223
- it "proceses string message correctly" do
224
- event = subject.event_from_exception(ExceptionWithContext.new, message: "MSG")
225
- expect(event.message).to eq("MSG")
226
- end
227
-
228
- it "slices long string message" do
229
- event = subject.event_from_exception(ExceptionWithContext.new, message: "MSG" * 3000)
230
- expect(event.message.length).to eq(8192)
231
- end
232
-
233
- it "converts non-string message into string" do
234
- expect(configuration.logger).to receive(:debug).with("You're passing a non-string message")
235
-
236
- event = subject.event_from_exception(ExceptionWithContext.new, message: { foo: "bar" })
237
- expect(event.message).to eq("{:foo=>\"bar\"}")
238
- end
239
- end
240
-
241
- context 'for a nested exception type' do
242
- module Sentry::Test
243
- class Exception < RuntimeError; end
244
- end
245
- let(:exception) { Sentry::Test::Exception.new(message) }
246
-
247
- it 'sends the module name as part of the exception info' do
248
- expect(hash[:exception][:values][0][:module]).to eq('Sentry::Test')
249
- end
250
- end
251
-
252
- describe "exception types test" do
253
- context 'for a Sentry::Error' do
254
- let(:exception) { Sentry::Error.new }
255
- it 'does not create an event' do
256
- expect(subject.event_from_exception(exception)).to be_nil
257
- end
258
- end
259
-
260
- context 'for an excluded exception type' do
261
- module Sentry::Test
262
- class BaseExc < RuntimeError; end
263
- class SubExc < BaseExc; end
264
- module ExcTag; end
265
- end
266
-
267
- let(:config) { subject.configuration }
268
-
269
- context "invalid exclusion type" do
270
- it 'returns Sentry::Event' do
271
- config.excluded_exceptions << nil
272
- config.excluded_exceptions << 1
273
- config.excluded_exceptions << {}
274
- expect(subject.event_from_exception(Sentry::Test::BaseExc.new)).to be_a(Sentry::Event)
275
- end
276
- end
277
-
278
- context "defined by string type" do
279
- it 'returns nil for a class match' do
280
- config.excluded_exceptions << 'Sentry::Test::BaseExc'
281
- expect(subject.event_from_exception(Sentry::Test::BaseExc.new)).to be_nil
282
- end
283
-
284
- it 'returns nil for a top class match' do
285
- config.excluded_exceptions << '::Sentry::Test::BaseExc'
286
- expect(subject.event_from_exception(Sentry::Test::BaseExc.new)).to be_nil
287
- end
288
-
289
- it 'returns nil for a sub class match' do
290
- config.excluded_exceptions << 'Sentry::Test::BaseExc'
291
- expect(subject.event_from_exception(Sentry::Test::SubExc.new)).to be_nil
292
- end
293
-
294
- it 'returns nil for a tagged class match' do
295
- config.excluded_exceptions << 'Sentry::Test::ExcTag'
296
- expect(
297
- subject.event_from_exception(Sentry::Test::SubExc.new.tap { |x| x.extend(Sentry::Test::ExcTag) })
298
- ).to be_nil
299
- end
300
-
301
- it 'returns Sentry::Event for an undefined exception class' do
302
- config.excluded_exceptions << 'Sentry::Test::NonExistentExc'
303
- expect(subject.event_from_exception(Sentry::Test::BaseExc.new)).to be_a(Sentry::Event)
304
- end
305
- end
306
-
307
- context "defined by class type" do
308
- it 'returns nil for a class match' do
309
- config.excluded_exceptions << Sentry::Test::BaseExc
310
- expect(subject.event_from_exception(Sentry::Test::BaseExc.new)).to be_nil
311
- end
312
-
313
- it 'returns nil for a sub class match' do
314
- config.excluded_exceptions << Sentry::Test::BaseExc
315
- expect(subject.event_from_exception(Sentry::Test::SubExc.new)).to be_nil
316
- end
317
-
318
- it 'returns nil for a tagged class match' do
319
- config.excluded_exceptions << Sentry::Test::ExcTag
320
- expect(subject.event_from_exception(Sentry::Test::SubExc.new.tap { |x| x.extend(Sentry::Test::ExcTag) })).to be_nil
321
- end
322
- end
323
- end
324
-
325
- # Only check causes when they're supported
326
- if Exception.new.respond_to? :cause
327
- context 'when the exception has a cause' do
328
- let(:exception) { build_exception_with_cause }
329
-
330
- it 'captures the cause' do
331
- expect(hash[:exception][:values].length).to eq(2)
332
- end
333
- end
334
-
335
- context 'when the exception has nested causes' do
336
- let(:exception) { build_exception_with_two_causes }
337
-
338
- it 'captures nested causes' do
339
- expect(hash[:exception][:values].length).to eq(3)
340
- end
341
- end
342
- end
343
-
344
- context 'when the exception has a recursive cause' do
345
- let(:exception) { build_exception_with_recursive_cause }
346
-
347
- it 'should handle it gracefully' do
348
- expect(hash[:exception][:values].length).to eq(1)
349
- end
350
- end
351
-
352
- if RUBY_PLATFORM == "java"
353
- context 'when running under jRuby' do
354
- let(:exception) do
355
- begin
356
- raise java.lang.OutOfMemoryError, "A Java error"
357
- rescue Exception => e
358
- return e
359
- end
360
- end
361
-
362
- it 'should have a backtrace' do
363
- frames = hash[:exception][:values][0][:stacktrace][:frames]
364
- expect(frames.length).not_to eq(0)
365
- end
366
- end
367
- end
368
-
369
- context 'when the exception has a backtrace' do
370
- let(:exception) do
371
- e = Exception.new(message)
372
- allow(e).to receive(:backtrace).and_return [
373
- "/path/to/some/file:22:in `function_name'",
374
- "/some/other/path:1412:in `other_function'"
375
- ]
376
- e
377
- end
378
-
379
- it 'parses the backtrace' do
380
- frames = hash[:exception][:values][0][:stacktrace][:frames]
381
- expect(frames.length).to eq(2)
382
- expect(frames[0][:lineno]).to eq(1412)
383
- expect(frames[0][:function]).to eq('other_function')
384
- expect(frames[0][:filename]).to eq('/some/other/path')
385
-
386
- expect(frames[1][:lineno]).to eq(22)
387
- expect(frames[1][:function]).to eq('function_name')
388
- expect(frames[1][:filename]).to eq('/path/to/some/file')
389
- end
390
-
391
- context 'with internal backtrace' do
392
- let(:exception) do
393
- e = Exception.new(message)
394
- allow(e).to receive(:backtrace).and_return(["<internal:prelude>:10:in `synchronize'"])
395
- e
396
- end
397
-
398
- it 'marks filename and in_app correctly' do
399
- frames = hash[:exception][:values][0][:stacktrace][:frames]
400
- expect(frames[0][:lineno]).to eq(10)
401
- expect(frames[0][:function]).to eq("synchronize")
402
- expect(frames[0][:filename]).to eq("<internal:prelude>")
403
- end
404
- end
405
-
406
- context 'when a path in the stack trace is on the load path' do
407
- before do
408
- $LOAD_PATH << '/some'
409
- end
410
-
411
- after do
412
- $LOAD_PATH.delete('/some')
413
- end
414
-
415
- it 'strips prefixes in the load path from frame filenames' do
416
- frames = hash[:exception][:values][0][:stacktrace][:frames]
417
- expect(frames[0][:filename]).to eq('other/path')
418
- end
419
- end
420
- end
421
-
422
- context 'merging exception context' do
423
- let(:hash) do
424
- event = subject.event_from_exception(
425
- ExceptionWithContext.new,
426
- message: "MSG",
427
- extra: {
428
- 'context_event_key' => 'event_value',
429
- 'event_key' => 'event_value'
430
- }
431
- )
432
- event.to_hash
433
- end
434
-
435
- it 'prioritizes event context over request context' do
436
- expect(hash[:extra]['context_event_key']).to eq('event_value')
437
- expect(hash[:extra]['context_key']).to eq('context_value')
438
- expect(hash[:extra]['event_key']).to eq('event_value')
439
- end
440
- end
441
- end
442
- end
443
- end