anschel 0.6.1 → 0.6.2

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 8f81ae5fdcf71f580680520067255911285629aa
4
- data.tar.gz: 68ab5e077fa13d9d4e142fe798f222912dce5f6a
3
+ metadata.gz: 70986c1daf98761ecae7d688a9cac9dca77d5245
4
+ data.tar.gz: 423be3728f6d0b12816965df20cb48c3ccc77198
5
5
  SHA512:
6
- metadata.gz: 0179da5dc7e53fc18e3c490f4e49f521e210184a0df80a5d834052237b2f476f4b99fbcad40bd390f1f318a9af9559f9609117098d8e7cf02d35829a560d2aab
7
- data.tar.gz: 95309336805570a5e7cd50dfa1d47e43677caa3a72f78ea1a8e8b7fadc68146c26e00feb73706b0a2620868f73777af78b94c4b6368eeb8f4bc1c8e30c74d88f
6
+ metadata.gz: 82ff4b34d365f33a3a39cc3bac477cac4c8c449ebfadb8317a15a92372bc6af858ee2715afd6329d976fa70e2f07e7c4cff14f0ccf6a14a61cefb30d1a748052
7
+ data.tar.gz: db692abab264dc1ad1ccee814560071e398d81430717e2b61d76469e83754128bf0277820eadc55231e131719271d79851aa4bff51902bf7372ca40f08c1c2a2
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.6.1
1
+ 0.6.2
@@ -7,7 +7,6 @@
7
7
  module Anschel
8
8
  class Filter
9
9
  def convert conf, log
10
- log.debug event: 'compile-filter', filter: 'convert', conf: conf
11
10
  field = conf.delete :field
12
11
  type = conf.delete :type
13
12
 
@@ -22,7 +21,7 @@ module Anschel
22
21
  'string' => :to_s
23
22
  }
24
23
 
25
- log.debug event: 'compiled-filter', filter: 'convert', \
24
+ log.trace event: 'filter-compiled', kind: 'convert', \
26
25
  field: field, type: type
27
26
 
28
27
  lambda do |event|
@@ -19,7 +19,7 @@ module Anschel
19
19
  field = field.to_sym
20
20
 
21
21
 
22
- log.debug event: 'compiled-filter', filter: 'gsub', \
22
+ log.trace event: 'filter-compiled', kind: 'gsub', \
23
23
  field: field, match: match, replace: replace
24
24
 
25
25
  lambda do |event|
@@ -23,7 +23,7 @@ module Anschel
23
23
  joda = joda.withOffsetParsed
24
24
 
25
25
 
26
- log.debug event: 'compiled-filter', filter: 'index', \
26
+ log.trace event: 'filter-compiled', kind: 'index', \
27
27
  stamp: stamp, prefix: prefix, suffix: suffix, format: format
28
28
 
29
29
  lambda do |event|
@@ -16,7 +16,7 @@ module Anschel
16
16
  field = field.to_sym
17
17
 
18
18
 
19
- log.debug event: 'compiled-filter', filter: 'parse', \
19
+ log.trace event: 'filter-compiled', kind: 'parse', \
20
20
  field: field, pattern: pattern
21
21
 
22
22
  lambda do |event|
@@ -20,7 +20,7 @@ module Anschel
20
20
  target = target.to_sym
21
21
 
22
22
 
23
- log.debug event: 'compiled-filter', filter: 'scan', \
23
+ log.trace event: 'filter-compiled', kind: 'scan', \
24
24
  field: field, pattern: pattern, target: target
25
25
 
26
26
  lambda do |event|
@@ -2,7 +2,8 @@
2
2
  # "stamp": {
3
3
  # "utc?": false,
4
4
  # "field": "timestamp",
5
- # "pattern": [ "YYYY-MM-dd HH:mm:ss.SSS" ]
5
+ # "pattern": [ "YYYY-MM-dd HH:mm:ss.SSS" ],
6
+ # "target": "@timestamp"
6
7
  # }
7
8
  # }
8
9
  module Anschel
@@ -31,8 +32,9 @@ module Anschel
31
32
 
32
33
  offset_s = utc ? Time.zone_offset(Time.now.zone).to_f : 0.0
33
34
 
34
- log.debug event: 'compiled-filter', filter: 'stamp', \
35
- field: field, pattern: pattern, target: target, error_tag: error_tag
35
+
36
+ log.trace event: 'filter-compiled', kind: 'stamp', \
37
+ utc?: utc, field: field, pattern: pattern, target: target
36
38
 
37
39
  lambda do |event|
38
40
  return event unless event.has_key? field
@@ -12,7 +12,8 @@ module Anschel
12
12
  attr_reader :filters
13
13
 
14
14
  def initialize config, stats, log
15
- log.trace event: 'filter', config: config
15
+ log.info event: 'filter-loading'
16
+ log.debug event: 'filter-config', config: config
16
17
  config ||= {} # Allow for nil config
17
18
  @filters = Hash.new { |h,k| h[k] = [] }
18
19
  config.each do |event_type, filter_defns|
