bugsnag 6.13.0 → 6.13.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 2298a07774ef42fb825c7ae6aa9722c9da1234617789236a442cd0d888a4e486
4
- data.tar.gz: f4882c3be40fe0e4d6582ec24e00751257ab5f5926866c0317a7d6d0ae3aa129
3
+ metadata.gz: 25dcf74c356f7025c163ad055ddb01ecb27b46ddf31b746f87b8753d9c1899ca
4
+ data.tar.gz: fab1845fb7b1165caa97a88561bdc49230603e7d8d9e218a55c0cf52af2da640
5
5
  SHA512:
6
- metadata.gz: 129a9b9cf9411234935f4d49be119596e55475d31ff68e943e978f14ca95d17f2418c37fffa6190f25b03301fd408d5c0d4719c11807934982d3cd6f4d1c52ff
7
- data.tar.gz: 6dae71c25d20bb071104e07608e51b33e4ab2deaaa0a7bf2bab06694f850d20823d2afde37c1edebd105b8e190b0d22baf61da8d16925b84f3fb5ec757cf6cbf
6
+ metadata.gz: d103cd0a9df8e2d02fd98a10f9b24ef706dc93c8266f148d480076c1ee2d2d06114de0c60983ca5c3275804271c9f664cdc64ddffdbc19fda1f787afb6d49e24
7
+ data.tar.gz: 6d85db5571b16d3de7c23baf7c932536c08fdd9261557bbb2f59e4436981caf02177fb5b91fb7cb4adbbc62d5c6f42f610128890f7414eda85aa1e1c21248ba2
@@ -1,6 +1,16 @@
1
1
  Changelog
2
2
  =========
3
3
 
