semantic_logger 4.3.1 → 4.4.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (62) hide show
  1. checksums.yaml +4 -4
  2. data/lib/semantic_logger.rb +7 -1
  3. data/lib/semantic_logger/appender.rb +3 -0
  4. data/lib/semantic_logger/appender/async.rb +29 -10
  5. data/lib/semantic_logger/appender/rabbitmq.rb +120 -0
  6. data/lib/semantic_logger/appenders.rb +89 -0
  7. data/lib/semantic_logger/base.rb +3 -3
  8. data/lib/semantic_logger/concerns/compatibility.rb +2 -2
  9. data/lib/semantic_logger/formatters.rb +1 -0
  10. data/lib/semantic_logger/formatters/base.rb +28 -6
  11. data/lib/semantic_logger/formatters/color.rb +4 -3
  12. data/lib/semantic_logger/formatters/fluentd.rb +37 -0
  13. data/lib/semantic_logger/formatters/json.rb +4 -2
  14. data/lib/semantic_logger/formatters/raw.rb +2 -2
  15. data/lib/semantic_logger/formatters/signalfx.rb +4 -3
  16. data/lib/semantic_logger/levels.rb +38 -0
  17. data/lib/semantic_logger/log.rb +11 -6
  18. data/lib/semantic_logger/loggable.rb +1 -1
  19. data/lib/semantic_logger/logger.rb +43 -1
  20. data/lib/semantic_logger/processor.rb +10 -130
  21. data/lib/semantic_logger/reporters/minitest.rb +49 -0
  22. data/lib/semantic_logger/semantic_logger.rb +40 -75
  23. data/lib/semantic_logger/version.rb +1 -1
  24. metadata +9 -81
  25. data/test/appender/async_batch_test.rb +0 -60
  26. data/test/appender/async_test.rb +0 -44
  27. data/test/appender/bugsnag_test.rb +0 -81
  28. data/test/appender/elasticsearch_http_test.rb +0 -74
  29. data/test/appender/elasticsearch_test.rb +0 -248
  30. data/test/appender/file_test.rb +0 -120
  31. data/test/appender/graylog_test.rb +0 -82
  32. data/test/appender/honeybadger_test.rb +0 -45
  33. data/test/appender/http_test.rb +0 -63
  34. data/test/appender/kafka_test.rb +0 -35
  35. data/test/appender/mongodb_test.rb +0 -104
  36. data/test/appender/new_relic_test.rb +0 -80
  37. data/test/appender/newrelic_rpm.rb +0 -14
  38. data/test/appender/sentry_test.rb +0 -47
  39. data/test/appender/splunk_http_test.rb +0 -79
  40. data/test/appender/splunk_test.rb +0 -83
  41. data/test/appender/syslog_test.rb +0 -61
  42. data/test/appender/tcp_test.rb +0 -66
  43. data/test/appender/udp_test.rb +0 -59
  44. data/test/appender/wrapper_test.rb +0 -95
  45. data/test/concerns/compatibility_test.rb +0 -117
  46. data/test/debug_as_trace_logger_test.rb +0 -81
  47. data/test/formatters/color_test.rb +0 -153
  48. data/test/formatters/default_test.rb +0 -175
  49. data/test/formatters/one_line_test.rb +0 -60
  50. data/test/formatters/signalfx_test.rb +0 -197
  51. data/test/formatters_test.rb +0 -36
  52. data/test/in_memory_appender.rb +0 -8
  53. data/test/in_memory_appender_helper.rb +0 -43
  54. data/test/in_memory_batch_appender.rb +0 -8
  55. data/test/in_memory_metrics_appender.rb +0 -13
  56. data/test/loggable_test.rb +0 -103
  57. data/test/logger_test.rb +0 -334
  58. data/test/measure_test.rb +0 -346
  59. data/test/metric/new_relic_test.rb +0 -35
  60. data/test/metric/signalfx_test.rb +0 -77
  61. data/test/semantic_logger_test.rb +0 -303
  62. data/test/test_helper.rb +0 -31
