fluent-plugin-prometheus 1.5.0 → 1.7.2

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: de38cb79041db3b0a78ead61eee23d58b568b71292886b19db9ca30ad38ad00b
4
- data.tar.gz: a1867c481cd9527cc4ada9125a266a2455aacca7868c4f00d8489926c845a665
3
+ metadata.gz: b8cdb0af95b316cebf86dba1a0beb649d51dca8ebcc2a9148c3a54341510037a
4
+ data.tar.gz: 348dc37b2707ad5d272a2ad3ea8aba4f2188084fa359bdb1cacd4081467c1227
5
5
  SHA512:
6
- metadata.gz: eb397416c207fcc7d6111aaa9346bca990e5c44764b25072a7a0c68ef32748e767ba04637ec9576be25273caf2345303e6ab7bacbbb261e572cd3288b01475ff
7
- data.tar.gz: 3e4a0484386035bf791b49f39d567b52675b97c5ccf7738edaeeb90e23c4adfce852ee1f5a5c69ee0905bbc33f57358e0322761dbbdf86b559d10524f7c21abf
6
+ metadata.gz: 0a014a3ff64dd13721e3c6c0a5b1bc9f7cccf7523cc1040944eeb40d74b9e8c45fa89e47fbf68f83ae968ef36bb19ef461be7cf346b407262e7457d8a38b6bc6
7
+ data.tar.gz: 395ef53fcfd6d0c6619960dc69b249a4ebf44230c9348c5d688c901980dbcd1aba95f826003fd1a9fa37f22e15d4383b1f5757c6d49ebe1dcd524aca730044d3
@@ -1,9 +1,9 @@
1
1
  language: ruby
2
2
 
3
3
  rvm:
4
- - "2.3.6"
5
- - "2.4.3"
6
- - "2.5.0"
4
+ - "2.4.7"
5
+ - "2.5"
6
+ - "2.6"
7
7
 
8
8
  gemfile:
9
9
  - Gemfile
data/README.md CHANGED
@@ -58,18 +58,25 @@ More configuration parameters:
58
58
  - `bind`: binding interface (default: '0.0.0.0')
59
59
  - `port`: listen port (default: 24231)
60
60
  - `metrics_path`: metrics HTTP endpoint (default: /metrics)
61
+ - `aggregated_metrics_path`: metrics HTTP endpoint (default: /aggregated_metrics)
61
62
 
62
63
  When using multiple workers, each worker binds to port + `fluent_worker_id`.
64
+ To scrape metrics from all workers at once, you can access http://localhost:24231/aggregated_metrics.
63
65
 
64
66
  ### prometheus_monitor input plugin
65
67
 
