logstash-core 5.6.16-java → 6.0.0.alpha1-java
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.
- checksums.yaml +4 -4
- data/gemspec_jars.rb +4 -7
- data/lib/logstash-core/logstash-core.jar +0 -0
- data/lib/logstash-core/version.rb +4 -8
- data/lib/logstash-core_jars.rb +12 -26
- data/lib/logstash/agent.rb +261 -246
- data/lib/logstash/api/commands/default_metadata.rb +1 -1
- data/lib/logstash/api/commands/hot_threads_reporter.rb +5 -11
- data/lib/logstash/api/commands/node.rb +3 -2
- data/lib/logstash/api/commands/stats.rb +3 -2
- data/lib/logstash/bootstrap_check/bad_java.rb +16 -0
- data/lib/logstash/bootstrap_check/bad_ruby.rb +12 -0
- data/lib/logstash/bootstrap_check/default_config.rb +17 -0
- data/lib/logstash/compiler.rb +38 -0
- data/lib/logstash/compiler/lscl.rb +566 -0
- data/lib/logstash/compiler/lscl/lscl_grammar.rb +3503 -0
- data/lib/logstash/compiler/treetop_monkeypatches.rb +92 -0
- data/lib/logstash/config/config_ast.rb +4 -82
- data/lib/logstash/config/mixin.rb +73 -41
- data/lib/logstash/config/pipeline_config.rb +48 -0
- data/lib/logstash/config/source/base.rb +16 -0
- data/lib/logstash/config/source/local.rb +215 -0
- data/lib/logstash/config/source_loader.rb +125 -0
- data/lib/logstash/converge_result.rb +103 -0
- data/lib/logstash/environment.rb +6 -19
- data/lib/logstash/errors.rb +2 -0
- data/lib/logstash/execution_context.rb +4 -7
- data/lib/logstash/filter_delegator.rb +6 -9
- data/lib/logstash/inputs/base.rb +0 -2
- data/lib/logstash/instrument/collector.rb +5 -7
- data/lib/logstash/instrument/metric_store.rb +12 -12
- data/lib/logstash/instrument/metric_type/mean.rb +0 -5
- data/lib/logstash/instrument/namespaced_metric.rb +0 -4
- data/lib/logstash/instrument/namespaced_null_metric.rb +0 -4
- data/lib/logstash/instrument/null_metric.rb +0 -10
- data/lib/logstash/instrument/periodic_poller/cgroup.rb +85 -168
- data/lib/logstash/instrument/periodic_poller/jvm.rb +5 -5
- data/lib/logstash/instrument/periodic_poller/pq.rb +3 -7
- data/lib/logstash/instrument/periodic_pollers.rb +1 -3
- data/lib/logstash/instrument/wrapped_write_client.rb +24 -33
- data/lib/logstash/logging/logger.rb +15 -47
- data/lib/logstash/namespace.rb +0 -1
- data/lib/logstash/output_delegator.rb +5 -7
- data/lib/logstash/outputs/base.rb +0 -2
- data/lib/logstash/pipeline.rb +159 -87
- data/lib/logstash/pipeline_action.rb +13 -0
- data/lib/logstash/pipeline_action/base.rb +29 -0
- data/lib/logstash/pipeline_action/create.rb +47 -0
- data/lib/logstash/pipeline_action/reload.rb +48 -0
- data/lib/logstash/pipeline_action/stop.rb +23 -0
- data/lib/logstash/plugin.rb +0 -1
- data/lib/logstash/plugins/hooks_registry.rb +6 -0
- data/lib/logstash/plugins/registry.rb +0 -1
- data/lib/logstash/program.rb +14 -0
- data/lib/logstash/queue_factory.rb +5 -1
- data/lib/logstash/runner.rb +58 -80
- data/lib/logstash/settings.rb +3 -27
- data/lib/logstash/state_resolver.rb +41 -0
- data/lib/logstash/util/java_version.rb +6 -0
- data/lib/logstash/util/safe_uri.rb +12 -148
- data/lib/logstash/util/thread_dump.rb +4 -7
- data/lib/logstash/util/wrapped_acked_queue.rb +36 -39
- data/lib/logstash/util/wrapped_synchronous_queue.rb +29 -39
- data/lib/logstash/version.rb +10 -8
- data/locales/en.yml +3 -54
- data/logstash-core.gemspec +8 -35
- data/spec/{logstash/api/modules → api/lib/api}/logging_spec.rb +10 -1
- data/spec/{logstash/api/modules → api/lib/api}/node_plugins_spec.rb +2 -1
- data/spec/{logstash/api/modules → api/lib/api}/node_spec.rb +3 -3
- data/spec/{logstash/api/modules → api/lib/api}/node_stats_spec.rb +3 -7
- data/spec/{logstash/api/modules → api/lib/api}/plugins_spec.rb +3 -4
- data/spec/{logstash/api/modules → api/lib/api}/root_spec.rb +2 -2
- data/spec/api/lib/api/support/resource_dsl_methods.rb +87 -0
- data/spec/{logstash/api/commands/stats_spec.rb → api/lib/commands/stats.rb} +2 -7
- data/spec/{logstash/api → api/lib}/errors_spec.rb +1 -1
- data/spec/{logstash/api → api/lib}/rack_app_spec.rb +0 -0
- data/spec/api/spec_helper.rb +106 -0
- data/spec/logstash/agent/converge_spec.rb +286 -0
- data/spec/logstash/agent/metrics_spec.rb +244 -0
- data/spec/logstash/agent_spec.rb +213 -225
- data/spec/logstash/compiler/compiler_spec.rb +584 -0
- data/spec/logstash/config/config_ast_spec.rb +8 -47
- data/spec/logstash/config/mixin_spec.rb +2 -42
- data/spec/logstash/config/pipeline_config_spec.rb +75 -0
- data/spec/logstash/config/source/local_spec.rb +395 -0
- data/spec/logstash/config/source_loader_spec.rb +122 -0
- data/spec/logstash/converge_result_spec.rb +179 -0
- data/spec/logstash/event_spec.rb +0 -66
- data/spec/logstash/execution_context_spec.rb +8 -12
- data/spec/logstash/filter_delegator_spec.rb +12 -24
- data/spec/logstash/inputs/base_spec.rb +7 -5
- data/spec/logstash/instrument/periodic_poller/cgroup_spec.rb +92 -225
- data/spec/logstash/instrument/periodic_poller/jvm_spec.rb +1 -1
- data/spec/logstash/instrument/periodic_poller/os_spec.rb +32 -29
- data/spec/logstash/instrument/wrapped_write_client_spec.rb +33 -33
- data/spec/logstash/legacy_ruby_event_spec.rb +13 -4
- data/spec/logstash/output_delegator_spec.rb +11 -20
- data/spec/logstash/outputs/base_spec.rb +7 -5
- data/spec/logstash/pipeline_action/create_spec.rb +83 -0
- data/spec/logstash/pipeline_action/reload_spec.rb +83 -0
- data/spec/logstash/pipeline_action/stop_spec.rb +37 -0
- data/spec/logstash/pipeline_pq_file_spec.rb +1 -1
- data/spec/logstash/pipeline_spec.rb +81 -137
- data/spec/logstash/plugin_spec.rb +2 -1
- data/spec/logstash/plugins/hooks_registry_spec.rb +6 -0
- data/spec/logstash/queue_factory_spec.rb +13 -1
- data/spec/logstash/runner_spec.rb +29 -140
- data/spec/logstash/settings/writable_directory_spec.rb +10 -13
- data/spec/logstash/settings_spec.rb +0 -91
- data/spec/logstash/state_resolver_spec.rb +156 -0
- data/spec/logstash/timestamp_spec.rb +2 -6
- data/spec/logstash/util/java_version_spec.rb +22 -0
- data/spec/logstash/util/safe_uri_spec.rb +0 -56
- data/spec/logstash/util/wrapped_synchronous_queue_spec.rb +22 -0
- data/spec/support/helpers.rb +9 -11
- data/spec/support/matchers.rb +96 -6
- data/spec/support/mocks_classes.rb +80 -0
- data/spec/support/shared_contexts.rb +2 -27
- metadata +100 -149
- data/lib/logstash/config/loader.rb +0 -107
- data/lib/logstash/config/modules_common.rb +0 -103
- data/lib/logstash/config/source/modules.rb +0 -55
- data/lib/logstash/config/string_escape.rb +0 -27
- data/lib/logstash/dependency_report.rb +0 -131
- data/lib/logstash/dependency_report_runner.rb +0 -17
- data/lib/logstash/elasticsearch_client.rb +0 -142
- data/lib/logstash/instrument/global_metrics.rb +0 -13
- data/lib/logstash/instrument/periodic_poller/dlq.rb +0 -24
- data/lib/logstash/modules/cli_parser.rb +0 -74
- data/lib/logstash/modules/elasticsearch_config.rb +0 -22
- data/lib/logstash/modules/elasticsearch_importer.rb +0 -37
- data/lib/logstash/modules/elasticsearch_resource.rb +0 -10
- data/lib/logstash/modules/file_reader.rb +0 -36
- data/lib/logstash/modules/kibana_base.rb +0 -24
- data/lib/logstash/modules/kibana_client.rb +0 -124
- data/lib/logstash/modules/kibana_config.rb +0 -105
- data/lib/logstash/modules/kibana_dashboards.rb +0 -36
- data/lib/logstash/modules/kibana_importer.rb +0 -17
- data/lib/logstash/modules/kibana_resource.rb +0 -10
- data/lib/logstash/modules/kibana_settings.rb +0 -40
- data/lib/logstash/modules/logstash_config.rb +0 -120
- data/lib/logstash/modules/resource_base.rb +0 -38
- data/lib/logstash/modules/scaffold.rb +0 -52
- data/lib/logstash/modules/settings_merger.rb +0 -23
- data/lib/logstash/modules/util.rb +0 -17
- data/lib/logstash/util/dead_letter_queue_manager.rb +0 -61
- data/lib/logstash/util/environment_variables.rb +0 -43
- data/spec/logstash/config/loader_spec.rb +0 -38
- data/spec/logstash/config/string_escape_spec.rb +0 -24
- data/spec/logstash/instrument/periodic_poller/dlq_spec.rb +0 -17
- data/spec/logstash/modules/logstash_config_spec.rb +0 -56
- data/spec/logstash/modules/scaffold_spec.rb +0 -234
- data/spec/logstash/pipeline_dlq_commit_spec.rb +0 -109
- data/spec/logstash/settings/splittable_string_array_spec.rb +0 -51
- data/spec/logstash/util/wrapped_acked_queue_spec.rb +0 -49
- data/versions-gem-copy.yml +0 -12
@@ -1,5 +1,4 @@
|
|
1
1
|
# encoding: utf-8
|
2
|
-
java_import 'org.logstash.instrument.reports.ThreadsReport'
|
3
2
|
|
4
3
|
class HotThreadsReport
|
5
4
|
STRING_SEPARATOR_LENGTH = 80.freeze
|
@@ -8,7 +7,8 @@ class HotThreadsReport
|
|
8
7
|
def initialize(cmd, options)
|
9
8
|
@cmd = cmd
|
10
9
|
filter = { :stacktrace_size => options.fetch(:stacktrace_size, HOT_THREADS_STACK_TRACES_SIZE_DEFAULT) }
|
11
|
-
|
10
|
+
jr_dump = JRMonitor.threads.generate(filter)
|
11
|
+
@thread_dump = ::LogStash::Util::ThreadDump.new(options.merge(:dump => jr_dump))
|
12
12
|
end
|
13
13
|
|
14
14
|
def to_s
|
@@ -17,12 +17,7 @@ class HotThreadsReport
|
|
17
17
|
report << '=' * STRING_SEPARATOR_LENGTH
|
18
18
|
report << "\n"
|
19
19
|
hash[:threads].each do |thread|
|
20
|
-
|
21
|
-
:percent_of_cpu_time => thread[:percent_of_cpu_time],
|
22
|
-
:thread_state => thread[:state],
|
23
|
-
:thread_name => thread[:name],
|
24
|
-
:thread_id => thread[:thread_id])
|
25
|
-
thread_report = "#{line_str} \n"
|
20
|
+
thread_report = "#{I18n.t("logstash.web_api.hot_threads.thread_title", :percent_of_cpu_time => thread[:percent_of_cpu_time], :thread_state => thread[:state], :thread_name => thread[:name])} \n"
|
26
21
|
thread_report << "#{thread[:path]}\n" if thread[:path]
|
27
22
|
thread[:traces].each do |trace|
|
28
23
|
thread_report << "\t#{trace}\n"
|
@@ -36,10 +31,9 @@ class HotThreadsReport
|
|
36
31
|
|
37
32
|
def to_hash
|
38
33
|
hash = { :time => Time.now.iso8601, :busiest_threads => @thread_dump.top_count, :threads => [] }
|
39
|
-
@thread_dump.each do |_hash|
|
34
|
+
@thread_dump.each do |thread_name, _hash|
|
40
35
|
thread_name, thread_path = _hash["thread.name"].split(": ")
|
41
36
|
thread = { :name => thread_name,
|
42
|
-
:thread_id => _hash["thread.id"],
|
43
37
|
:percent_of_cpu_time => cpu_time_as_percent(_hash),
|
44
38
|
:state => _hash["thread.state"]
|
45
39
|
}
|
@@ -48,7 +42,7 @@ class HotThreadsReport
|
|
48
42
|
_hash["thread.stacktrace"].each do |trace|
|
49
43
|
traces << trace
|
50
44
|
end
|
51
|
-
thread[:traces] = traces
|
45
|
+
thread[:traces] = traces unless traces.empty?
|
52
46
|
hash[:threads] << thread
|
53
47
|
end
|
54
48
|
{ :hot_threads => hash }
|
@@ -20,8 +20,8 @@ module LogStash
|
|
20
20
|
def pipeline(pipeline_id = LogStash::SETTINGS.get("pipeline.id").to_sym)
|
21
21
|
stats = extract_metrics(
|
22
22
|
[:stats, :pipelines, pipeline_id, :config],
|
23
|
-
:workers, :batch_size, :batch_delay, :config_reload_automatic, :config_reload_interval
|
24
|
-
)
|
23
|
+
:workers, :batch_size, :batch_delay, :config_reload_automatic, :config_reload_interval
|
24
|
+
)
|
25
25
|
stats.merge(:id => pipeline_id)
|
26
26
|
end
|
27
27
|
|
@@ -40,6 +40,7 @@ module LogStash
|
|
40
40
|
{
|
41
41
|
:pid => ManagementFactory.getRuntimeMXBean().getName().split("@").first.to_i,
|
42
42
|
:version => java.lang.System.getProperty("java.version"),
|
43
|
+
:vm_name => java.lang.System.getProperty("java.vm.name"),
|
43
44
|
:vm_version => java.lang.System.getProperty("java.version"),
|
44
45
|
:vm_vendor => java.lang.System.getProperty("java.vendor"),
|
45
46
|
:vm_name => java.lang.System.getProperty("java.vm.name"),
|
@@ -54,6 +54,7 @@ module LogStash
|
|
54
54
|
def memory
|
55
55
|
memory = service.get_shallow(:jvm, :memory)
|
56
56
|
{
|
57
|
+
:heap_used_in_bytes => memory[:heap][:used_in_bytes],
|
57
58
|
:heap_used_percent => memory[:heap][:used_percent],
|
58
59
|
:heap_committed_in_bytes => memory[:heap][:committed_in_bytes],
|
59
60
|
:heap_max_in_bytes => memory[:heap][:max_in_bytes],
|
@@ -107,8 +108,8 @@ module LogStash
|
|
107
108
|
},
|
108
109
|
:reloads => stats[:reloads],
|
109
110
|
:queue => stats[:queue]
|
110
|
-
}
|
111
|
-
|
111
|
+
}
|
112
|
+
end
|
112
113
|
end # module PluginsStats
|
113
114
|
end
|
114
115
|
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require "logstash/util"
|
3
|
+
require "logstash/util/java_version"
|
4
|
+
require "logstash/errors"
|
5
|
+
|
6
|
+
module LogStash module BootstrapCheck
|
7
|
+
class BadJava
|
8
|
+
def self.check(settings)
|
9
|
+
# Exit on bad java versions
|
10
|
+
LogStash::Util::JavaVersion.validate_java_version!
|
11
|
+
rescue => e
|
12
|
+
# Just rewrap the original exception
|
13
|
+
raise LogStash::BootstrapCheckError, e.message
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require "logstash/errors"
|
3
|
+
|
4
|
+
module LogStash module BootstrapCheck
|
5
|
+
class BadRuby
|
6
|
+
def self.check(settings)
|
7
|
+
if RUBY_VERSION < "1.9.2"
|
8
|
+
raise LogStash::BootstrapCheckError, "Ruby 1.9.2 or later is required. (You are running: " + RUBY_VERSION + ")"
|
9
|
+
end
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require "logstash/errors"
|
3
|
+
|
4
|
+
module LogStash module BootstrapCheck
|
5
|
+
class DefaultConfig
|
6
|
+
def self.check(settings)
|
7
|
+
if settings.get("config.string").nil? && settings.get("path.config").nil?
|
8
|
+
raise LogStash::BootstrapCheckError, I18n.t("logstash.runner.missing-configuration")
|
9
|
+
end
|
10
|
+
|
11
|
+
if settings.get("config.reload.automatic") && settings.get("path.config").nil?
|
12
|
+
# there's nothing to reload
|
13
|
+
raise LogStash::BootstrapCheckError, I18n.t("logstash.runner.reload-without-config-path")
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
require 'logstash/util/loggable'
|
2
|
+
require 'logstash/compiler/lscl/lscl_grammar'
|
3
|
+
|
4
|
+
java_import org.logstash.config.ir.Pipeline
|
5
|
+
java_import org.logstash.config.ir.graph.Graph;
|
6
|
+
java_import org.logstash.config.ir.graph.PluginVertex;
|
7
|
+
|
8
|
+
module LogStash; class Compiler
|
9
|
+
include ::LogStash::Util::Loggable
|
10
|
+
|
11
|
+
def self.compile_pipeline(config_str, source_file=nil)
|
12
|
+
graph_sections = self.compile_graph(config_str, source_file)
|
13
|
+
pipeline = org.logstash.config.ir.Pipeline.new(
|
14
|
+
graph_sections[:input],
|
15
|
+
graph_sections[:filter],
|
16
|
+
graph_sections[:output]
|
17
|
+
)
|
18
|
+
end
|
19
|
+
|
20
|
+
def self.compile_ast(config_str, source_file=nil)
|
21
|
+
grammar = LogStashCompilerLSCLGrammarParser.new
|
22
|
+
config = grammar.parse(config_str)
|
23
|
+
|
24
|
+
if config.nil?
|
25
|
+
raise ConfigurationError, grammar.failure_reason
|
26
|
+
end
|
27
|
+
|
28
|
+
config
|
29
|
+
end
|
30
|
+
|
31
|
+
def self.compile_imperative(config_str, source_file=nil)
|
32
|
+
compile_ast(config_str, source_file).compile(source_file)
|
33
|
+
end
|
34
|
+
|
35
|
+
def self.compile_graph(config_str, source_file=nil)
|
36
|
+
Hash[compile_imperative(config_str, source_file).map {|section,icompiled| [section, icompiled.toGraph]}]
|
37
|
+
end
|
38
|
+
end; end
|
@@ -0,0 +1,566 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require 'logstash/errors'
|
3
|
+
require "treetop"
|
4
|
+
require "logstash/compiler/treetop_monkeypatches"
|
5
|
+
java_import org.logstash.config.ir.DSL
|
6
|
+
java_import org.logstash.common.SourceWithMetadata
|
7
|
+
|
8
|
+
module LogStashCompilerLSCLGrammar; module LogStash; module Compiler; module LSCL; module AST
|
9
|
+
# Helpers for parsing LSCL files
|
10
|
+
module Helpers
|
11
|
+
def source_meta
|
12
|
+
line, column = line_and_column
|
13
|
+
org.logstash.common.SourceWithMetadata.new(source_file, line, column, self.text_value)
|
14
|
+
end
|
15
|
+
|
16
|
+
def source_file=(value)
|
17
|
+
set_meta(:source_file, value)
|
18
|
+
end
|
19
|
+
|
20
|
+
def source_file
|
21
|
+
get_meta(:source_file)
|
22
|
+
end
|
23
|
+
|
24
|
+
def compose(*statements)
|
25
|
+
compose_for(section_type.to_sym).call(source_meta, *statements)
|
26
|
+
end
|
27
|
+
|
28
|
+
def compose_for(section_sym)
|
29
|
+
if section_sym == :filter
|
30
|
+
jdsl.method(:iComposeSequence)
|
31
|
+
else
|
32
|
+
jdsl.method(:iComposeParallel)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
def line_and_column
|
37
|
+
start = self.interval.first
|
38
|
+
[self.input.line_of(start), self.input.column_of(start)]
|
39
|
+
end
|
40
|
+
|
41
|
+
def empty_source_meta()
|
42
|
+
org.logstash.common.SourceWithMetadata.new()
|
43
|
+
end
|
44
|
+
|
45
|
+
def jdsl
|
46
|
+
org.logstash.config.ir.DSL
|
47
|
+
end
|
48
|
+
|
49
|
+
def self.jdsl
|
50
|
+
org.logstash.config.ir.DSL
|
51
|
+
end
|
52
|
+
|
53
|
+
AND_METHOD = jdsl.method(:eAnd)
|
54
|
+
OR_METHOD = jdsl.method(:eOr)
|
55
|
+
end
|
56
|
+
|
57
|
+
class Node < Treetop::Runtime::SyntaxNode
|
58
|
+
include Helpers
|
59
|
+
|
60
|
+
def section_type
|
61
|
+
if recursive_select_parent(Plugin).any?
|
62
|
+
return "codec"
|
63
|
+
else
|
64
|
+
section = recursive_select_parent(PluginSection)
|
65
|
+
return section.first.plugin_type.text_value
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
class Config < Node
|
71
|
+
include Helpers
|
72
|
+
|
73
|
+
def compile(source_file=nil)
|
74
|
+
# There is no way to move vars across nodes in treetop :(
|
75
|
+
self.source_file = source_file
|
76
|
+
|
77
|
+
sections = recursive_select(PluginSection)
|
78
|
+
|
79
|
+
section_map = {
|
80
|
+
:input => [],
|
81
|
+
:filter => [],
|
82
|
+
:output => []
|
83
|
+
}
|
84
|
+
|
85
|
+
sections.each do |section|
|
86
|
+
section_name = section.plugin_type.text_value.to_sym
|
87
|
+
section_expr = section.expr
|
88
|
+
raise "Unknown section name #{section_name}!" if ![:input, :output, :filter].include?(section_name)
|
89
|
+
::Array[section_expr].each do |se|
|
90
|
+
section_map[section_name].concat se
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
94
|
+
section_map.keys.each do |key|
|
95
|
+
section_map[key] = compose_for(key).call(empty_source_meta, *section_map[key])
|
96
|
+
end
|
97
|
+
|
98
|
+
section_map
|
99
|
+
end
|
100
|
+
end
|
101
|
+
|
102
|
+
class Comment < Node; end
|
103
|
+
class Whitespace < Node; end
|
104
|
+
|
105
|
+
class PluginSection < Node
|
106
|
+
def expr
|
107
|
+
recursive_select(Branch, Plugin).map(&:expr)
|
108
|
+
end
|
109
|
+
end
|
110
|
+
|
111
|
+
class Plugins < Node; end
|
112
|
+
class Plugin < Node
|
113
|
+
def expr
|
114
|
+
jdsl.iPlugin(source_meta, plugin_type_enum, self.plugin_name, self.expr_attributes)
|
115
|
+
end
|
116
|
+
|
117
|
+
def plugin_type_enum
|
118
|
+
case section_type
|
119
|
+
when "input"
|
120
|
+
Java::OrgLogstashConfigIr::PluginDefinition::Type::INPUT
|
121
|
+
when "codec"
|
122
|
+
Java::OrgLogstashConfigIr::PluginDefinition::Type::CODEC
|
123
|
+
when "filter"
|
124
|
+
Java::OrgLogstashConfigIr::PluginDefinition::Type::FILTER
|
125
|
+
when "output"
|
126
|
+
Java::OrgLogstashConfigIr::PluginDefinition::Type::OUTPUT
|
127
|
+
end
|
128
|
+
end
|
129
|
+
|
130
|
+
def plugin_name
|
131
|
+
return name.text_value
|
132
|
+
end
|
133
|
+
|
134
|
+
def expr_attributes
|
135
|
+
# Turn attributes into a hash map
|
136
|
+
self.attributes.recursive_select(Attribute).map(&:expr).map {|k,v|
|
137
|
+
if v.java_kind_of?(Java::OrgLogstashConfigIrExpression::ValueExpression)
|
138
|
+
[k, v.get]
|
139
|
+
else
|
140
|
+
[k,v]
|
141
|
+
end
|
142
|
+
}.reduce({}) do |hash,kv|
|
143
|
+
k,v = kv
|
144
|
+
hash[k] = v
|
145
|
+
hash
|
146
|
+
end
|
147
|
+
|
148
|
+
end
|
149
|
+
end
|
150
|
+
|
151
|
+
class Name < Node
|
152
|
+
def expr
|
153
|
+
return text_value
|
154
|
+
end
|
155
|
+
end
|
156
|
+
|
157
|
+
class Attribute < Node
|
158
|
+
def expr
|
159
|
+
[name.text_value, value.expr]
|
160
|
+
end
|
161
|
+
end
|
162
|
+
|
163
|
+
class RValue < Node; end
|
164
|
+
class Value < RValue; end
|
165
|
+
|
166
|
+
class Bareword < Value
|
167
|
+
def expr
|
168
|
+
jdsl.eValue(source_meta, text_value)
|
169
|
+
end
|
170
|
+
end
|
171
|
+
|
172
|
+
class String < Value
|
173
|
+
def expr
|
174
|
+
jdsl.e_value(source_meta, text_value[1...-1])
|
175
|
+
end
|
176
|
+
end
|
177
|
+
|
178
|
+
class RegExp < Value
|
179
|
+
def expr
|
180
|
+
# Strip the slashes off
|
181
|
+
jdsl.eRegex(text_value[1..-2])
|
182
|
+
end
|
183
|
+
end
|
184
|
+
|
185
|
+
class Number < Value
|
186
|
+
def expr
|
187
|
+
jdsl.eValue(source_meta, text_value.include?(".") ?
|
188
|
+
text_value.to_f :
|
189
|
+
text_value.to_i)
|
190
|
+
end
|
191
|
+
end
|
192
|
+
|
193
|
+
class Array < Value
|
194
|
+
def expr
|
195
|
+
jdsl.eValue(source_meta, recursive_select(Value).map(&:expr).map(&:get))
|
196
|
+
end
|
197
|
+
end
|
198
|
+
|
199
|
+
class Hash < Value
|
200
|
+
def validate!
|
201
|
+
duplicate_values = find_duplicate_keys
|
202
|
+
|
203
|
+
if duplicate_values.size > 0
|
204
|
+
raise ConfigurationError.new(
|
205
|
+
I18n.t("logstash.runner.configuration.invalid_plugin_settings_duplicate_keys",
|
206
|
+
:keys => duplicate_values.join(', '),
|
207
|
+
:line => input.line_of(interval.first),
|
208
|
+
:column => input.column_of(interval.first),
|
209
|
+
:byte => interval.first + 1,
|
210
|
+
:after => input[0..interval.first]
|
211
|
+
)
|
212
|
+
)
|
213
|
+
end
|
214
|
+
end
|
215
|
+
|
216
|
+
def find_duplicate_keys
|
217
|
+
values = recursive_select(HashEntry).collect { |hash_entry| hash_entry.name.text_value }
|
218
|
+
values.find_all { |v| values.count(v) > 1 }.uniq
|
219
|
+
end
|
220
|
+
|
221
|
+
def expr
|
222
|
+
validate!
|
223
|
+
::Hash[recursive_select(HashEntry).map(&:expr)]
|
224
|
+
end
|
225
|
+
end
|
226
|
+
|
227
|
+
class HashEntries < Node; end
|
228
|
+
|
229
|
+
class HashEntry < Node
|
230
|
+
def expr
|
231
|
+
return [name.expr.get, value.expr.get()]
|
232
|
+
end
|
233
|
+
end
|
234
|
+
|
235
|
+
class Branch < Node
|
236
|
+
def expr
|
237
|
+
# Build this stuff as s-expressions for convenience at first
|
238
|
+
# This will turn if/elsif/else blocks into nested if/else trees
|
239
|
+
|
240
|
+
exprs = []
|
241
|
+
else_stack = [] # For turning if / elsif / else into nested ifs
|
242
|
+
|
243
|
+
self.recursive_select(Plugin, If, Elsif, Else).each do |node|
|
244
|
+
if node.is_a?(If)
|
245
|
+
exprs << :if
|
246
|
+
exprs << expr_cond(node)
|
247
|
+
exprs << expr_body(node)
|
248
|
+
elsif node.is_a?(Elsif)
|
249
|
+
condition = expr_cond(node)
|
250
|
+
body = expr_body(node)
|
251
|
+
else_stack << [:if, condition, body]
|
252
|
+
elsif node.is_a?(Else)
|
253
|
+
body = expr_body(node)
|
254
|
+
if else_stack.size >= 1
|
255
|
+
else_stack.last << body
|
256
|
+
else
|
257
|
+
exprs << body
|
258
|
+
end
|
259
|
+
end
|
260
|
+
end
|
261
|
+
|
262
|
+
else_stack.reverse.each_cons(2) do |cons|
|
263
|
+
later,earlier = cons
|
264
|
+
earlier << later
|
265
|
+
end
|
266
|
+
exprs << else_stack.first
|
267
|
+
|
268
|
+
# Then convert to the imperative java IR
|
269
|
+
javaify_sexpr(exprs)
|
270
|
+
end
|
271
|
+
|
272
|
+
def javaify_sexpr(sexpr)
|
273
|
+
return nil if sexpr.nil?
|
274
|
+
|
275
|
+
head, tail = sexpr.first
|
276
|
+
tail = sexpr[1..-1]
|
277
|
+
|
278
|
+
if head == :if
|
279
|
+
condition, t_branch, f_branch = tail
|
280
|
+
|
281
|
+
java_t_branch = t_branch && javaify_sexpr(t_branch)
|
282
|
+
java_f_branch = f_branch && javaify_sexpr(f_branch)
|
283
|
+
|
284
|
+
if java_t_branch || java_f_branch
|
285
|
+
jdsl.iIf(condition, java_t_branch || jdsl.noop, java_f_branch || jdsl.noop)
|
286
|
+
else
|
287
|
+
jdsl.noop()
|
288
|
+
end
|
289
|
+
elsif head == :compose
|
290
|
+
tail && tail.size > 0 ? compose(*tail) : jdsl.noop
|
291
|
+
else
|
292
|
+
raise "Unknown expression #{sexpr}!"
|
293
|
+
end
|
294
|
+
end
|
295
|
+
|
296
|
+
def expr_cond(node)
|
297
|
+
node.elements.find {|e| e.is_a?(Condition)}.expr
|
298
|
+
end
|
299
|
+
|
300
|
+
def expr_body(node)
|
301
|
+
[:compose, *node.recursive_select(Plugin, Branch).map(&:expr)]
|
302
|
+
end
|
303
|
+
end
|
304
|
+
|
305
|
+
# Branch covers all these
|
306
|
+
class BranchEntry < Node; end
|
307
|
+
class If < BranchEntry; end
|
308
|
+
class Elsif < BranchEntry; end
|
309
|
+
class Else < BranchEntry; end
|
310
|
+
|
311
|
+
class Condition < Node
|
312
|
+
include Helpers
|
313
|
+
|
314
|
+
def expr
|
315
|
+
first_element = elements.first
|
316
|
+
rest_elements = elements.size > 1 ? elements[1].recursive_select(BooleanOperator, Expression, SelectorElement) : []
|
317
|
+
|
318
|
+
all_elements = [first_element, *rest_elements]
|
319
|
+
|
320
|
+
if all_elements.size == 1
|
321
|
+
elem = all_elements.first
|
322
|
+
if elem.is_a?(Selector)
|
323
|
+
eventValue = elem.recursive_select(SelectorElement).first.expr
|
324
|
+
jdsl.eTruthy(source_meta, eventValue)
|
325
|
+
elsif elem.is_a?(RegexpExpression)
|
326
|
+
elem.expr
|
327
|
+
else
|
328
|
+
join_conditions(all_elements)
|
329
|
+
end
|
330
|
+
else
|
331
|
+
join_conditions(all_elements)
|
332
|
+
end
|
333
|
+
end
|
334
|
+
|
335
|
+
def precedence(op)
|
336
|
+
# Believe this is right for logstash?
|
337
|
+
case op
|
338
|
+
when AND_METHOD
|
339
|
+
2
|
340
|
+
when OR_METHOD
|
341
|
+
1
|
342
|
+
else
|
343
|
+
raise ArgumentError, "Unexpected operator #{op}"
|
344
|
+
end
|
345
|
+
end
|
346
|
+
|
347
|
+
# Converts an sexpr of :and or :or to the java imperative IR
|
348
|
+
def jconvert(sexpr)
|
349
|
+
raise "jconvert cannot handle nils!" if sexpr.nil?
|
350
|
+
|
351
|
+
if sexpr.java_kind_of?(Java::OrgLogstashConfigIrExpression::Expression)
|
352
|
+
return sexpr
|
353
|
+
end
|
354
|
+
|
355
|
+
op, left, right = sexpr
|
356
|
+
|
357
|
+
left_c = jconvert(left)
|
358
|
+
right_c = jconvert(right)
|
359
|
+
|
360
|
+
case op
|
361
|
+
when :and
|
362
|
+
return jdsl.eAnd(left, right);
|
363
|
+
when :or
|
364
|
+
return jdsl.eOr(left, right);
|
365
|
+
else
|
366
|
+
raise "Unknown op #{jop}"
|
367
|
+
end
|
368
|
+
end
|
369
|
+
|
370
|
+
def join_conditions(all_elements)
|
371
|
+
# Use Dijkstra's shunting yard algorithm
|
372
|
+
out = []
|
373
|
+
operators = []
|
374
|
+
|
375
|
+
all_elements.each do |e|
|
376
|
+
e_exp = e.expr
|
377
|
+
|
378
|
+
if e.is_a?(BooleanOperator)
|
379
|
+
if operators.last && precedence(operators.last) > precedence(e_exp)
|
380
|
+
out << operators.pop
|
381
|
+
end
|
382
|
+
operators << e_exp
|
383
|
+
else
|
384
|
+
out << e_exp
|
385
|
+
end
|
386
|
+
end
|
387
|
+
operators.reverse.each {|o| out << o}
|
388
|
+
|
389
|
+
stack = []
|
390
|
+
expr = []
|
391
|
+
out.each do |e|
|
392
|
+
if e.is_a?(Symbol)
|
393
|
+
rval, lval = stack.pop, stack.pop
|
394
|
+
stack << jconvert([e, lval, rval])
|
395
|
+
elsif e.nil?
|
396
|
+
raise "Nil expr encountered! This should not happen!"
|
397
|
+
else
|
398
|
+
stack << e
|
399
|
+
end
|
400
|
+
end
|
401
|
+
|
402
|
+
stack_to_expr(stack)
|
403
|
+
end
|
404
|
+
|
405
|
+
def stack_to_expr(stack)
|
406
|
+
raise "Got an empty stack! This should not happen!" if stack.empty?
|
407
|
+
stack = stack.reverse # We need to work the stack in reverse order
|
408
|
+
|
409
|
+
working_stack = []
|
410
|
+
while elem = stack.pop
|
411
|
+
if elem.is_a?(::Method)
|
412
|
+
right, left = working_stack.pop, working_stack.pop
|
413
|
+
working_stack << elem.call(left, right)
|
414
|
+
else
|
415
|
+
working_stack << elem
|
416
|
+
end
|
417
|
+
end
|
418
|
+
|
419
|
+
raise "Invariant violated! Stack size > 1" if working_stack.size > 1
|
420
|
+
|
421
|
+
working_stack.first
|
422
|
+
end
|
423
|
+
end
|
424
|
+
|
425
|
+
module Expression
|
426
|
+
def expr
|
427
|
+
# If we have a more specific type (like a Negative expression) use that
|
428
|
+
if defined?(super)
|
429
|
+
return super
|
430
|
+
end
|
431
|
+
|
432
|
+
exprs = self.recursive_select(Condition, Selector).map(&:expr)
|
433
|
+
|
434
|
+
raise "Exprs should only have one part!" if exprs.size != 1
|
435
|
+
exprs.first
|
436
|
+
end
|
437
|
+
end
|
438
|
+
|
439
|
+
module NegativeExpression
|
440
|
+
include Helpers
|
441
|
+
|
442
|
+
def expr
|
443
|
+
exprs = self.recursive_select(Condition, Selector).map(&:expr)
|
444
|
+
raise "Negative exprs should only have one part!" if exprs.size != 1
|
445
|
+
jdsl.eNot(source_meta, exprs.first)
|
446
|
+
end
|
447
|
+
end
|
448
|
+
|
449
|
+
module ComparisonExpression
|
450
|
+
include Helpers
|
451
|
+
|
452
|
+
def expr
|
453
|
+
lval, comparison_method, rval = self.recursive_select(Selector, Expression, ComparisonOperator, Number, String).map(&:expr)
|
454
|
+
comparison_method.call(source_meta, lval, rval)
|
455
|
+
end
|
456
|
+
end
|
457
|
+
|
458
|
+
module InExpression
|
459
|
+
include Helpers
|
460
|
+
|
461
|
+
def expr
|
462
|
+
item, list = recursive_select(RValue)
|
463
|
+
jdsl.eIn(source_meta, item.expr, list.expr)
|
464
|
+
end
|
465
|
+
end
|
466
|
+
|
467
|
+
module NotInExpression
|
468
|
+
include Helpers
|
469
|
+
|
470
|
+
def expr
|
471
|
+
item, list = recursive_select(RValue)
|
472
|
+
jdsl.eNot(source_meta, jdsl.eIn(item.expr, list.expr))
|
473
|
+
end
|
474
|
+
end
|
475
|
+
|
476
|
+
# Not implemented because no one uses this
|
477
|
+
class MethodCall < Node; end
|
478
|
+
|
479
|
+
class RegexpExpression < Node
|
480
|
+
def expr
|
481
|
+
selector, operator_method, regexp = recursive_select(
|
482
|
+
Selector,
|
483
|
+
LogStash::Compiler::LSCL::AST::RegExpOperator,
|
484
|
+
LogStash::Compiler::LSCL::AST::RegExp,
|
485
|
+
LogStash::Compiler::LSCL::AST::String # Strings work as rvalues! :p
|
486
|
+
).map(&:expr)
|
487
|
+
|
488
|
+
# Handle string rvalues, they just get turned into regexps
|
489
|
+
# Maybe we really shouldn't handle these anymore...
|
490
|
+
if regexp.class == org.logstash.config.ir.expression.ValueExpression
|
491
|
+
regexp = jdsl.eRegex(regexp.get)
|
492
|
+
end
|
493
|
+
|
494
|
+
raise "Expected a selector in #{text_value}!" unless selector
|
495
|
+
raise "Expected a regexp in #{text_value}!" unless regexp
|
496
|
+
|
497
|
+
operator_method.call(source_meta, selector, regexp);
|
498
|
+
end
|
499
|
+
end
|
500
|
+
|
501
|
+
module BranchOrPlugin; end
|
502
|
+
|
503
|
+
module ComparisonOperator
|
504
|
+
include Helpers
|
505
|
+
|
506
|
+
def expr
|
507
|
+
case self.text_value
|
508
|
+
when "=="
|
509
|
+
jdsl.method(:eEq)
|
510
|
+
when "!="
|
511
|
+
jdsl.method(:eNeq)
|
512
|
+
when ">"
|
513
|
+
jdsl.method(:eGt)
|
514
|
+
when "<"
|
515
|
+
jdsl.method(:eLt)
|
516
|
+
when ">="
|
517
|
+
jdsl.method(:eGte)
|
518
|
+
when "<="
|
519
|
+
jdsl.method(:eLte)
|
520
|
+
else
|
521
|
+
raise "Unknown operator #{self.text_value}"
|
522
|
+
end
|
523
|
+
end
|
524
|
+
end
|
525
|
+
|
526
|
+
module RegExpOperator
|
527
|
+
include Helpers
|
528
|
+
|
529
|
+
def expr
|
530
|
+
if self.text_value == '!~'
|
531
|
+
jdsl.method(:eRegexNeq)
|
532
|
+
elsif self.text_value == '=~'
|
533
|
+
jdsl.method(:eRegexEq)
|
534
|
+
else
|
535
|
+
raise "Unknown regex operator #{self.text_value}"
|
536
|
+
end
|
537
|
+
end
|
538
|
+
end
|
539
|
+
|
540
|
+
module BooleanOperator
|
541
|
+
include Helpers
|
542
|
+
|
543
|
+
def expr
|
544
|
+
case self.text_value
|
545
|
+
when "and"
|
546
|
+
AND_METHOD
|
547
|
+
when "or"
|
548
|
+
OR_METHOD
|
549
|
+
else
|
550
|
+
raise "Unknown operator #{self.text_value}"
|
551
|
+
end
|
552
|
+
end
|
553
|
+
end
|
554
|
+
|
555
|
+
class Selector < RValue
|
556
|
+
def expr
|
557
|
+
jdsl.eEventValue(source_meta, text_value)
|
558
|
+
end
|
559
|
+
end
|
560
|
+
|
561
|
+
class SelectorElement < Node;
|
562
|
+
def expr
|
563
|
+
jdsl.eEventValue(source_meta, text_value)
|
564
|
+
end
|
565
|
+
end
|
566
|
+
end; end; end; end; end;
|