@@ -1,60 +0,0 @@
1
- require_relative '../test_helper'
2
-
3
- module SemanticLogger
4
- module Formatters
5
- class DefaultTest < Minitest::Test
6
- describe Default do
7
- let(:log_time) do
8
- Time.utc(2017, 1, 14, 8, 32, 5.375276)
9
- end
10
-
11
- let(:level) do
12
- :debug
13
- end
14
-
15
- let(:log) do
16
- log = SemanticLogger::Log.new('DefaultTest', level)
17
- log.time = log_time
18
- log
19
- end
20
-
21
- let(:set_exception) do
22
- begin
23
- raise 'Oh no'
24
- rescue Exception => exc
25
- log.exception = exc
26
- end
27
- end
28
-
29
- let(:formatter) do
30
- formatter = SemanticLogger::Formatters::OneLine.new
31
- # Does not use the logger instance for formatting purposes
32
- formatter.call(log, nil)
33
- formatter
34
- end
35
-
36
- describe 'message' do
37
- it 'logs message' do
38
- log.message = "Hello \nWorld\n"
39
- assert_equal '-- Hello World', formatter.message
40
- end
41
-
42
- it 'skips empty message' do
43
- refute formatter.message
44
- end
45
- end
46
-
47
- describe 'exception' do
48
- it 'logs exception' do
49
- set_exception
50
- assert_equal '-- Exception: RuntimeError: Oh no', formatter.exception
51
- end
52
-
53
- it 'skips nil exception' do
54
- refute formatter.exception
55
- end
56
- end
57
- end
58
- end
59
- end
60
- end
@@ -1,197 +0,0 @@
1
- require_relative '../test_helper'
2
- require 'net/http'
3
-
4
- module SemanticLogger
5
- module Formatters
6
- class SignalfxTest < Minitest::Test
7
- describe SemanticLogger::Formatters::Signalfx do
8
- let :average_metric_name do
9
- 'Application.average'
10
- end
11
-
12
- let :counter_metric_name do
13
- 'Application.counter'
14
- end
15
-
16
- let :log do
17
- metric = '/user/login'
18
- log = SemanticLogger::Log.new('User', :debug)
19
- log.metric = metric
20
- log
21
- end
22
-
23
- let :logs do
24
- 3.times.collect do |i|
25
- l = log.dup
26
- l.metric = "/user/login#{i + 1}"
27
- l
28
- end
29
- end
30
-
31
- let :same_logs do
32
- 3.times.collect do |_i|
33
- l = log.dup
34
- l.metric = '/user/login'
35
- l
36
- end
37
- end
38
-
39
- let :dimensions do
40
- {action: 'hit', user: 'jbloggs', state: 'FL'}
41
- end
42
-
43
- let :all_dimensions do
44
- dims = dimensions.merge(
45
- host: SemanticLogger.host,
46
- application: SemanticLogger.application,
47
- environment: 'test'
48
- )
49
- string_keys = {}
50
- dims.each_pair { |k, v| string_keys[k.to_s] = v }
51
- string_keys
52
- end
53
-
54
- let :appender do
55
- Net::HTTP.stub_any_instance(:start, true) do
56
- SemanticLogger::Metric::Signalfx.new(token: 'TEST')
57
- end
58
- end
59
-
60
- let :formatter do
61
- appender.formatter
62
- end
63
-
64
- describe 'format single log' do
65
- let :result do
66
- JSON.parse(formatter.call(log, appender))
67
- end
68
-
69
- it 'send counter metric when there is no duration' do
70
- hash = result
71
- assert counters = hash['counter'], hash
72
- assert counter = counters.first, hash
73
- assert_equal counter_metric_name, counter['metric'], counter
74
- assert_equal 1, counter['value'], counter
75
- assert_equal (log.time.to_i * 1_000).to_i, counter['timestamp'], counter
76
- assert counter.key?('dimensions')
77
- end
78
-
79
- it 'send gauge metric when log includes duration' do
80
- log.duration = 1234
81
- hash = result
82
- assert counters = hash['gauge'], hash
83
- assert counter = counters.first, hash
84
- assert_equal average_metric_name, counter['metric'], counter
85
- assert_equal 1234, counter['value'], counter
86
- assert_equal (log.time.to_i * 1_000).to_i, counter['timestamp'], counter
87
- assert counter.key?('dimensions')
88
- end
89
-
90
- it 'also sends counter metric when gauge metric is sent' do
91
- log.duration = 1234
92
- hash = result
93
- assert counters = hash['counter'], hash
94
- assert counter = counters.first, hash
95
- assert_equal counter_metric_name, counter['metric'], counter
96
- assert_equal 1, counter['value'], counter
97
- assert_equal (log.time.to_i * 1_000).to_i, counter['timestamp'], counter
98
- assert counter.key?('dimensions')
99
- end
100
-
101
- it 'only forwards whitelisted dimensions from named_tags' do
102
- log.named_tags = {user_id: 47, tracking_number: 7474, session_id: 'hsdhngsd'}
103
- formatter.dimensions = %i[user_id application]
104
- hash = result
105
- assert counters = hash['counter'], hash
106
- assert counter = counters.first, hash
107
- assert_equal({'class' => 'user', 'action' => 'login', 'environment' => 'test', 'user_id' => '47', 'host' => SemanticLogger.host, 'application' => SemanticLogger.application}, counter['dimensions'], counter)
108
- end
109
-
110
- it 'raises exception with both a whitelist and blacklist' do
111
- assert_raises ArgumentError do
112
- SemanticLogger::Formatters::Signalfx.new(token: 'TEST', dimensions: [:user_id], exclude_dimensions: [:tracking_number])
113
- end
114
- end
115
-
116
- it 'send custom counter metric when there is no duration' do
117
- log.metric = 'Filter/count'
118
- log.dimensions = dimensions
119
- hash = result
120
-
121
- assert counters = hash['counter'], hash
122
- assert counter = counters.first, hash
123
- assert_equal 'Filter.count', counter['metric'], counter
124
- assert_equal 1, counter['value'], counter
125
- assert_equal (log.time.to_i * 1_000).to_i, counter['timestamp'], counter
126
- assert_equal all_dimensions, counter['dimensions']
127
- end
128
- end
129
-
130
- describe 'format batch logs' do
131
- let :result do
132
- JSON.parse(formatter.batch(logs, appender))
133
- end
134
-
135
- it 'send metrics' do
136
- hash = result
137
-
138
- assert counters = hash['counter'], hash
139
- assert_equal 3, counters.size
140
- assert_equal counter_metric_name, counters[0]['metric']
141
- assert_equal 1, counters[0]['value']
142
- assert_equal counter_metric_name, counters[1]['metric']
143
- assert_equal counter_metric_name, counters[2]['metric']
144
- end
145
-
146
- it 'sends gauge metrics' do
147
- logs.each { |log| log.duration = 3.5 }
148
- hash = result
149
- assert gauges = hash['gauge'], hash
150
- assert_equal 3, gauges.size
151
- assert_equal average_metric_name, gauges[0]['metric']
152
- assert_equal 3.5, gauges[0]['value']
153
- assert_equal average_metric_name, gauges[1]['metric']
154
- assert_equal average_metric_name, gauges[2]['metric']
155
- end
156
-
157
- describe 'send custom' do
158
- let :logs do
159
- 3.times.collect do |_i|
160
- l = log.dup
161
- l.metric = 'Filter/count'
162
- l.dimensions = dimensions
163
- l
164
- end
165
- end
166
-
167
- it 'counter metric when there is no duration' do
168
- hash = result
169
-
170
- assert counters = hash['counter'], hash
171
- assert counter = counters.first, hash
172
- assert_equal 'Filter.count', counter['metric'], counter
173
- assert_equal 3, counter['value'], counter
174
- assert_equal (log.time.to_i * 1_000).to_i, counter['timestamp'], counter
175
- assert_equal all_dimensions, counter['dimensions']
176
- end
177
- end
178
- end
179
-
180
- describe 'format batch logs with aggregation' do
181
- let :result do
182
- JSON.parse(formatter.batch(same_logs, appender))
183
- end
184
-
185
- it 'sends counter metrics' do
186
- hash = result
187
-
188
- assert counters = hash['counter'], hash
189
- assert_equal 1, counters.size
190
- assert_equal counter_metric_name, counters[0]['metric']
191
- assert_equal 3, counters[0]['value']
192
- end
193
- end
194
- end
195
- end
196
- end
197
- end
@@ -1,36 +0,0 @@
1
- require_relative 'test_helper'
2
-
3
- class FormattersTest < Minitest::Test
4
- describe SemanticLogger::Formatters do
5
- describe '.factory' do
6
- let :log do
7
- SemanticLogger::Log.new('Test', :info)
8
- end
9
-
10
- let :appender do
11
- SemanticLogger::Appender::File.new(io: STDOUT)
12
- end
13
-
14
- it 'from a symbol' do
15
- assert formatter = SemanticLogger::Formatters.factory(:raw)
16
- assert formatter.is_a?(SemanticLogger::Formatters::Raw)
17
- assert_equal 'Test', formatter.call(log, appender)[:name]
18
- end
19
-
20
- it 'from a Hash (Symbol with options)' do
21
- assert formatter = SemanticLogger::Formatters.factory(raw: {time_format: '%Y%m%d'})
22
- assert formatter.is_a?(SemanticLogger::Formatters::Raw)
23
- assert result = formatter.call(log, appender)
24
- assert_equal 'Test', result[:name]
25
- assert_equal Time.now.strftime('%Y%m%d'), result[:time]
26
- end
27
-
28
- it 'from block' do
29
- my_formatter = ->(log, _appender) { log.name }
30
- assert formatter = SemanticLogger::Formatters.factory(my_formatter)
31
- assert formatter.is_a?(Proc)
32
- assert_equal 'Test', formatter.call(log, appender)
33
- end
34
- end
35
- end
36
- end
@@ -1,8 +0,0 @@
1
- # Store in memory the last log message received.
2
- class InMemoryAppender < SemanticLogger::Subscriber
3
- attr_accessor :message
4
-
5
- def log(log)
6
- self.message = log
7
- end
8
- end
@@ -1,43 +0,0 @@
1
- require 'minitest/shared_description'
2
-
3
- InMemoryAppenderHelper = shared_description do
4
- let :log_message do
5
- SemanticLogger.flush
6
- appender.message
7
- end
8
-
9
- let :appender do
10
- InMemoryAppender.new
11
- end
12
-
13
- let :thread_name do
14
- Thread.current.name
15
- end
16
-
17
- let :payload do
18
- {session_id: 'HSSKLEU@JDK767', tracking_number: 12_345}
19
- end
20
-
21
- let :logger do
22
- SemanticLogger['TestLogger']
23
- end
24
-
25
- let :appender_options do
26
- {appender: appender}
27
- end
28
-
29
- let :added_appender do
30
- SemanticLogger.add_appender(appender_options)
31
- end
32
-
33
- before do
34
- SemanticLogger.default_level = :trace
35
- SemanticLogger.backtrace_level = :trace
36
- SemanticLogger.flush
37
- added_appender
38
- end
39
-
40
- after do
41
- SemanticLogger.appenders.each { |appender| SemanticLogger.remove_appender(appender) }
42
- end
43
- end
@@ -1,8 +0,0 @@
1
- # Store in memory the last log message received.
2
- class InMemoryBatchAppender < SemanticLogger::Subscriber
3
- attr_accessor :message
4
-
5
- def batch(logs)
6
- self.message = logs
7
- end
8
- end
@@ -1,13 +0,0 @@
1
- # Store in memory the last log message received.
2
- class InMemoryMetricsAppender < SemanticLogger::Subscriber
3
- attr_accessor :message
4
-
5
- def log(log)
6
- self.message = log
7
- end
8
-
9
- # Only forward log entries that contain metrics.
10
- def should_log?(log)
11
- log.metric && meets_log_level?(log) && !filtered?(log)
12
- end
13
- end
@@ -1,103 +0,0 @@
1
- require_relative 'test_helper'
2
- require 'stringio'
3
-
4
- class TestAttribute
5
- include SemanticLogger::Loggable
6
- end
7
-
8
- # Unit Test for SemanticLogger::Appender::File
9
- #
10
- class AppenderFileTest < Minitest::Test
11
- module Perform
12
- def perform
13
- logger.info 'perform'
14
- end
15
- end
16
-
17
- class Base
18
- include SemanticLogger::Loggable
19
- include Perform
20
- end
21
-
22
- module Process
23
- def process
24
- logger.info 'process'
25
- end
26
- end
27
-
28
- class Subclass < Base
29
- include Process
30
- end
31
-
32
- describe SemanticLogger::Loggable do
33
- describe 'inheritance' do
34
- it 'should give child classes their own logger' do
35
- assert_equal Subclass.name, Subclass.logger.name
36
- assert_equal Base.name, Base.logger.name
37
- assert_equal Subclass.name, Subclass.logger.name
38
- child_logger = Subclass.logger
39
- refute_equal child_logger, Base.logger
40
- assert_equal child_logger.object_id, Subclass.logger.object_id
41
- end
42
-
43
- it 'should give child objects their own logger' do
44
- subclass = Subclass.new
45
- base = Base.new
46
- assert_equal subclass.class.name, subclass.logger.name
47
- assert_equal base.class.name, base.logger.name
48
- assert_equal subclass.class.name, subclass.logger.name
49
- child_logger = subclass.logger
50
- refute_equal child_logger, base.logger
51
- assert_equal child_logger.object_id, subclass.logger.object_id
52
- end
53
-
54
- it 'should allow mixins to call parent logger' do
55
- base = Base.new
56
- base.perform
57
- called = false
58
- Base.logger.stub(:info, ->(description) { called = true if description == 'perform' }) do
59
- base.perform
60
- end
61
- assert called, 'Did not call the correct logger'
62
- end
63
-
64
- it 'should allow child mixins to call parent logger' do
65
- subclass = Subclass.new
66
- subclass.process
67
- called = false
68
- Subclass.logger.stub(:info, ->(description) { called = true if description == 'process' }) do
69
- subclass.process
70
- end
71
- assert called, 'Did not call the correct logger'
72
- end
73
- end
74
-
75
- describe 'logger' do
76
- include InMemoryAppenderHelper
77
-
78
- describe 'for each log level' do
79
- # Ensure that any log level can be logged
80
- SemanticLogger::LEVELS.each do |level|
81
- it "logs #{level} information with class attribute" do
82
- TestAttribute.logger.send(level, "hello #{level}", payload)
83
-
84
- assert log = log_message
85
- assert_equal "hello #{level}", log.message
86
- assert_equal level, log.level
87
- assert_equal 'TestAttribute', log.name
88
- assert_equal payload, log.payload
89
- end
90
-
91
- it "log #{level} information with instance attribute" do
92
- TestAttribute.new.logger.send(level, "hello #{level}", payload)
93
- assert log = log_message
94
- assert_equal "hello #{level}", log.message
95
- assert_equal level, log.level
96
- assert_equal 'TestAttribute', log.name
97
- assert_equal payload, log.payload
98
- end
99
- end
100
- end
101
- end
102
- end
103
- end