4
+ ## 6.13.1 (11 May 2020)
5
+
6
+ ### Fixes
7
+
8
+ * Only call custom diagnostic data methods once
9
+ | [#586](https://github.com/bugsnag/bugsnag-ruby/pull/586)
10
+ | [stoivo](https://github.com/stoivo)
11
+ * Guard against exceptions in to_s when cleaning objects
12
+ | [#591](https://github.com/bugsnag/bugsnag-ruby/pull/591)
13
+
4
14
  ## 6.13.0 (30 Jan 2020)
5
15
 
6
16
  ### Enhancements
data/VERSION CHANGED
@@ -1 +1 @@
1
- 6.13.0
1
+ 6.13.1
@@ -29,10 +29,19 @@ module Bugsnag
29
29
  when Hash
30
30
  clean_hash = {}
31
31
  obj.each do |k,v|
32
- if filters_match_deeply?(k, scope)
33
- clean_hash[k] = FILTERED
34
- else
35
- clean_hash[k] = traverse_object(v, seen, [scope, k].compact.join('.'))
32
+ begin
33
+ if filters_match_deeply?(k, scope)
34
+ clean_hash[k] = FILTERED
35
+ else
36
+ clean_hash[k] = traverse_object(v, seen, [scope, k].compact.join('.'))
37
+ end
38
+ # If we get an error here, we assume the key needs to be filtered
39
+ # to avoid leaking things we shouldn't. We also remove the key itself
40
+ # because it may cause issues later e.g. when being converted to JSON
41
+ rescue StandardError
42
+ clean_hash[RAISED] = FILTERED
43
+ rescue SystemStackError
44
+ clean_hash[RECURSION] = FILTERED
36
45
  end
37
46
  end
38
47
  clean_hash
@@ -43,7 +52,15 @@ module Bugsnag
43
52
  when String
44
53
  clean_string(obj)
45
54
  else
46
- str = obj.to_s rescue RAISED
55
+ # guard against objects that raise or blow the stack when stringified
56
+ begin
57
+ str = obj.to_s
58
+ rescue StandardError
59
+ str = RAISED
60
+ rescue SystemStackError
61
+ str = RECURSION
62
+ end
63
+
47
64
  # avoid leaking potentially sensitive data from objects' #inspect output
48
65
  if str =~ /#<.*>/
49
66
  OBJECT
@@ -9,21 +9,27 @@ module Bugsnag::Middleware
9
9
  def call(report)
10
10
  # Apply the user's information attached to the exceptions
11
11
  report.raw_exceptions.each do |exception|
12
- if exception.respond_to?(:bugsnag_user_id) && exception.bugsnag_user_id.is_a?(String)
13
- report.user = {id: exception.bugsnag_user_id}
12
+ if exception.respond_to?(:bugsnag_user_id)
13
+ user_id = exception.bugsnag_user_id
14
+ report.user = {id: user_id} if user_id.is_a?(String)
14
15
  end
15
16
 
16
- if exception.respond_to?(:bugsnag_context) && exception.bugsnag_context.is_a?(String)
17
- report.context = exception.bugsnag_context
17
+ if exception.respond_to?(:bugsnag_context)
18
+ context = exception.bugsnag_context
19
+ report.context = context if context.is_a?(String)
18
20
  end
19
21
 
20
- if exception.respond_to?(:bugsnag_grouping_hash) && exception.bugsnag_grouping_hash.is_a?(String)
21
- report.grouping_hash = exception.bugsnag_grouping_hash
22
+ if exception.respond_to?(:bugsnag_grouping_hash)
23
+ group_hash = exception.bugsnag_grouping_hash
24
+ report.grouping_hash = group_hash if group_hash.is_a?(String)
22
25
  end
23
26
 
24
- if exception.respond_to?(:bugsnag_meta_data) && exception.bugsnag_meta_data.is_a?(Hash)
25
- exception.bugsnag_meta_data.each do |key, value|
26
- report.add_tab key, value
27
+ if exception.respond_to?(:bugsnag_meta_data)
28
+ meta_data = exception.bugsnag_meta_data
29
+ if meta_data.is_a?(Hash)
30
+ meta_data.each do |key, value|
31
+ report.add_tab key, value
32
+ end
27
33
  end
28
34
  end
29
35
  end
@@ -6,12 +6,84 @@ describe Bugsnag::Cleaner do
6
6
  subject { described_class.new(nil) }
7
7
 
8
8
  describe "#clean_object" do
9
+ is_jruby = defined?(RUBY_ENGINE) && RUBY_ENGINE == 'jruby'
10
+
9
11
  it "cleans up recursive hashes" do
10
12
  a = {:a => {}}
11
13
  a[:a][:b] = a
12
14
  expect(subject.clean_object(a)).to eq({:a => {:b => "[RECURSION]"}})
13
15
  end
14
16
 
17
+ it "cleans up hashes when keys infinitely recurse in to_s" do
18
+ skip "JRuby doesn't allow recovery from SystemStackErrors" if is_jruby
19
+
20
+ class RecursiveHashKey
21
+ def to_s
22
+ to_s
23
+ end
24
+ end
25
+
26
+ key = RecursiveHashKey.new
27
+
28
+ a = {}
29
+ a[key] = 1
30
+
31
+ expect(subject.clean_object(a)).to eq({ "[RECURSION]" => "[FILTERED]" })
32
+ end
33
+
34
+ it "cleans up hashes when a nested key infinitely recurse in to_s" do
35
+ skip "JRuby doesn't allow recovery from SystemStackErrors" if is_jruby
36
+
37
+ class RecursiveHashKey
38
+ def to_s
39
+ to_s
40
+ end
41
+ end
42
+
43
+ key = RecursiveHashKey.new
44
+
45
+ a = {}
46
+ a[:b] = {}
47
+ a[:b][key] = 1
48
+
49
+ expected = { :b => { "[RECURSION]" => "[FILTERED]" } }
50
+
51
+ expect(subject.clean_object(a)).to eq(expected)
52
+ end
53
+
54
+ it "cleans up hashes when keys raise in to_s" do
55
+ class RaisingHashKey
56
+ def to_s
57
+ raise "hey!"
58
+ end
59
+ end
60
+
61
+ key = RaisingHashKey.new
62
+
63
+ a = {}
64
+ a[key] = 1
65
+
66
+ expect(subject.clean_object(a)).to eq({ "[RAISED]" => "[FILTERED]" })
67
+ end
68
+
69
+ it "cleans up hashes when nested keys raise in to_s" do
70
+ class RaisingHashKey
71
+ def to_s
72
+ raise "hey!"
73
+ end
74
+ end
75
+
76
+ key = RaisingHashKey.new
77
+
78
+ a = {}
79
+ a[:b] = {}
80
+ a[:b][key] = 1
81
+
82
+ expected = { :b => { "[RAISED]" => "[FILTERED]" } }
83
+
84
+ expect(subject.clean_object(a)).to eq(expected)
85
+ end
86
+
15
87
  it "cleans up recursive arrays" do
16
88
  a = []
17
89
  a << a
@@ -48,6 +120,20 @@ describe Bugsnag::Cleaner do
48
120
  expect(subject.clean_object(a)).to eq('[OBJECT]')
49
121
  end
50
122
 
123
+ it "cleans custom objects when they infinitely recurse" do
124
+ skip "JRuby doesn't allow recovery from SystemStackErrors" if is_jruby
125
+
126
+ class RecursiveObject
127
+ def to_s
128
+ to_s
129
+ end
130
+ end
131
+
132
+ object = RecursiveObject.new
133
+
134
+ expect(subject.clean_object(object)).to eq("[RECURSION]")
135
+ end
136
+
51
137
  it "cleans up binary strings properly" do
52
138
  if RUBY_VERSION > "1.9"
53
139
  obj = "Andr\xc7\xff"
@@ -50,6 +50,61 @@ describe Bugsnag::Helpers do
50
50
  value = Bugsnag::Helpers.trim_if_needed([1, 3, StringRaiser.new])
51
51
  expect(value[2]).to eq "[RAISED]"
52
52
  end
53
+
54
+ it "replaces hash key with '[RAISED]'" do
55
+ a = {}
56
+ a[StringRaiser.new] = 1
57
+
58
+ value = Bugsnag::Helpers.trim_if_needed(a)
59
+ expect(value).to eq({ "[RAISED]" => "[FILTERED]" })
60
+ end
61
+
62
+ it "uses a single '[RAISED]'key when multiple keys raise" do
63
+ a = {}
64
+ a[StringRaiser.new] = 1
65
+ a[StringRaiser.new] = 2
66
+
67
+ value = Bugsnag::Helpers.trim_if_needed(a)
68
+ expect(value).to eq({ "[RAISED]" => "[FILTERED]" })
69
+ end
70
+ end
71
+
72
+ context "an object will infinitely recurse if `to_s` is called" do
73
+ is_jruby = defined?(RUBY_ENGINE) && RUBY_ENGINE == 'jruby'
74
+
75
+ class StringRecurser
76
+ def to_s
77
+ to_s
78
+ end
79
+ end
80
+
81
+ it "uses the string '[RECURSION]' instead" do
82
+ skip "JRuby doesn't allow recovery from SystemStackErrors" if is_jruby
83
+
84
+ value = Bugsnag::Helpers.trim_if_needed([1, 3, StringRecurser.new])
85
+ expect(value[2]).to eq "[RECURSION]"
86
+ end
87
+
88
+ it "replaces hash key with '[RECURSION]'" do
89
+ skip "JRuby doesn't allow recovery from SystemStackErrors" if is_jruby
90
+
91
+ a = {}
92
+ a[StringRecurser.new] = 1
93
+
94
+ value = Bugsnag::Helpers.trim_if_needed(a)
95
+ expect(value).to eq({ "[RECURSION]" => "[FILTERED]" })
96
+ end
97
+
98
+ it "uses a single '[RECURSION]'key when multiple keys recurse" do
99
+ skip "JRuby doesn't allow recovery from SystemStackErrors" if is_jruby
100
+
101
+ a = {}
102
+ a[StringRecurser.new] = 1
103
+ a[StringRecurser.new] = 2
104
+
105
+ value = Bugsnag::Helpers.trim_if_needed(a)
106
+ expect(value).to eq({ "[RECURSION]" => "[FILTERED]" })
107
+ end
53
108
  end
54
109
 
55
110
  context "payload length is less than allowed" do
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: bugsnag
3
3
  version: !ruby/object:Gem::Version
4
- version: 6.13.0
4
+ version: 6.13.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - James Smith
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-01-30 00:00:00.000000000 Z
11
+ date: 2020-05-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: concurrent-ruby
@@ -722,8 +722,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
722
722
  - !ruby/object:Gem::Version
723
723
  version: '0'
724
724
  requirements: []
725
- rubyforge_project:
726
- rubygems_version: 2.7.6.2
725
+ rubygems_version: 3.1.2
727
726
  signing_key:
728
727
  specification_version: 4
729
728
  summary: Ruby notifier for bugsnag.com