logstash-output-scalyr 0.1.22.beta → 0.1.26.beta
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +7 -0
- data/Gemfile +1 -0
- data/README.md +1 -2
- data/lib/logstash/outputs/scalyr.rb +116 -70
- data/lib/scalyr/constants.rb +1 -1
- data/logstash-output-scalyr.gemspec +3 -2
- data/spec/benchmarks/flattening_and_serialization.rb +1 -26
- data/spec/benchmarks/json_serialization.rb +85 -0
- data/spec/benchmarks/util.rb +24 -0
- data/spec/logstash/outputs/scalyr_spec.rb +172 -0
- data/vendor/bundle/jruby/2.5.0/cache/jrjackson-0.4.14-java.gem +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/Gemfile +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/Mavenfile +1 -7
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/README.md +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/Rakefile +8 -2
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/alt_bench.rb +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/changelog.md +25 -2
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/jrjackson.gemspec +2 -1
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.14-java/lib/com/fasterxml/jackson/core/jackson-annotations/2.9.10/jackson-annotations-2.9.10.jar +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.14-java/lib/com/fasterxml/jackson/core/jackson-core/2.9.10/jackson-core-2.9.10.jar +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.14-java/lib/com/fasterxml/jackson/core/jackson-databind/2.9.10.8/jackson-databind-2.9.10.8.jar +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.14-java/lib/com/fasterxml/jackson/module/jackson-module-afterburner/2.9.10/jackson-module-afterburner-2.9.10.jar +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/lib/jrjackson/build_info.rb +9 -5
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java/lib/jrjackson/jars/jrjackson-1.2.26.jar → jrjackson-0.4.14-java/lib/jrjackson/jars/jrjackson-1.2.32.jar} +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/lib/jrjackson/jrjackson.rb +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/lib/jrjackson.rb +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/lib/jrjackson_jars.rb +8 -8
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/lib/require_relative_patch.rb +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/pom.xml +8 -25
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/profiling/profiled.rb +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/run_all_individual_bench.sh +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/run_jruby_individual_bench.sh +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/run_mri_individual_bench.sh +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/IParseHandler.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JavaBigDecimalValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JavaBigIntValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JavaConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JavaFloatValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JavaHandler.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JavaLongValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JjParse.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrJacksonBase.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrJacksonJava.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrJacksonRaw.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrJacksonRuby.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrJacksonSaj.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrJacksonSch.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrJacksonService.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/JrParse.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/ParseError.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyAnySerializer.java +4 -4
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyBigDecimalValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyBigIntValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyDateFormat.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyFloatValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyHandler.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyIntValueConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyJacksonModule.java +18 -6
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyKeyConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyNameConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyObjectDeserializer.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyStringConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyStringKeyConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyStringNameConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubySymbolKeyConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubySymbolNameConverter.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/RubyUtils.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/SajParse.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/SchParse.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/main/java/com/jrjackson/StreamParse.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/src/test/java/com/jrjackson/RubyAnySerializerTest.java +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/{jrjackson-0.4.8-java → jrjackson-0.4.14-java}/test/jrjackson_test.rb +15 -0
- data/vendor/bundle/jruby/2.5.0/specifications/{jrjackson-0.4.8-java.gemspec → jrjackson-0.4.14-java.gemspec} +7 -7
- metadata +98 -66
- data/vendor/bundle/jruby/2.5.0/cache/jrjackson-0.4.8-java.gem +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.8-java/lib/com/fasterxml/jackson/core/jackson-annotations/2.9.7/jackson-annotations-2.9.7.jar +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.8-java/lib/com/fasterxml/jackson/core/jackson-core/2.9.7/jackson-core-2.9.7.jar +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.8-java/lib/com/fasterxml/jackson/core/jackson-databind/2.9.7/jackson-databind-2.9.7.jar +0 -0
- data/vendor/bundle/jruby/2.5.0/gems/jrjackson-0.4.8-java/lib/com/fasterxml/jackson/module/jackson-module-afterburner/2.9.7/jackson-module-afterburner-2.9.7.jar +0 -0
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 5593e93dedad0ddb545f8911e7f1cd8cabde4043a6a76b8c5b78d99c0c4d12a5
|
4
|
+
data.tar.gz: 6c821768c3d780529d00bc1f58c4ec8841ecba2758a46c71ecf17201fb8ba3d1
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 57901dc94f49aa844130f4b2a7ac084c95d473c1a948902b699cbaba8d63049d1e960b69b49b20cf8ffa8b2c1f5f68a53ad9687b72867799f113a384f490e01d
|
7
|
+
data.tar.gz: 329f985e8121d49bab836381861ca878c229f2b316e160792263461900a8fc4cf7f46bdc2aba889174a0f35b0c67f567b0e5a09d429f888948b788707ab3c0b7
|
data/CHANGELOG.md
CHANGED
@@ -1,5 +1,12 @@
|
|
1
1
|
# Beta
|
2
2
|
|
3
|
+
## 0.1.26.beta
|
4
|
+
- Add support for new ``json_library`` config option. Valid values are ``stdlib`` (default) are ``jrjackson``. The later may offer 2-4x faster JSON serialization.
|
5
|
+
|
6
|
+
|
7
|
+
## 0.1.23.beta
|
8
|
+
- Add testing support for disabling estimation of serialized event size for each event in the batch.
|
9
|
+
|
3
10
|
## 0.1.22.beta
|
4
11
|
- Add new plugin metric for tracking the duration of ``build_multi_event_request_array`` method.
|
5
12
|
- Update internal dependencies (``manticore``) to latest stable version.
|
data/Gemfile
CHANGED
data/README.md
CHANGED
@@ -1,4 +1,3 @@
|
|
1
|
-
|
2
1
|
[![CircleCI](https://circleci.com/gh/scalyr/logstash-output-scalyr.svg?style=svg)](https://circleci.com/gh/scalyr/logstash-output-scalyr)
|
3
2
|
|
4
3
|
# [Scalyr output plugin for Logstash (Beta release)]
|
@@ -10,7 +9,7 @@ You can view documentation for this plugin [on the Scalyr website](https://app.s
|
|
10
9
|
# Quick start
|
11
10
|
|
12
11
|
1. Build the gem, run `gem build logstash-output-scalyr.gemspec`
|
13
|
-
2. Install the gem into a Logstash installation, run `/usr/share/logstash/bin/logstash-plugin install logstash-output-scalyr-0.1.
|
12
|
+
2. Install the gem into a Logstash installation, run `/usr/share/logstash/bin/logstash-plugin install logstash-output-scalyr-0.1.25.beta.gem` or follow the latest official instructions on working with plugins from Logstash.
|
14
13
|
3. Configure the output plugin (e.g. add it to a pipeline .conf)
|
15
14
|
4. Restart Logstash
|
16
15
|
|
@@ -13,6 +13,7 @@ require 'rbzip2'
|
|
13
13
|
require 'zlib'
|
14
14
|
require 'stringio'
|
15
15
|
require 'quantile'
|
16
|
+
require 'jrjackson'
|
16
17
|
|
17
18
|
require 'scalyr/common/client'
|
18
19
|
require "scalyr/common/util"
|
@@ -140,11 +141,21 @@ class LogStash::Outputs::Scalyr < LogStash::Outputs::Base
|
|
140
141
|
# Whether or not to create fresh quantile estimators after a status send. Depending on what you want to gather from
|
141
142
|
# these stas this might be wanted or not.
|
142
143
|
config :flush_quantile_estimates_on_status_send, :validate => :boolean, :default => false
|
143
|
-
|
144
|
+
|
144
145
|
# Causes this plugin to act as if it successfully uploaded the logs, while actually returning as quickly as possible
|
145
146
|
# after no work being done.
|
146
147
|
config :noop_mode, :validate => :boolean, :default => false
|
147
148
|
|
149
|
+
# Set to true to disable estimiating the size of each serialized event to make sure we don't go over the max request
|
150
|
+
# size (5.5) and split batch into multiple Scalyr requests, if needed. Since this estimation is not "free", especially
|
151
|
+
# for large batches, it may make sense to disable this option when logstash batch size is configured in a way that
|
152
|
+
# Scalyr single request limit won't be reached.
|
153
|
+
config :estimate_each_event_size, :validate => :boolean, :default => true
|
154
|
+
|
155
|
+
# Library to use for JSON serialization. Valid values are "stdlib" and "jrjackson". The later may offer 2-4 performance
|
156
|
+
# improvements on serialization.
|
157
|
+
config :json_library, :validate => :string, :default => "stdlib"
|
158
|
+
|
148
159
|
# Manticore related options
|
149
160
|
config :http_connect_timeout, :validate => :number, :default => 10
|
150
161
|
config :http_socket_timeout, :validate => :number, :default => 10
|
@@ -184,6 +195,24 @@ class LogStash::Outputs::Scalyr < LogStash::Outputs::Base
|
|
184
195
|
@logger.warn "Maximum request buffer > 6 MB. This may result in requests being rejected by Scalyr."
|
185
196
|
end
|
186
197
|
|
198
|
+
if not @estimate_each_event_size
|
199
|
+
@logger.warn("estimate_each_event_size config option is false, this means very large batches may be rejected or partially processed by the server")
|
200
|
+
end
|
201
|
+
|
202
|
+
if @json_library != "stdlib" and @json_library != "jrjackson"
|
203
|
+
raise LogStash::ConfigurationError, "json_library config option needs to be either stdlib or jrjackson"
|
204
|
+
end
|
205
|
+
|
206
|
+
if @json_library == "stdlib"
|
207
|
+
define_singleton_method "json_encode" do |data|
|
208
|
+
data.to_json
|
209
|
+
end
|
210
|
+
elsif @json_library == "jrjackson"
|
211
|
+
define_singleton_method "json_encode" do |data|
|
212
|
+
JrJackson::Json.dump(data)
|
213
|
+
end
|
214
|
+
end
|
215
|
+
|
187
216
|
@dlq_writer = dlq_enabled? ? execution_context.dlq_writer : nil
|
188
217
|
|
189
218
|
@message_encoding = nil
|
@@ -316,16 +345,12 @@ class LogStash::Outputs::Scalyr < LogStash::Outputs::Base
|
|
316
345
|
begin
|
317
346
|
records_count = events.to_a.length
|
318
347
|
|
319
|
-
# We also time the duration of the build_multi_event_request_array method
|
348
|
+
# We also time the duration of the build_multi_event_request_array method. To avoid locking twice,
|
349
|
+
# we store the duration value here and record metric at the end.
|
320
350
|
start_time = Time.now.to_f
|
321
351
|
|
322
352
|
multi_event_request_array = build_multi_event_request_array(events)
|
323
|
-
|
324
|
-
if records_count > 0
|
325
|
-
@stats_lock.synchronize do
|
326
|
-
@plugin_metrics[:build_multi_duration_secs].observe(Time.now.to_f - start_time)
|
327
|
-
end
|
328
|
-
end
|
353
|
+
build_multi_duration_secs = Time.now.to_f - start_time
|
329
354
|
|
330
355
|
# Loop over all array of multi-event requests, sending each multi-event to Scalyr
|
331
356
|
sleep_interval = @retry_initial_interval
|
@@ -439,6 +464,7 @@ class LogStash::Outputs::Scalyr < LogStash::Outputs::Base
|
|
439
464
|
if records_count > 0
|
440
465
|
@stats_lock.synchronize do
|
441
466
|
@multi_receive_statistics[:total_multi_receive_secs] += (Time.now.to_f - start_time)
|
467
|
+
@plugin_metrics[:build_multi_duration_secs].observe(build_multi_duration_secs)
|
442
468
|
@plugin_metrics[:multi_receive_duration_secs].observe(Time.now.to_f - start_time)
|
443
469
|
@plugin_metrics[:multi_receive_event_count].observe(records_count)
|
444
470
|
@plugin_metrics[:batches_per_multi_receive].observe(total_batches)
|
@@ -675,67 +701,75 @@ class LogStash::Outputs::Scalyr < LogStash::Outputs::Base
|
|
675
701
|
scalyr_event[:log] = logs_ids[log_identifier]
|
676
702
|
end
|
677
703
|
|
678
|
-
|
679
|
-
|
680
|
-
|
681
|
-
|
682
|
-
|
683
|
-
|
684
|
-
|
685
|
-
|
686
|
-
|
687
|
-
|
688
|
-
|
689
|
-
|
690
|
-
|
691
|
-
|
692
|
-
|
693
|
-
|
694
|
-
|
695
|
-
|
696
|
-
|
697
|
-
|
698
|
-
|
699
|
-
|
700
|
-
|
701
|
-
|
702
|
-
|
703
|
-
|
704
|
-
|
705
|
-
|
706
|
-
|
707
|
-
@
|
704
|
+
if @estimate_each_event_size
|
705
|
+
# get json string of event to keep track of how many bytes we are sending
|
706
|
+
begin
|
707
|
+
event_json = self.json_encode(scalyr_event)
|
708
|
+
log_json = nil
|
709
|
+
if add_log
|
710
|
+
log_json = self.json_encode(logs[log_identifier])
|
711
|
+
end
|
712
|
+
rescue JSON::GeneratorError, Encoding::UndefinedConversionError => e
|
713
|
+
@logger.warn "#{e.class}: #{e.message}"
|
714
|
+
|
715
|
+
# Send the faulty event to a label @ERROR block and allow to handle it there (output to exceptions file for ex)
|
716
|
+
# TODO
|
717
|
+
# atime = Fluent::EventTime.new( sec, nsec )
|
718
|
+
# router.emit_error_event(serverHost, time, record, e)
|
719
|
+
|
720
|
+
scalyr_event[:attrs].each do |key, value|
|
721
|
+
@logger.debug "\t#{key} (#{value.encoding.name}): '#{value}'"
|
722
|
+
scalyr_event[:attrs][key] = value.encode(
|
723
|
+
"UTF-8", :invalid => :replace, :undef => :replace, :replace => "<?>"
|
724
|
+
).force_encoding('UTF-8')
|
725
|
+
end
|
726
|
+
event_json = self.json_encode(scalyr_event)
|
727
|
+
rescue Java::JavaLang::ClassCastException => e
|
728
|
+
# Most likely we ran into the issue described here: https://github.com/flori/json/issues/336
|
729
|
+
# Because of the version of jruby logstash works with we don't have the option to just update this away,
|
730
|
+
# so if we run into it we convert bignums into strings so we can get the data in at least.
|
731
|
+
# This is fixed in JRuby 9.2.7, which includes json 2.2.0
|
732
|
+
@logger.warn("Error serializing events to JSON, likely due to the presence of Bignum values. Converting Bignum values to strings.")
|
733
|
+
@stats_lock.synchronize do
|
734
|
+
@multi_receive_statistics[:total_java_class_cast_errors] += 1
|
735
|
+
end
|
736
|
+
Scalyr::Common::Util.convert_bignums(scalyr_event)
|
737
|
+
event_json = self.json_encode(scalyr_event)
|
738
|
+
log_json = nil
|
739
|
+
if add_log
|
740
|
+
log_json = self.json_encode(logs[log_identifier])
|
741
|
+
end
|
708
742
|
end
|
709
|
-
|
710
|
-
|
711
|
-
|
712
|
-
|
713
|
-
|
743
|
+
|
744
|
+
# generate new request if json size of events in the array exceed maximum request buffer size
|
745
|
+
append_event = true
|
746
|
+
add_bytes = event_json.bytesize
|
747
|
+
if log_json
|
748
|
+
add_bytes = add_bytes + log_json.bytesize
|
714
749
|
end
|
715
|
-
end
|
716
750
|
|
717
|
-
|
718
|
-
|
719
|
-
|
720
|
-
|
721
|
-
|
722
|
-
|
723
|
-
|
724
|
-
|
725
|
-
|
726
|
-
|
727
|
-
|
728
|
-
|
751
|
+
if total_bytes + add_bytes > @max_request_buffer
|
752
|
+
# make sure we always have at least one event
|
753
|
+
if scalyr_events.size == 0
|
754
|
+
scalyr_events << scalyr_event
|
755
|
+
l_events << l_event
|
756
|
+
append_event = false
|
757
|
+
end
|
758
|
+
|
759
|
+
multi_event_request = self.create_multi_event_request(scalyr_events, l_events, current_threads, logs)
|
760
|
+
multi_event_request_array << multi_event_request
|
761
|
+
|
762
|
+
total_bytes = 0
|
763
|
+
current_threads = Hash.new
|
764
|
+
logs = Hash.new
|
765
|
+
logs_ids = Hash.new
|
766
|
+
scalyr_events = Array.new
|
767
|
+
l_events = Array.new
|
729
768
|
end
|
730
|
-
|
731
|
-
|
732
|
-
|
733
|
-
|
734
|
-
current_threads = Hash.new
|
735
|
-
logs = Hash.new
|
736
|
-
logs_ids = Hash.new
|
737
|
-
scalyr_events = Array.new
|
738
|
-
l_events = Array.new
|
769
|
+
else
|
770
|
+
# If size estimation is disabled we simply append the event and handle splitting later on (if needed)
|
771
|
+
append_event = true
|
772
|
+
add_bytes = 0
|
739
773
|
end
|
740
774
|
|
741
775
|
# if we haven't consumed the current event already
|
@@ -748,9 +782,12 @@ class LogStash::Outputs::Scalyr < LogStash::Outputs::Base
|
|
748
782
|
|
749
783
|
}
|
750
784
|
|
751
|
-
# create a final request with any left over events
|
752
|
-
|
753
|
-
|
785
|
+
# create a final request with any left over events (and make sure there is at least one event)
|
786
|
+
if scalyr_events.size >= 1
|
787
|
+
multi_event_request = self.create_multi_event_request(scalyr_events, l_events, current_threads, logs)
|
788
|
+
multi_event_request_array << multi_event_request
|
789
|
+
end
|
790
|
+
|
754
791
|
multi_event_request_array
|
755
792
|
end
|
756
793
|
|
@@ -801,17 +838,26 @@ class LogStash::Outputs::Scalyr < LogStash::Outputs::Base
|
|
801
838
|
# We time serialization to get some insight on how long it takes to serialize the request body
|
802
839
|
start_time = Time.now.to_f
|
803
840
|
begin
|
804
|
-
serialized_body = body
|
841
|
+
serialized_body = self.json_encode(body)
|
805
842
|
rescue Java::JavaLang::ClassCastException => e
|
806
843
|
@logger.warn("Error serializing events to JSON, likely due to the presence of Bignum values. Converting Bignum values to strings.")
|
807
844
|
@stats_lock.synchronize do
|
808
845
|
@multi_receive_statistics[:total_java_class_cast_errors] += 1
|
809
846
|
end
|
810
847
|
Scalyr::Common::Util.convert_bignums(body)
|
811
|
-
serialized_body = body
|
848
|
+
serialized_body = self.json_encode(body)
|
812
849
|
end
|
813
850
|
end_time = Time.now.to_f
|
814
851
|
serialization_duration = end_time - start_time
|
852
|
+
|
853
|
+
serialized_request_size = serialized_body.bytesize
|
854
|
+
|
855
|
+
# We give it "buffer" since the splitting code allows for some slack and doesn't take into account top-level non-event attributes
|
856
|
+
if not @estimate_each_event_size and serialized_request_size >= @max_request_buffer + 5000
|
857
|
+
# TODO: If we end up here is estimate config opsion is false, split the request here into multiple ones
|
858
|
+
@logger.warn("Serialized request size (#{serialized_request_size}) is larger than max_request_buffer (#{max_request_buffer})!")
|
859
|
+
end
|
860
|
+
|
815
861
|
{
|
816
862
|
:body => serialized_body, :record_count => scalyr_events.size, :serialization_duration => serialization_duration,
|
817
863
|
:logstash_events => logstash_events
|
data/lib/scalyr/constants.rb
CHANGED
@@ -1,2 +1,2 @@
|
|
1
1
|
# encoding: utf-8
|
2
|
-
PLUGIN_VERSION = "v0.1.
|
2
|
+
PLUGIN_VERSION = "v0.1.26.beta"
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Gem::Specification.new do |s|
|
2
2
|
s.name = 'logstash-output-scalyr'
|
3
|
-
s.version = '0.1.
|
3
|
+
s.version = '0.1.26.beta'
|
4
4
|
s.licenses = ['Apache-2.0']
|
5
5
|
s.summary = "Scalyr output plugin for Logstash"
|
6
6
|
s.description = "Sends log data collected by Logstash to Scalyr (https://www.scalyr.com)"
|
@@ -18,11 +18,12 @@ Gem::Specification.new do |s|
|
|
18
18
|
s.metadata = { "logstash_plugin" => "true", "logstash_group" => "output" }
|
19
19
|
|
20
20
|
# Gem dependencies
|
21
|
-
#
|
22
21
|
s.add_runtime_dependency 'net-http-persistent'
|
23
22
|
s.add_runtime_dependency 'logstash-core-plugin-api', '>= 1.60', '<= 2.99'
|
24
23
|
s.add_runtime_dependency 'logstash-codec-plain'
|
25
24
|
s.add_runtime_dependency 'quantile'
|
25
|
+
s.add_runtime_dependency 'jrjackson'
|
26
|
+
s.add_runtime_dependency 'manticore'
|
26
27
|
s.add_runtime_dependency 'ffi', '>= 1.9.18'
|
27
28
|
s.add_runtime_dependency 'rbzip2', '0.3.0'
|
28
29
|
s.add_development_dependency 'logstash-devutils'
|
@@ -2,6 +2,7 @@ require 'benchmark'
|
|
2
2
|
require 'json'
|
3
3
|
|
4
4
|
require_relative '../../lib/scalyr/common/util'
|
5
|
+
require_relative './util'
|
5
6
|
|
6
7
|
# NOTE: When using jRuby using multiple iterations with the same dataset doesn't make
|
7
8
|
# sense since it will just use JITed version of the code which will be very fast. If we
|
@@ -9,31 +10,6 @@ require_relative '../../lib/scalyr/common/util'
|
|
9
10
|
# input data for each iteration.
|
10
11
|
ITERATIONS = 500
|
11
12
|
|
12
|
-
def rand_str(len)
|
13
|
-
return (0...len).map { (65 + rand(26)).chr }.join
|
14
|
-
end
|
15
|
-
|
16
|
-
def generate_hash(widths)
|
17
|
-
result = {}
|
18
|
-
if widths.empty?
|
19
|
-
return rand_str(20)
|
20
|
-
else
|
21
|
-
widths[0].times do
|
22
|
-
result[rand_str(9)] = generate_hash(widths[1..widths.length])
|
23
|
-
end
|
24
|
-
return result
|
25
|
-
end
|
26
|
-
end
|
27
|
-
|
28
|
-
def generate_data_array_for_spec(spec)
|
29
|
-
data = []
|
30
|
-
ITERATIONS.times do
|
31
|
-
data << generate_hash(spec)
|
32
|
-
end
|
33
|
-
|
34
|
-
data
|
35
|
-
end
|
36
|
-
|
37
13
|
def run_benchmark_and_print_results(data, run_benchmark_func)
|
38
14
|
puts ""
|
39
15
|
puts "Using %s total keys in a hash" % [Scalyr::Common::Util.flatten(data[0]).count]
|
@@ -70,7 +46,6 @@ DATASETS = {
|
|
70
46
|
:keys_2700 => generate_data_array_for_spec([14, 8, 6, 4])
|
71
47
|
}
|
72
48
|
|
73
|
-
|
74
49
|
puts "Using %s iterations" % [ITERATIONS]
|
75
50
|
puts ""
|
76
51
|
|
@@ -0,0 +1,85 @@
|
|
1
|
+
require 'benchmark'
|
2
|
+
require 'json'
|
3
|
+
require 'jrjackson'
|
4
|
+
|
5
|
+
require_relative '../../lib/scalyr/common/util'
|
6
|
+
require_relative './util'
|
7
|
+
|
8
|
+
ITERATIONS = 500
|
9
|
+
|
10
|
+
def json_serialize_data_native(data)
|
11
|
+
data.to_json
|
12
|
+
end
|
13
|
+
|
14
|
+
def json_serialize_data_jrjackson(data)
|
15
|
+
JrJackson::Json.dump(data)
|
16
|
+
end
|
17
|
+
|
18
|
+
DATASETS = {
|
19
|
+
:keys_50 => generate_data_array_for_spec([3, 3, 3, 2]),
|
20
|
+
:keys_200 => generate_data_array_for_spec([4, 4, 3, 4]),
|
21
|
+
:keys_200_flat => generate_data_array_for_spec([200]),
|
22
|
+
:keys_512 => generate_data_array_for_spec([8, 4, 4, 4]),
|
23
|
+
:keys_960 => generate_data_array_for_spec([12, 5, 4, 4]),
|
24
|
+
:keys_2700 => generate_data_array_for_spec([14, 8, 6, 4])
|
25
|
+
}
|
26
|
+
|
27
|
+
def run_benchmark_and_print_results(data, run_benchmark_func)
|
28
|
+
puts ""
|
29
|
+
puts "Using %s total keys in a hash" % [Scalyr::Common::Util.flatten(data[0]).count]
|
30
|
+
puts ""
|
31
|
+
|
32
|
+
result = []
|
33
|
+
ITERATIONS.times do |i|
|
34
|
+
result << Benchmark.measure { run_benchmark_func.(data[0]) }
|
35
|
+
end
|
36
|
+
|
37
|
+
sum = result.inject(nil) { |sum, t| sum.nil? ? sum = t : sum += t }
|
38
|
+
avg = sum / result.size
|
39
|
+
|
40
|
+
Benchmark.bm(7, "sum:", "avg:") do |b|
|
41
|
+
[sum, avg]
|
42
|
+
end
|
43
|
+
puts ""
|
44
|
+
end
|
45
|
+
|
46
|
+
puts "Using %s iterations" % [ITERATIONS]
|
47
|
+
puts ""
|
48
|
+
|
49
|
+
puts "native"
|
50
|
+
puts "==============================="
|
51
|
+
|
52
|
+
# Around ~50 keys in a hash
|
53
|
+
data = DATASETS[:keys_50]
|
54
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_native))
|
55
|
+
|
56
|
+
# Around ~200 keys in a hash
|
57
|
+
data = DATASETS[:keys_200]
|
58
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_native))
|
59
|
+
|
60
|
+
# Around ~200 keys in a hash (single level)
|
61
|
+
data = DATASETS[:keys_200_flat]
|
62
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_native))
|
63
|
+
|
64
|
+
# Around ~2700 keys in a hash
|
65
|
+
data = DATASETS[:keys_2700]
|
66
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_native))
|
67
|
+
|
68
|
+
puts "jrjackson"
|
69
|
+
puts "==============================="
|
70
|
+
|
71
|
+
# Around ~50 keys in a hash
|
72
|
+
data = DATASETS[:keys_50]
|
73
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_jrjackson))
|
74
|
+
|
75
|
+
# Around ~200 keys in a hash
|
76
|
+
data = DATASETS[:keys_200]
|
77
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_jrjackson))
|
78
|
+
|
79
|
+
# Around ~200 keys in a hash (single level)
|
80
|
+
data = DATASETS[:keys_200_flat]
|
81
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_jrjackson))
|
82
|
+
|
83
|
+
# Around ~2700 keys in a hash
|
84
|
+
data = DATASETS[:keys_2700]
|
85
|
+
run_benchmark_and_print_results(data, method(:json_serialize_data_jrjackson))
|