66
68
  This plugin collects internal metrics in Fluentd. The metrics are similar to/part of [monitor_agent](https://docs.fluentd.org/input/monitor_agent).
67
69
 
68
- Current exposed metrics:
69
70
 
70
- - `buffer_queue_length` of each BufferedOutput plugins
71
- - `buffer_total_queued_size` of each BufferedOutput plugins
72
- - `retry_count` of each BufferedOutput plugins
71
+ #### Exposed metrics
72
+
73
+ - `fluentd_status_buffer_queue_length`
74
+ - `fluentd_status_buffer_total_queued_size`
75
+ - `fluentd_status_retry_count`
76
+ - `fluentd_status_buffer_newest_timekey` from fluentd v1.4.2
77
+ - `fluentd_status_buffer_oldest_timekey` from fluentd v1.4.2
78
+
79
+ #### Configuration
73
80
 
74
81
  With following configuration, those metrics are collected.
75
82
 
@@ -86,28 +93,35 @@ More configuration parameters:
86
93
 
87
94
  ### prometheus_output_monitor input plugin
88
95
 
89
- **experimental**
90
-
91
96
  This plugin collects internal metrics for output plugin in Fluentd. This is similar to `prometheus_monitor` plugin, but specialized for output plugin. There are Many metrics `prometheus_monitor` does not include, such as `num_errors`, `retry_wait` and so on.
92
97
 
93
- Current exposed metrics:
98
+ #### Exposed metrics
99
+
100
+ Metrics for output
94
101
 
95
- - `fluentd_output_status_buffer_queue_length`
96
- - `fluentd_output_status_buffer_total_bytes`
97
102
  - `fluentd_output_status_retry_count`
98
103
  - `fluentd_output_status_num_errors`
99
104
  - `fluentd_output_status_emit_count`
100
- - `fluentd_output_status_flush_time_count`
101
- - `fluentd_output_status_slow_flush_count`
102
105
  - `fluentd_output_status_retry_wait`
103
106
  - current retry_wait computed from last retry time and next retry time
104
107
  - `fluentd_output_status_emit_records`
105
- - only for v0.14
106
108
  - `fluentd_output_status_write_count`
107
- - only for v0.14
108
109
  - `fluentd_output_status_rollback_count`
109
- - only for v0.14
110
+ - `fluentd_output_status_flush_time_count` from fluentd v1.6.0
111
+ - `fluentd_output_status_slow_flush_count` from fluentd v1.6.0
112
+
113
+ Metrics for buffer
114
+
115
+ - `fluentd_output_status_buffer_total_bytes`
116
+ - `fluentd_output_status_buffer_stage_length` from fluentd v1.6.0
117
+ - `fluentd_output_status_buffer_stage_byte_size` from fluentd v1.6.0
118
+ - `fluentd_output_status_buffer_queue_length`
119
+ - `fluentd_output_status_buffer_queue_byte_size` from fluentd v1.6.0
120
+ - `fluentd_output_status_buffer_newest_timekey` from fluentd v1.6.0
121
+ - `fluentd_output_status_buffer_oldest_timekey` from fluentd v1.6.0
122
+ - `fluentd_output_status_buffer_available_space_ratio` from fluentd v1.6.0
110
123
 
124
+ #### Configuration
111
125
 
112
126
  With following configuration, those metrics are collected.
113
127
 
@@ -124,13 +138,11 @@ More configuration parameters:
124
138
 
125
139
  ### prometheus_tail_monitor input plugin
126
140
 
127
- **experimental**
128
-
129
141
  This plugin collects internal metrics for in_tail plugin in Fluentd. in_tail plugin holds internal state for files that the plugin is watching. The state is sometimes important to monitor plugins work correctly.
130
142
 
131
143
  This plugin uses internal class of Fluentd, so it's easy to break.
132
144
 
133
- Current exposed metrics:
145
+ #### Exposed metrics
134
146
 
135
147
  - `fluentd_tail_file_position`
136
148
  - Current bytes which plugin reads from the file
@@ -143,6 +155,8 @@ Default labels:
143
155
  - `type`: plugin name. `in_tail` only for now.
144
156
  - `path`: file path
145
157
 
158
+ #### Configuration
159
+
146
160
  With following configuration, those metrics are collected.
147
161
 
148
162
  ```
@@ -355,7 +369,13 @@ Reserved placeholders are:
355
369
  - `${worker_id}`: fluent worker id
356
370
  - `${tag}`: tag name
357
371
  - only available in Prometheus output/filter plugin
358
-
372
+ - `${tag_parts[N]}` refers to the Nth part of the tag.
373
+ - only available in Prometheus output/filter plugin
374
+ - `${tag_prefix[N]}` refers to the [0..N] part of the tag.
375
+ - only available in Prometheus output/filter plugin
376
+ - `${tag_suffix[N]}` refers to the [`tagsize`-1-N..] part of the tag.
377
+ - where `tagsize` is the size of tag which is splitted with `.` (when tag is `1.2.3`, then `tagsize` is 3)
378
+ - only available in Prometheus output/filter plugin
359
379
 
360
380
  ### top-level labels and labels inside metric
361
381
 
@@ -1,6 +1,6 @@
1
1
  Gem::Specification.new do |spec|
2
2
  spec.name = "fluent-plugin-prometheus"
3
- spec.version = "1.5.0"
3
+ spec.version = "1.7.2"
4
4
  spec.authors = ["Masahiro Sano"]
5
5
  spec.email = ["sabottenda@gmail.com"]
6
6
  spec.summary = %q{A fluent plugin that collects metrics and exposes for Prometheus.}
@@ -14,7 +14,7 @@ Gem::Specification.new do |spec|
14
14
  spec.require_paths = ["lib"]
15
15
 
16
16
  spec.add_dependency "fluentd", ">= 0.14.20", "< 2"
17
- spec.add_dependency "prometheus-client"
17
+ spec.add_dependency "prometheus-client", "< 0.10"
18
18
  spec.add_development_dependency "bundler"
19
19
  spec.add_development_dependency "rake"
20
20
  spec.add_development_dependency "rspec"
@@ -4,6 +4,7 @@ require 'fluent/plugin/filter'
4
4
  module Fluent::Plugin
5
5
  class PrometheusFilter < Fluent::Plugin::Filter
6
6
  Fluent::Plugin.register_filter('prometheus', self)
7
+ include Fluent::Plugin::PrometheusLabelParser
7
8
  include Fluent::Plugin::Prometheus
8
9
 
9
10
  def initialize
@@ -17,13 +18,13 @@ module Fluent::Plugin
17
18
 
18
19
  def configure(conf)
19
20
  super
20
- labels = Fluent::Plugin::Prometheus.parse_labels_elements(conf)
21
+ labels = parse_labels_elements(conf)
21
22
  @metrics = Fluent::Plugin::Prometheus.parse_metrics_elements(conf, @registry, labels)
22
23
  end
23
24
 
24
- def filter_stream(tag, es)
25
- instrument(tag, es, @metrics)
26
- es
25
+ def filter(tag, time, record)
26
+ instrument_single(tag, time, record, @metrics)
27
+ record
27
28
  end
28
29
  end
29
30
  end
@@ -1,5 +1,7 @@
1
1
  require 'fluent/plugin/input'
2
2
  require 'fluent/plugin/prometheus'
3
+ require 'fluent/plugin/prometheus_metrics'
4
+ require 'net/http'
3
5
  require 'webrick'
4
6
 
5
7
  module Fluent::Plugin
@@ -11,6 +13,7 @@ module Fluent::Plugin
11
13
  config_param :bind, :string, default: '0.0.0.0'
12
14
  config_param :port, :integer, default: 24231
13
15
  config_param :metrics_path, :string, default: '/metrics'
16
+ config_param :aggregated_metrics_path, :string, default: '/aggregated_metrics'
14
17
 
15
18
  desc 'Enable ssl configuration for the server'
16
19
  config_section :ssl, required: false, multi: false do
@@ -31,6 +34,10 @@ module Fluent::Plugin
31
34
 
32
35
  attr_reader :registry
33
36
 
37
+ attr_reader :num_workers
38
+ attr_reader :base_port
39
+ attr_reader :metrics_path
40
+
34
41
  def initialize
35
42
  super
36
43
  @registry = ::Prometheus::Client.registry
@@ -38,6 +45,18 @@ module Fluent::Plugin
38
45
 
39
46
  def configure(conf)
40
47
  super
48
+
49
+ # Get how many workers we have
50
+ sysconf = if self.respond_to?(:owner) && owner.respond_to?(:system_config)
51
+ owner.system_config
52
+ elsif self.respond_to?(:system_config)
53
+ self.system_config
54
+ else
55
+ nil
56
+ end
57
+ @num_workers = sysconf && sysconf.workers ? sysconf.workers : 1
58
+
59
+ @base_port = @port
41
60
  @port += fluentd_worker_id
42
61
  end
43
62
 
@@ -82,6 +101,7 @@ module Fluent::Plugin
82
101
 
83
102
  @server = WEBrick::HTTPServer.new(config)
84
103
  @server.mount(@metrics_path, MonitorServlet, self)
104
+ @server.mount(@aggregated_metrics_path, MonitorServletAll, self)
85
105
  thread_create(:in_prometheus) do
86
106
  @server.start
87
107
  end
@@ -110,5 +130,35 @@ module Fluent::Plugin
110
130
  res.body = $!.to_s
111
131
  end
112
132
  end
133
+
134
+ class MonitorServletAll < WEBrick::HTTPServlet::AbstractServlet
135
+ def initialize(server, prometheus)
136
+ @prometheus = prometheus
137
+ end
138
+
139
+ def do_GET(req, res)
140
+ res.status = 200
141
+ res['Content-Type'] = ::Prometheus::Client::Formats::Text::CONTENT_TYPE
142
+
143
+ full_result = PromMetricsAggregator.new
144
+ fluent_server_ip = @prometheus.bind == '0.0.0.0' ? '127.0.0.1' : @prometheus.bind
145
+ current_worker = 0
146
+ while current_worker < @prometheus.num_workers
147
+ Net::HTTP.start(fluent_server_ip, @prometheus.base_port + current_worker) do |http|
148
+ req = Net::HTTP::Get.new(@prometheus.metrics_path)
149
+ result = http.request(req)
150
+ if result.is_a?(Net::HTTPSuccess)
151
+ full_result.add_metrics(result.body)
152
+ end
153
+ end
154
+ current_worker += 1
155
+ end
156
+ res.body = full_result.get_metrics
157
+ rescue
158
+ res.status = 500
159
+ res['Content-Type'] = 'text/plain'
160
+ res.body = $!.to_s
161
+ end
162
+ end
113
163
  end
114
164
  end
@@ -5,6 +5,7 @@ require 'fluent/plugin/prometheus'
5
5
  module Fluent::Plugin
6
6
  class PrometheusMonitorInput < Fluent::Plugin::Input
7
7
  Fluent::Plugin.register_input('prometheus_monitor', self)
8
+ include Fluent::Plugin::PrometheusLabelParser
8
9
 
9
10
  helpers :timer
10
11
 
@@ -23,14 +24,14 @@ module Fluent::Plugin
23
24
  def configure(conf)
24
25
  super
25
26
  hostname = Socket.gethostname
26
- expander = Fluent::Plugin::Prometheus.placeholder_expander(log)
27
- placeholders = expander.prepare_placeholders({'hostname' => hostname, 'worker_id' => fluentd_worker_id})
28
- @base_labels = Fluent::Plugin::Prometheus.parse_labels_elements(conf)
27
+ expander_builder = Fluent::Plugin::Prometheus.placeholder_expander(log)
28
+ expander = expander_builder.build({ 'hostname' => hostname, 'worker_id' => fluentd_worker_id })
29
+ @base_labels = parse_labels_elements(conf)
29
30
  @base_labels.each do |key, value|
30
31
  unless value.is_a?(String)
31
32
  raise Fluent::ConfigError, "record accessor syntax is not available in prometheus_monitor"
32
33
  end
33
- @base_labels[key] = expander.expand(value, placeholders)
34
+ @base_labels[key] = expander.expand(value)
34
35
  end
35
36
 
36
37
  if defined?(Fluent::Plugin) && defined?(Fluent::Plugin::MonitorAgentInput)
@@ -45,6 +46,12 @@ module Fluent::Plugin
45
46
  def start
46
47
  super
47
48
 
49
+ @buffer_newest_timekey = @registry.gauge(
50
+ :fluentd_status_buffer_newest_timekey,
51
+ 'Newest timekey in buffer.')
52
+ @buffer_oldest_timekey = @registry.gauge(
53
+ :fluentd_status_buffer_oldest_timekey,
54
+ 'Oldest timekey in buffer.')
48
55
  buffer_queue_length = @registry.gauge(
49
56
  :fluentd_status_buffer_queue_length,
50
57
  'Current buffer queue length.')
@@ -65,11 +72,19 @@ module Fluent::Plugin
65
72
 
66
73
  def update_monitor_info
67
74
  @monitor_agent.plugins_info_all.each do |info|
75
+ label = labels(info)
76
+
68
77
  @monitor_info.each do |name, metric|
69
78
  if info[name]
70
- metric.set(labels(info), info[name])
79
+ metric.set(label, info[name])
71
80
  end
72
81
  end
82
+
83
+ timekeys = info["buffer_timekeys"]
84
+ if timekeys && !timekeys.empty?
85
+ @buffer_newest_timekey.set(label, timekeys.max)
86
+ @buffer_oldest_timekey.set(label, timekeys.min)
87
+ end
73
88
  end
74
89
  end
75
90
 
@@ -5,6 +5,7 @@ require 'fluent/plugin/prometheus'
5
5
  module Fluent::Plugin
6
6
  class PrometheusOutputMonitorInput < Fluent::Input
7
7
  Fluent::Plugin.register_input('prometheus_output_monitor', self)
8
+ include Fluent::Plugin::PrometheusLabelParser
8
9
 
9
10
  helpers :timer
10
11
 
@@ -42,14 +43,14 @@ module Fluent::Plugin
42
43
  def configure(conf)
43
44
  super
44
45
  hostname = Socket.gethostname
45
- expander = Fluent::Plugin::Prometheus.placeholder_expander(log)
46
- placeholders = expander.prepare_placeholders({'hostname' => hostname, 'worker_id' => fluentd_worker_id})
47
- @base_labels = Fluent::Plugin::Prometheus.parse_labels_elements(conf)
46
+ expander_builder = Fluent::Plugin::Prometheus.placeholder_expander(log)
47
+ expander = expander_builder.build({ 'hostname' => hostname, 'worker_id' => fluentd_worker_id })
48
+ @base_labels = parse_labels_elements(conf)
48
49
  @base_labels.each do |key, value|
49
50
  unless value.is_a?(String)
50
51
  raise Fluent::ConfigError, "record accessor syntax is not available in prometheus_output_monitor"
51
52
  end
52
- @base_labels[key] = expander.expand(value, placeholders)
53
+ @base_labels[key] = expander.expand(value)
53
54
  end
54
55
 
55
56
  if defined?(Fluent::Plugin) && defined?(Fluent::Plugin::MonitorAgentInput)
@@ -64,12 +65,33 @@ module Fluent::Plugin
64
65
  super
65
66
 
66
67
  @metrics = {
67
- buffer_queue_length: @registry.gauge(
68
- :fluentd_output_status_buffer_queue_length,
69
- 'Current buffer queue length.'),
68
+ # Buffer metrics
70
69
  buffer_total_queued_size: @registry.gauge(
71
70
  :fluentd_output_status_buffer_total_bytes,
72
- 'Current total size of queued buffers.'),
71
+ 'Current total size of stage and queue buffers.'),
72
+ buffer_stage_length: @registry.gauge(
73
+ :fluentd_output_status_buffer_stage_length,
74
+ 'Current length of stage buffers.'),
75
+ buffer_stage_byte_size: @registry.gauge(
76
+ :fluentd_output_status_buffer_stage_byte_size,
77
+ 'Current total size of stage buffers.'),
78
+ buffer_queue_length: @registry.gauge(
79
+ :fluentd_output_status_buffer_queue_length,
80
+ 'Current length of queue buffers.'),
81
+ buffer_queue_byte_size: @registry.gauge(
82
+ :fluentd_output_status_queue_byte_size,
83
+ 'Current total size of queue buffers.'),
84
+ buffer_available_buffer_space_ratios: @registry.gauge(
85
+ :fluentd_output_status_buffer_available_space_ratio,
86
+ 'Ratio of available space in buffer.'),
87
+ buffer_newest_timekey: @registry.gauge(
88
+ :fluentd_output_status_buffer_newest_timekey,
89
+ 'Newest timekey in buffer.'),
90
+ buffer_oldest_timekey: @registry.gauge(
91
+ :fluentd_output_status_buffer_oldest_timekey,
92
+ 'Oldest timekey in buffer.'),
93
+
94
+ # Output metrics
73
95
  retry_counts: @registry.gauge(
74
96
  :fluentd_output_status_retry_count,
75
97
  'Current retry counts.'),
@@ -112,8 +134,17 @@ module Fluent::Plugin
112
134
  }
113
135
 
114
136
  monitor_info = {
115
- 'buffer_queue_length' => @metrics[:buffer_queue_length],
137
+ # buffer metrics
116
138
  'buffer_total_queued_size' => @metrics[:buffer_total_queued_size],
139
+ 'buffer_stage_length' => @metrics[:buffer_stage_length],
140
+ 'buffer_stage_byte_size' => @metrics[:buffer_stage_byte_size],
141
+ 'buffer_queue_length' => @metrics[:buffer_queue_length],
142
+ 'buffer_queue_byte_size' => @metrics[:buffer_queue_byte_size],
143
+ 'buffer_available_buffer_space_ratios' => @metrics[:buffer_available_buffer_space_ratios],
144
+ 'buffer_newest_timekey' => @metrics[:buffer_newest_timekey],
145
+ 'buffer_oldest_timekey' => @metrics[:buffer_oldest_timekey],
146
+
147
+ # output metrics
117
148
  'retry_count' => @metrics[:retry_counts],
118
149
  }
119
150
  instance_vars_info = {
@@ -5,6 +5,7 @@ require 'fluent/plugin/prometheus'
5
5
  module Fluent::Plugin
6
6
  class PrometheusTailMonitorInput < Fluent::Plugin::Input
7
7
  Fluent::Plugin.register_input('prometheus_tail_monitor', self)
8
+ include Fluent::Plugin::PrometheusLabelParser
8
9
 
9
10
  helpers :timer
10
11
 
@@ -27,14 +28,14 @@ module Fluent::Plugin
27
28
  def configure(conf)
28
29
  super
29
30
  hostname = Socket.gethostname
30
- expander = Fluent::Plugin::Prometheus.placeholder_expander(log)
31
- placeholders = expander.prepare_placeholders({'hostname' => hostname, 'worker_id' => fluentd_worker_id})
32
- @base_labels = Fluent::Plugin::Prometheus.parse_labels_elements(conf)
31
+ expander_builder = Fluent::Plugin::Prometheus.placeholder_expander(log)
32
+ expander = expander_builder.prepare_placeholders({ 'hostname' => hostname, 'worker_id' => fluentd_worker_id })
33
+ @base_labels = parse_labels_elements(conf)
33
34
  @base_labels.each do |key, value|
34
35
  unless value.is_a?(String)
35
36
  raise Fluent::ConfigError, "record accessor syntax is not available in prometheus_tail_monitor"
36
37
  end
37
- @base_labels[key] = expander.expand(value, placeholders)
38
+ @base_labels[key] = expander.expand(value)
38
39
  end
39
40
 
40
41
  if defined?(Fluent::Plugin) && defined?(Fluent::Plugin::MonitorAgentInput)
@@ -4,6 +4,7 @@ require 'fluent/plugin/prometheus'
4
4
  module Fluent::Plugin
5
5
  class PrometheusOutput < Fluent::Plugin::Output
6
6
  Fluent::Plugin.register_output('prometheus', self)
7
+ include Fluent::Plugin::PrometheusLabelParser
7
8
  include Fluent::Plugin::Prometheus
8
9
 
9
10
  def initialize
@@ -17,7 +18,7 @@ module Fluent::Plugin
17
18
 
18
19
  def configure(conf)
19
20
  super
20
- labels = Fluent::Plugin::Prometheus.parse_labels_elements(conf)
21
+ labels = parse_labels_elements(conf)
21
22
  @metrics = Fluent::Plugin::Prometheus.parse_metrics_elements(conf, @registry, labels)
22
23
  end
23
24