Skip to content

Commit fb20a58

Browse files
authored
Fix JSON::GeneratorError for objects with invalid UTF-8 in to_s (#1199)
Rollbar::Encoding.encode only processed String and Symbol types. When objects with to_s methods returning invalid UTF-8 were included in the payload, they bypassed encoding and caused JSON serialization to fail with "source sequence is illegal/malformed utf-8". Now all non-JSON-native types are passed through the Encoder, which already calls to_s and handles encoding normalization. Fixes #1196
1 parent f6f633c commit fb20a58

2 files changed

Lines changed: 11 additions & 5 deletions

File tree

lib/rollbar/encoding.rb

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,12 @@ def self.setup
1010
end
1111

1212
def self.encode(object)
13-
can_be_encoded = object.is_a?(String) || object.is_a?(Symbol)
14-
15-
return object unless can_be_encoded
16-
17-
encoding_class.new(object).encode
13+
case object
14+
when Numeric, TrueClass, FalseClass, NilClass
15+
object
16+
else
17+
encoding_class.new(object).encode
18+
end
1819
end
1920
end
2021
end

spec/rollbar/util_spec.rb

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -134,10 +134,14 @@
134134
it 'should replace invalid utf8 values' do
135135
bad_key = force_to_ascii("inner \x92bad key")
136136

137+
class ObjClass; def to_s; "bad obj\255".force_encoding('ASCII-8BIT'); end; end
138+
bad_obj = ObjClass.new
139+
137140
payload = {
138141
:bad_value => force_to_ascii("bad value 1\255"),
139142
:bad_value2 => force_to_ascii("bad\255 value 2"),
140143
force_to_ascii("bad\255 key") => 'good value',
144+
:bad_obj => bad_obj,
141145
:hash => {
142146
:inner_bad_value => force_to_ascii("\255\255bad value 3"),
143147
bad_key.to_sym => 'inner good value',
@@ -157,6 +161,7 @@
157161
payload_copy[:bad_value].should eq('bad value 1')
158162
payload_copy[:bad_value2].should eq('bad value 2')
159163
payload_copy['bad key'].should eq('good value')
164+
payload_copy[:bad_obj].should eq('bad obj')
160165
payload_copy.keys.should_not include("bad\456 key")
161166
payload_copy[:hash][:inner_bad_value].should eq('bad value 3')
162167
payload_copy[:hash][:"inner bad key"].should eq('inner good value')

0 commit comments

Comments
 (0)