Skip to content

Commit 6186ad6

Browse files
use Event#from_json when possible
cosmetic reindent refactor for the array return value of from_json wrong paramter refactor to support testing from_json and legacy parser refactor to support testing from_json and legacy parser - take2
1 parent 257cbd7 commit 6186ad6

File tree

2 files changed

+55
-19
lines changed

2 files changed

+55
-19
lines changed

lib/logstash/codecs/json_lines.rb

Lines changed: 18 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -36,26 +36,34 @@ def register
3636
@converter.logger = @logger
3737
end
3838

39-
def decode(data)
39+
def decode(data, &block)
4040
@buffer.extract(data).each do |line|
41-
yield guard(@converter.convert(line))
41+
parse(@converter.convert(line), &block)
4242
end
43-
end # def decode
43+
end
4444

4545
def encode(event)
4646
# Tack on a @delimiter for now because previously most of logstash's JSON
4747
# outputs emitted one per line, and whitespace is OK in json.
4848
@on_event.call(event, "#{event.to_json}#{@delimiter}")
49-
end # def encode
49+
end
5050

5151
private
5252

53-
def guard(data)
54-
begin
55-
LogStash::Event.new(LogStash::Json.load(data))
56-
rescue LogStash::Json::ParserError => e
57-
LogStash::Event.new("message" => data, "tags" => ["_jsonparsefailure"])
58-
end
53+
# from_json_parse uses the Event#from_json method to deserialize and directly produce events
54+
def from_json_parse(json, &block)
55+
LogStash::Event.from_json(json).each { |event| yield event }
56+
rescue LogStash::Json::ParserError
57+
yield LogStash::Event.new("message" => json, "tags" => ["_jsonparsefailure"])
5958
end
6059

60+
# legacy_parse uses the LogStash::Json class to deserialize json
61+
def legacy_parse(json, &block)
62+
yield LogStash::Event.new(LogStash::Json.load(json))
63+
rescue LogStash::Json::ParserError
64+
yield LogStash::Event.new("message" => json, "tags" => ["_jsonparsefailure"])
65+
end
66+
67+
alias_method :parse, LogStash::Event.respond_to?(:from_json) ? :from_json_parse : :legacy_parse
68+
6169
end # class LogStash::Codecs::JSONLines

spec/codecs/json_lines_spec.rb

Lines changed: 37 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,10 @@
66
require "insist"
77

88
describe LogStash::Codecs::JSONLines do
9-
subject do
10-
next LogStash::Codecs::JSONLines.new
11-
end
9+
10+
let(:codec_options) { {} }
11+
12+
shared_examples :codec do
1213

1314
context "#decode" do
1415
it "should return an event from json data" do
@@ -37,9 +38,7 @@
3738
context "when using custom delimiter" do
3839
let(:delimiter) { "|" }
3940
let(:line) { "{\"hey\":1}|{\"hey\":2}|{\"hey\":3}|" }
40-
subject do
41-
next LogStash::Codecs::JSONLines.new("delimiter" => delimiter)
42-
end
41+
let(:codec_options) { { "delimiter" => delimiter } }
4342

4443
it "should decode multiple lines separated by the delimiter" do
4544
result = []
@@ -122,9 +121,7 @@
122121

123122
context "when using custom delimiter" do
124123
let(:delimiter) { "|" }
125-
subject do
126-
next LogStash::Codecs::JSONLines.new("delimiter" => delimiter)
127-
end
124+
let(:codec_options) { { "delimiter" => delimiter } }
128125

129126
it "should decode multiple lines separated by the delimiter" do
130127
subject.on_event do |e, d|
@@ -170,4 +167,35 @@
170167
expect(collector.last['field']).to eq('value2')
171168
end
172169
end
170+
171+
end
172+
173+
context "forcing legacy parsing" do
174+
it_behaves_like :codec do
175+
subject do
176+
# register method is called in the constructor
177+
LogStash::Codecs::JSONLines.new(codec_options)
178+
end
179+
180+
before(:each) do
181+
# stub codec parse method to force use of the legacy parser.
182+
# this is very implementation specific but I am not sure how
183+
# this can be tested otherwise.
184+
allow(subject).to receive(:parse) do |line, &block|
185+
subject.send(:legacy_parse, line, &block)
186+
end
187+
end
188+
end
189+
end
190+
191+
context "default parser choice" do
192+
# here we cannot force the use of the Event#from_json since if this test is run in the
193+
# legacy context (no Java Event) it will fail but if in the new context, it will be picked up.
194+
it_behaves_like :codec do
195+
subject do
196+
# register method is called in the constructor
197+
LogStash::Codecs::JSONLines.new(codec_options)
198+
end
199+
end
200+
end
173201
end

0 commit comments

Comments
 (0)