@@ -22,7 +23,7 @@ module Anschel
22
23
  @filters[event_type] << self.send(filter_type, filter_conf, log)
23
24
  end
24
25
  end
25
- log.info event: 'filter-loaded'
26
+ log.info event: 'filter-fully-loaded'
26
27
  end
27
28
 
28
29
 
@@ -7,7 +7,6 @@ module Anschel
7
7
  class Input
8
8
  class Kafka < Base
9
9
  def initialize queue, config, stats, log
10
- log.trace event: 'input', kind: 'kafka', config: config
11
10
  @consumer_group = ::Kafka::Group.new config
12
11
  @consumer_group.run num_cpus, queue
13
12
  end
@@ -7,8 +7,6 @@ module Anschel
7
7
  class Input
8
8
  class RabbitMQ < Base
9
9
  def initialize queue, config, stats, log
10
- log.trace event: 'input', kind: 'rabbitmq', config: config
11
-
12
10
  default_exchange = {
13
11
  type: 'x-consistent-hash',
14
12
  durable: true
data/lib/anschel/input.rb CHANGED
@@ -4,34 +4,47 @@ require_relative 'input/rabbitmq'
4
4
 
5
5
  module Anschel
6
6
  class Input
7
- def initialize config, qsize, stats, log
8
- if config.empty?
9
- raise 'No input provided'
10
- end
7
+ def initialize config, qsize, stats, log, leftovers=[]
8
+ log.info event: 'output-loading'
9
+ log.debug event: 'output-config', config: config, qsize: qsize
11
10
 
12
11
  @queue = SizedQueue.new qsize || 2000
13
12
 
13
+ Thread.new do
14
+ leftovers ||= []
15
+ log.trace event: 'input-leftovers', leftovers_size: leftovers.size
16
+ leftovers.each { |l| @queue << l }
17
+ end
18
+
14
19
  @inputs = []
15
20
 
16
21
  config.each do |input|
17
22
  case input.delete(:kind)
18
23
  when 'kafka'
19
24
  @inputs << Input::Kafka.new(@queue, input, stats, log)
25
+ log.trace event: 'input-loaded', kind: 'kafka'
20
26
  when 'rabbitmq'
21
27
  @inputs << Input::RabbitMQ.new(@queue, input, stats, log)
28
+ log.trace event: 'input-loaded', kind: 'rabbitmq'
22
29
  else
23
30
  raise 'Uknown input type'
24
31
  end
25
32
  end
26
33
 
27
- log.info event: 'input-loaded'
34
+ log.info event: 'input-fully-loaded'
28
35
  end
29
36
 
30
37
 
31
38
  def stop
32
- return if @stopped
39
+ return @leftovers if defined? @leftovers
33
40
  @inputs.map &:stop
34
- @stopped = true
41
+ @leftovers = []
42
+ @leftovers << shift until @queue.empty?
43
+ end
44
+
45
+
46
+ def leftovers
47
+ return @leftovers if defined? @leftovers
35
48
  end
36
49
 
37
50
 
data/lib/anschel/main.rb CHANGED
@@ -5,6 +5,7 @@ require 'jrjackson'
5
5
 
6
6
  require_relative 'mjolnir'
7
7
  require_relative 'metadata'
8
+ require_relative 'store'
8
9
  require_relative 'stats'
9
10
  require_relative 'input'
10
11
  require_relative 'filter'
@@ -46,44 +47,70 @@ module Anschel
46
47
  options: options.to_hash,
47
48
  num_cpus: num_cpus
48
49
 
49
- config = JrJackson::Json.load \
50
- File.read(options.config), symbolize_keys: true
50
+ input, filter, output, store, stats, ts = \
51
+ nil, nil, nil, nil, nil, nil, nil
51
52
 
52
- setup_log4j config[:log4j]
53
+ begin
54
+ config = JrJackson::Json.load \
55
+ File.read(options.config), symbolize_keys: true
53
56
 
54
- stats = Stats.new log, options.stats_interval
57
+ setup_log4j config[:log4j]
55
58
 
56
- input = Input.new config[:input], config[:queue_size], stats, log
59
+ store = Store.new config[:store], log
57
60
 
58
- filter = Filter.new config[:filter], stats, log
61
+ stats = Stats.new log, options.stats_interval
59
62
 
60
- output = Output.new config[:output], stats, log
63
+ filter = Filter.new config[:filter], stats, log
61
64
 
62
- trap('SIGINT') do
63
- input.stop
64
- output.stop
65
- log.info event: 'goodbye', version: VERSION
66
- exit
67
- end
65
+ output = Output.new config[:output], stats, log
68
66
 
67
+ input = Input.new \
68
+ config[:input], config[:queue_size], stats, log, store[:input]
69
69
 
70
- stats.create 'event'
71
- stats.get 'event'
70
+ stats.create 'event'
71
+ stats.get 'event'
72
72
 
73
- ts = num_cpus.times.map do
74
- Thread.new do
75
- loop do
76
- event = JrJackson::Json.load \
77
- input.shift, symbolize_keys: true
78
- output.push filter.apply(event)
79
- stats.inc 'event'
73
+ ts = num_cpus.times.map do
74
+ Thread.new do
75
+ loop do
76
+ event = JrJackson::Json.load \
77
+ input.shift, symbolize_keys: true
78
+ output.push filter.apply(event)
79
+ stats.inc 'event'
80
+ end
80
81
  end
81
82
  end
83
+
84
+ rescue => e
85
+ log.fatal \
86
+ event: 'exception',
87
+ exception: e.inspect,
88
+ class: e.class,
89
+ message: e.message,
90
+ backtrace: e.backtrace.join("\n")
91
+ bye output, input, store, log, :error
92
+ exit 2
93
+ end
94
+
95
+ log.info event: 'all-systems-clear'
96
+
97
+ trap('SIGINT') do
98
+ bye output, input, store, log
99
+ exit
82
100
  end
83
101
 
84
- log.info event: 'fully-loaded'
85
102
  ts.map &:join
86
- exit
103
+ end
104
+
105
+
106
+ private
107
+ def bye output, input, store, log, level=:info
108
+ if input && output
109
+ output.stop ; input.stop
110
+ store[:input] = input.leftovers
111
+ log.debug event: 'flush'
112
+ end
113
+ log.send level, event: 'goodbye', version: VERSION
87
114
  end
88
115
 
89
116
  end
@@ -7,8 +7,6 @@ module Anschel
7
7
  class Output
8
8
  class Device < Base
9
9
  def initialize config, stats, log
10
- log.trace event: 'output', kind: 'device', config: config
11
-
12
10
  path = config.delete(:path) || '/dev/stdout'
13
11
  qsize = config.delete(:queue_size) || 2000
14
12
  @queue = SizedQueue.new qsize
@@ -11,8 +11,7 @@ module Anschel
11
11
  class Output
12
12
  class Elasticsearch < Base
13
13
  def initialize config, stats, log
14
- log.trace event: 'output', kind: 'elasticsearch', config: config
15
- default_index = config.delete(:default_index) || 'logs-anschel'
14
+ default_index = config.delete(:default_index) || '.anschel'
16
15
  qsize = config.delete(:queue_size) || 2000
17
16
  bsize = config.delete(:bulk_size) || 500
18
17
  timeout = config.delete(:bulk_timeout) || 0.5
@@ -5,9 +5,8 @@ require_relative 'output/device'
5
5
  module Anschel
6
6
  class Output
7
7
  def initialize config, stats, log
8
- if config.empty?
9
- raise 'No output provided'
10
- end
8
+ log.info event: 'output-loading'
9
+ log.debug event: 'output-config', config: config
11
10
 
12
11
  @outputs = []
13
12
 
@@ -15,14 +14,16 @@ module Anschel
15
14
  case output.delete(:kind)
16
15
  when 'device'
17
16
  @outputs << Output::Device.new(output, stats, log)
17
+ log.trace event: 'output-loaded', kind: 'device'
18
18
  when 'elasticsearch'
19
19
  @outputs << Output::Elasticsearch.new(output, stats, log)
20
+ log.trace event: 'output-loaded', kind: 'elasticsearch'
20
21
  else
21
22
  raise 'Unkown output type'
22
23
  end
23
24
  end
24
25
 
25
- log.info event: 'output-loaded'
26
+ log.info event: 'output-fully-loaded'
26
27
  end
27
28
 
28
29
 
@@ -32,6 +33,7 @@ module Anschel
32
33
  @stopped = true
33
34
  end
34
35
 
36
+
35
37
  def push event
36
38
  @outputs.each do |output|
37
39
  output.push event
data/lib/anschel/stats.rb CHANGED
@@ -83,6 +83,7 @@ module Anschel
83
83
  end
84
84
  end
85
85
 
86
+ return if stats.empty?
86
87
  @logger.info \
87
88
  event: 'stats',
88
89
  interval: @interval,
@@ -0,0 +1,27 @@
1
+ require 'jrjackson'
2
+
3
+
4
+ module Anschel
5
+ class Store
6
+ def initialize path, log
7
+ @path = path || '/tmp/anschel.db'
8
+ @hash = nil
9
+ if File.exist? @path
10
+ @hash = JrJackson::Json.load \
11
+ File.read(@path), symbolize_keys: true
12
+ end
13
+ @hash ||= {}
14
+ log.info event: 'stats-loaded'
15
+ end
16
+
17
+ def [] k ; @hash[k] end
18
+
19
+ def []= k,v ; @hash[k] = v ; save end
20
+
21
+ def save
22
+ File.open(@path, 'w') do |f|
23
+ f.puts JrJackson::Json.dump(@hash)
24
+ end
25
+ end
26
+ end
27
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: anschel
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.1
4
+ version: 0.6.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sean Clemmer
@@ -139,6 +139,7 @@ files:
139
139
  - lib/anschel/output/device.rb
140
140
  - lib/anschel/output/elasticsearch.rb
141
141
  - lib/anschel/stats.rb
142
+ - lib/anschel/store.rb
142
143
  homepage: https://github.com/sczizzo/anschel
143
144
  licenses:
144
145
  - ISC