semantic_logger 4.5.0 → 4.12.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (59) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +51 -21
  3. data/Rakefile +7 -7
  4. data/lib/semantic_logger/ansi_colors.rb +0 -10
  5. data/lib/semantic_logger/appender/async.rb +12 -10
  6. data/lib/semantic_logger/appender/async_batch.rb +7 -3
  7. data/lib/semantic_logger/appender/bugsnag.rb +43 -30
  8. data/lib/semantic_logger/appender/elasticsearch.rb +34 -15
  9. data/lib/semantic_logger/appender/elasticsearch_http.rb +4 -4
  10. data/lib/semantic_logger/appender/file.rb +249 -67
  11. data/lib/semantic_logger/appender/graylog.rb +15 -10
  12. data/lib/semantic_logger/appender/honeybadger.rb +3 -3
  13. data/lib/semantic_logger/appender/http.rb +41 -20
  14. data/lib/semantic_logger/appender/io.rb +68 -0
  15. data/lib/semantic_logger/appender/kafka.rb +46 -31
  16. data/lib/semantic_logger/appender/mongodb.rb +6 -6
  17. data/lib/semantic_logger/appender/new_relic.rb +2 -2
  18. data/lib/semantic_logger/appender/rabbitmq.rb +5 -5
  19. data/lib/semantic_logger/appender/sentry.rb +7 -7
  20. data/lib/semantic_logger/appender/sentry_ruby.rb +138 -0
  21. data/lib/semantic_logger/appender/splunk.rb +7 -5
  22. data/lib/semantic_logger/appender/splunk_http.rb +6 -5
  23. data/lib/semantic_logger/appender/syslog.rb +23 -15
  24. data/lib/semantic_logger/appender/tcp.rb +9 -9
  25. data/lib/semantic_logger/appender/udp.rb +2 -2
  26. data/lib/semantic_logger/appender/wrapper.rb +3 -2
  27. data/lib/semantic_logger/appender.rb +62 -65
  28. data/lib/semantic_logger/appenders.rb +36 -53
  29. data/lib/semantic_logger/base.rb +61 -39
  30. data/lib/semantic_logger/formatters/base.rb +16 -6
  31. data/lib/semantic_logger/formatters/color.rb +14 -15
  32. data/lib/semantic_logger/formatters/default.rb +18 -5
  33. data/lib/semantic_logger/formatters/fluentd.rb +7 -18
  34. data/lib/semantic_logger/formatters/json.rb +3 -5
  35. data/lib/semantic_logger/formatters/logfmt.rb +77 -0
  36. data/lib/semantic_logger/formatters/raw.rb +39 -10
  37. data/lib/semantic_logger/formatters/signalfx.rb +14 -21
  38. data/lib/semantic_logger/formatters/syslog.rb +8 -6
  39. data/lib/semantic_logger/formatters/syslog_cee.rb +9 -7
  40. data/lib/semantic_logger/formatters.rb +13 -13
  41. data/lib/semantic_logger/jruby/garbage_collection_logger.rb +4 -2
  42. data/lib/semantic_logger/levels.rb +9 -7
  43. data/lib/semantic_logger/log.rb +58 -73
  44. data/lib/semantic_logger/loggable.rb +8 -1
  45. data/lib/semantic_logger/logger.rb +19 -11
  46. data/lib/semantic_logger/metric/new_relic.rb +3 -3
  47. data/lib/semantic_logger/metric/signalfx.rb +3 -3
  48. data/lib/semantic_logger/metric/statsd.rb +7 -7
  49. data/lib/semantic_logger/processor.rb +9 -7
  50. data/lib/semantic_logger/reporters/minitest.rb +4 -4
  51. data/lib/semantic_logger/semantic_logger.rb +57 -23
  52. data/lib/semantic_logger/subscriber.rb +24 -7
  53. data/lib/semantic_logger/sync.rb +12 -0
  54. data/lib/semantic_logger/sync_processor.rb +58 -0
  55. data/lib/semantic_logger/test/capture_log_events.rb +34 -0
  56. data/lib/semantic_logger/utils.rb +32 -13
  57. data/lib/semantic_logger/version.rb +1 -1
  58. data/lib/semantic_logger.rb +27 -22
  59. metadata +15 -10
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 34b3b78799e196b270d81aba7deb9b0accd1187a900967a3943dd03301c63199
4
- data.tar.gz: 775b6eeca4ca6b9c38e9213e7f32fee9d179ce36148433dfa91a8630f74873b3
3
+ metadata.gz: b09c37737f1e42edbeee95b036ba0581d5164d756e13de37aca9b22b3093cd45
4
+ data.tar.gz: 9f66b72480df2371a7d305164e443f9667e1acd5521c1347d54c3841efbfa4c9
5
5
  SHA512:
6
- metadata.gz: 7cda8a50c62a2dcdb079d5f96cbde61e5cc941c443122a3bbc102a1513bc3686d44a20cca28e7627444bf640a6329035aefc43cb6111a3e6b9cb91411fe33782
7
- data.tar.gz: caf355bf16e08b133fe07ddd6b4cab813b6e7224b3e1f152e1ab54cf30f574fc8665f99ae3938078fb35fcfeea3643d565a814cbe2774d263135c93722147b06
6
+ metadata.gz: fb27aa1a6d5dc1f2e0e6505ba9348a7cec091a153763361e8c9c20c21177bf84ac11ac2f21fc37ec994988ba31763dcd5c3134ac40a169ac987ed617eceec46e
7
+ data.tar.gz: 5d084bc8cc57b1e836326eae912667ef6b7a284b0125c0b0acee678af78c01017b9667db9a43df7c0fb38af4998b0ab3128ac05d3e2bce266176e9c4d8fadccd
data/README.md CHANGED
@@ -1,25 +1,13 @@
1
1
  # Semantic Logger
2
- [![Gem Version](https://img.shields.io/gem/v/semantic_logger.svg)](https://rubygems.org/gems/semantic_logger) [![Build Status](https://travis-ci.org/rocketjob/semantic_logger.svg?branch=master)](https://travis-ci.org/rocketjob/semantic_logger) [![Downloads](https://img.shields.io/gem/dt/semantic_logger.svg)](https://rubygems.org/gems/semantic_logger) [![License](https://img.shields.io/badge/license-Apache%202.0-brightgreen.svg)](http://opensource.org/licenses/Apache-2.0) ![](https://img.shields.io/badge/status-Production%20Ready-blue.svg) [![Gitter chat](https://img.shields.io/badge/IRC%20(gitter)-Support-brightgreen.svg)](https://gitter.im/rocketjob/support)
2
+ [![Gem Version](https://img.shields.io/gem/v/semantic_logger.svg)](https://rubygems.org/gems/semantic_logger) [![Build Status](https://github.com/reidmorrison/semantic_logger/workflows/build/badge.svg)](https://github.com/reidmorrison/semantic_logger/actions?query=workflow%3Abuild) [![Downloads](https://img.shields.io/gem/dt/semantic_logger.svg)](https://rubygems.org/gems/semantic_logger) [![License](https://img.shields.io/badge/license-Apache%202.0-brightgreen.svg)](http://opensource.org/licenses/Apache-2.0) ![](https://img.shields.io/badge/status-Production%20Ready-blue.svg)
3
3
 
4
4
  Semantic Logger is a feature rich logging framework, and replacement for existing Ruby & Rails loggers.
5
5
 
6
- * https://rocketjob.github.io/semantic_logger/
6
+ * https://logger.rocketjob.io/
7
7
 
8
8
  ## Documentation
9
9
 
10
- [Semantic Logger Guide](http://rocketjob.github.io/semantic_logger)
11
-
12
- [Reference Documentation](http://www.rubydoc.info/gems/semantic_logger/)
13
-
14
- ## Upgrading to Semantic Logger v4.4
15
-
16
- With some forking frameworks it is necessary to call `reopen` after the fork. With v4.4 the
17
- workaround for Ruby 2.5 crashes is no longer needed.
18
- I.e. Please remove the following line if being called anywhere:
19
-
20
- ~~~ruby
21
- SemanticLogger::Processor.instance.instance_variable_set(:@queue, Queue.new)
22
- ~~~
10
+ [Semantic Logger Guide](https://logger.rocketjob.io/)
23
11
 
24
12
  ## Logging Destinations
25
13
 
@@ -34,7 +22,7 @@ Logging to the following destinations are all supported "out-of-the-box":
34
22
  * Splunk
35
23
  * MongoDB
36
24
  * Honeybadger
37
- * Sentry
25
+ * Sentry (both with legacy `sentry-raven` and modern `sentry-ruby` gem)
38
26
  * HTTP
39
27
  * TCP
40
28
  * UDP
@@ -50,7 +38,7 @@ handles saving log information to multiple destinations / appenders.
50
38
 
51
39
  ## Rails
52
40
 
53
- When running Rails, use [rails_semantic_logger](http://github.com/rocketjob/rails_semantic_logger)
41
+ When running Rails, use [rails_semantic_logger](http://github.com/reidmorrison/rails_semantic_logger)
54
42
  instead of Semantic Logger directly since it will automatically replace the Rails default logger with Semantic Logger.
55
43
 
56
44
  ## Rocket Job
@@ -72,11 +60,53 @@ and are therefore not automatically included by this gem:
72
60
  - Splunk Appender: gem 'splunk-sdk-ruby'
73
61
  - Elasticsearch Appender: gem 'elasticsearch'
74
62
  - Kafka Appender: gem 'ruby-kafka'
63
+ - Legacy Sentry Appender: gem 'sentry-raven' (deprecated)
64
+ - Sentry Appender: gem 'sentry-ruby'
65
+
66
+ ## Upgrading to Semantic Logger v4.9
67
+
68
+ These changes should not be noticeable by the majority of users of Semantic Logger, since
69
+ they are to the internal API. It is possible that advanced users may be using these internal
70
+ API's directly.
71
+
72
+ This does not affect any calls to the public api `SemanticLogger.add_appender`.
73
+
74
+ File and IO are now separate appenders. When creating the File appender explicitly, its arguments
75
+ have changed. For example, when requesting an IO stream, it needs to be changed from:
76
+
77
+ ~~~ruby
78
+ SemanticLogger::Appender::File.new(io: $stderr)
79
+ ~~~
80
+ to:
81
+ ~~~ruby
82
+ SemanticLogger::Appender::IO.new($stderr)
83
+ ~~~
84
+
85
+ Additionally, this needs to be changed from:
86
+ ~~~ruby
87
+ SemanticLogger::Appender::File.new(file_name: "file.log")
88
+ ~~~
89
+ to:
90
+ ~~~ruby
91
+ SemanticLogger::Appender::File.new("file.log")
92
+ ~~~
93
+
94
+ Rails Semantic Logger, if used, needs to be upgraded to v4.9 when upgrading to Semantic Logger v4.9.
95
+
96
+ ## Upgrading to Semantic Logger v4.4
97
+
98
+ With some forking frameworks it is necessary to call `reopen` after the fork. With v4.4 the
99
+ workaround for Ruby 2.5 crashes is no longer needed.
100
+ I.e. Please remove the following line if being called anywhere:
101
+
102
+ ~~~ruby
103
+ SemanticLogger::Processor.instance.instance_variable_set(:@queue, Queue.new)
104
+ ~~~
75
105
 
76
- ## V4 Upgrade notes
106
+ ## Upgrading to Semantic Logger v4.0
77
107
 
78
108
  The following changes need to be made when upgrading to V4:
79
- - Ruby V2.1 / JRuby V9.1 is now the minimum runtime version.
109
+ - Ruby V2.3 / JRuby V9.1 is now the minimum runtime version.
80
110
  - Replace calls to Logger#with_payload with SemanticLogger.named_tagged.
81
111
  - Replace calls to Logger#payload with SemanticLogger.named_tags.
82
112
  - MongoDB Appender requires Mongo Ruby Client V2 or greater.
@@ -129,13 +159,13 @@ SemanticLogger.default_level = :trace
129
159
  SemanticLogger.add_appender(file_name: 'development.log', formatter: :color)
130
160
  ~~~
131
161
 
132
- If running rails, see: [Semantic Logger Rails](http://rocketjob.github.io/semantic_logger/rails.html)
162
+ If running rails, see: [Semantic Logger Rails](https://logger.rocketjob.io/rails.html)
133
163
 
134
164
  ## Author
135
165
 
136
166
  [Reid Morrison](https://github.com/reidmorrison)
137
167
 
138
- [Contributors](https://github.com/rocketjob/semantic_logger/graphs/contributors)
168
+ [Contributors](https://github.com/reidmorrison/semantic_logger/graphs/contributors)
139
169
 
140
170
  ## Versioning
141
171
 
data/Rakefile CHANGED
@@ -1,22 +1,22 @@
1
- require 'rake/clean'
2
- require 'rake/testtask'
1
+ require "rake/clean"
2
+ require "rake/testtask"
3
3
 
4
- $LOAD_PATH.unshift File.expand_path('lib', __dir__)
5
- require 'semantic_logger/version'
4
+ $LOAD_PATH.unshift File.expand_path("lib", __dir__)
5
+ require "semantic_logger/version"
6
6
 
7
7
  task :gem do
8
- system 'gem build semantic_logger.gemspec'
8
+ system "gem build semantic_logger.gemspec"
9
9
  end
10
10
 
11
11
  task publish: :gem do
12
12
  system "git tag -a v#{SemanticLogger::VERSION} -m 'Tagging #{SemanticLogger::VERSION}'"
13
- system 'git push --tags'
13
+ system "git push --tags"
14
14
  system "gem push semantic_logger-#{SemanticLogger::VERSION}.gem"
15
15
  system "rm semantic_logger-#{SemanticLogger::VERSION}.gem"
16
16
  end
17
17
 
18
18
  Rake::TestTask.new(:test) do |t|
19
- t.pattern = 'test/**/*_test.rb'
19
+ t.pattern = "test/**/*_test.rb"
20
20
  t.verbose = true
21
21
  t.warning = false
22
22
  end
@@ -11,15 +11,5 @@ module SemanticLogger
11
11
  MAGENTA = "\e[35m".freeze
12
12
  CYAN = "\e[36m".freeze
13
13
  WHITE = "\e[37m".freeze
14
-
15
- # DEPRECATED - NOT USED
16
- LEVEL_MAP = {
17
- trace: MAGENTA,
18
- debug: GREEN,
19
- info: CYAN,
20
- warn: BOLD,
21
- error: RED,
22
- fatal: RED
23
- }.freeze
24
14
  end
25
15
  end
@@ -1,4 +1,4 @@
1
- require 'forwardable'
1
+ require "forwardable"
2
2
 
3
3
  module SemanticLogger
4
4
  module Appender
@@ -15,6 +15,7 @@ module SemanticLogger
15
15
  def_delegator :@appender, :filter
16
16
  def_delegator :@appender, :host
17
17
  def_delegator :@appender, :application
18
+ def_delegator :@appender, :environment
18
19
  def_delegator :@appender, :level
19
20
  def_delegator :@appender, :level=
20
21
  def_delegator :@appender, :logger
@@ -52,13 +53,13 @@ module SemanticLogger
52
53
  # Re-open appender after a fork
53
54
  def reopen
54
55
  # Workaround CRuby crash on fork by recreating queue on reopen
55
- # https://github.com/rocketjob/semantic_logger/issues/103
56
+ # https://github.com/reidmorrison/semantic_logger/issues/103
56
57
  @queue&.close
57
58
  create_queue
58
59
 
59
60
  appender.reopen if appender.respond_to?(:reopen)
60
61
 
61
- @thread.kill if @thread&.alive?
62
+ @thread&.kill if @thread&.alive?
62
63
  @thread = Thread.new { process }
63
64
  end
64
65
 
@@ -72,6 +73,7 @@ module SemanticLogger
72
73
  # Starts the worker thread if not running.
73
74
  def thread
74
75
  return @thread if @thread&.alive?
76
+
75
77
  @thread = Thread.new { process }
76
78
  end
77
79
 
@@ -114,21 +116,21 @@ module SemanticLogger
114
116
  # This thread is designed to never go down unless the main thread terminates
115
117
  # or the appender is closed.
116
118
  Thread.current.name = logger.name
117
- logger.trace 'Async: Appender thread active'
119
+ logger.trace "Async: Appender thread active"
118
120
  begin
119
121
  process_messages
120
- rescue StandardError => exception
122
+ rescue StandardError => e
121
123
  # This block may be called after the file handles have been released by Ruby
122
124
  begin
123
- logger.error('Async: Restarting due to exception', exception)
125
+ logger.error("Async: Restarting due to exception", e)
124
126
  rescue StandardError
125
127
  nil
126
128
  end
127
129
  retry
128
- rescue Exception => exception
130
+ rescue Exception => e
129
131
  # This block may be called after the file handles have been released by Ruby
130
132
  begin
131
- logger.error('Async: Stopping due to fatal exception', exception)
133
+ logger.error("Async: Stopping due to fatal exception", e)
132
134
  rescue StandardError
133
135
  nil
134
136
  end
@@ -136,7 +138,7 @@ module SemanticLogger
136
138
  @thread = nil
137
139
  # This block may be called after the file handles have been released by Ruby
138
140
  begin
139
- logger.trace('Async: Thread has stopped')
141
+ logger.trace("Async: Thread has stopped")
140
142
  rescue StandardError
141
143
  nil
142
144
  end
@@ -158,7 +160,7 @@ module SemanticLogger
158
160
  break unless process_message(message)
159
161
  end
160
162
  end
161
- logger.trace 'Async: Queue Closed'
163
+ logger.trace "Async: Queue Closed"
162
164
  end
163
165
 
164
166
  # Returns false when message processing should be stopped
@@ -1,4 +1,4 @@
1
- require 'concurrent'
1
+ require "concurrent"
2
2
 
3
3
  module SemanticLogger
4
4
  module Appender
@@ -42,7 +42,9 @@ module SemanticLogger
42
42
  lag_threshold_s: lag_threshold_s
43
43
  )
44
44
 
45
- raise(ArgumentError, "#{appender.class.name} does not support batching. It must implement #batch") unless appender.respond_to?(:batch)
45
+ return if appender.respond_to?(:batch)
46
+
47
+ raise(ArgumentError, "#{appender.class.name} does not support batching. It must implement #batch")
46
48
  end
47
49
 
48
50
  # Add log message for processing.
@@ -62,6 +64,7 @@ module SemanticLogger
62
64
  signal.wait(batch_seconds)
63
65
 
64
66
  logs = []
67
+ messages = []
65
68
  first = true
66
69
  message_count = queue.length
67
70
  message_count.times do
@@ -74,10 +77,11 @@ module SemanticLogger
74
77
  first = false
75
78
  end
76
79
  else
77
- process_message(message)
80
+ messages << message
78
81
  end
79
82
  end
80
83
  appender.batch(logs) if logs.size.positive?
84
+ messages.each { |message| process_message(message) }
81
85
  signal.reset unless queue.size >= batch_size
82
86
  end
83
87
  end
@@ -1,7 +1,7 @@
1
1
  begin
2
- require 'bugsnag'
2
+ require "bugsnag"
3
3
  rescue LoadError
4
- raise 'Gem bugsnag is required for logging purposes. Please add the gem "bugsnag" to your Gemfile.'
4
+ raise LoadError, 'Gem bugsnag is required for logging purposes. Please add the gem "bugsnag" to your Gemfile.'
5
5
  end
6
6
 
7
7
  # Send log messages to Bugsnag
@@ -30,7 +30,7 @@ module SemanticLogger
30
30
  # Proc: Only include log messages where the supplied Proc returns true
31
31
  # The Proc must return true or false.
32
32
  def initialize(level: :error, **args, &block)
33
- raise 'Bugsnag only supports :info, :warn, or :error log levels' unless %i[info warn error fatal].include?(level)
33
+ raise "Bugsnag only supports :info, :warn, or :error log levels" unless %i[info warn error fatal].include?(level)
34
34
 
35
35
  # Replace the Bugsnag logger so that we can identify its log messages and not forward them to Bugsnag
36
36
  ::Bugsnag.configure { |config| config.logger = SemanticLogger[Bugsnag] }
@@ -40,48 +40,61 @@ module SemanticLogger
40
40
 
41
41
  # Returns [Hash] of parameters to send to Bugsnag.
42
42
  def call(log, logger)
43
- h = SemanticLogger::Formatters::Raw.new.call(log, logger)
44
- h[:severity] = log_level(log)
45
- h.delete(:message) if h[:exception] && (h[:message] == h[:exception][:message])
46
- h.delete(:time)
47
- h.delete(:exception)
48
- h
43
+ hash = SemanticLogger::Formatters::Raw.new.call(log, logger)
44
+ hash.delete(:message) if hash[:exception] && (hash[:message] == hash[:exception][:message])
45
+ hash.delete(:time)
46
+ hash.delete(:level_index)
47
+ hash.delete(:exception)
48
+ hash[:file] = "#{hash[:file]}:#{hash.delete(:line)}" if hash.key?(:file)
49
+ hash
49
50
  end
50
51
 
51
- # Send an error notification to Bugsnag
52
52
  def log(log)
53
53
  # Ignore logs coming from Bugsnag itself
54
- return false if log.name == 'Bugsnag'
54
+ return false if log.name == "Bugsnag"
55
55
 
56
56
  # Send error messages as Runtime exceptions
57
- exception =
58
- if log.exception
59
- # Manually constructed Exception, without a backtrace.
60
- log.exception.set_backtrace(log.backtrace) if !log.exception.backtrace && log.backtrace
61
- log.exception
62
- else
63
- error = RuntimeError.new(log.message)
64
- error.set_backtrace(log.backtrace) if log.backtrace
65
- error
66
- end
67
-
68
- # For more documentation on the Bugsnag.notify method see:
69
- # https://bugsnag.com/docs/notifiers/ruby#sending-handled-exceptions
70
- ::Bugsnag.notify(exception, formatter.call(log, self))
57
+ exception = extract_exception(log)
58
+ hash = formatter.call(log, self)
59
+ bugsnag_notify(exception, hash, log_level(log.level))
71
60
  true
72
61
  end
73
62
 
74
63
  private
75
64
 
65
+ def bugsnag_notify(exception, hash, level)
66
+ if ::Bugsnag::VERSION.to_i >= 6
67
+ ::Bugsnag.notify(exception) do |report|
68
+ report.severity = level
69
+ hash.each_pair { |key, value| report.add_tab(key, value) }
70
+ end
71
+ else
72
+ hash[:severity] = level
73
+ ::Bugsnag.notify(exception, hash)
74
+ end
75
+ end
76
+
77
+ def extract_exception(log)
78
+ if log.exception
79
+ # Manually constructed Exception, without a backtrace.
80
+ log.exception.set_backtrace(log.backtrace) if !log.exception.backtrace && log.backtrace
81
+ return log.exception
82
+ end
83
+
84
+ error = RuntimeError.new(log.message)
85
+ error.set_backtrace(log.backtrace) if log.backtrace
86
+ error
87
+ end
88
+
76
89
  # Bugsnag supports: error, warning or info
77
- def log_level(log)
78
- case log.level
90
+ def log_level(level)
91
+ case level
79
92
  when :error, :fatal
80
- 'error'
93
+ "error"
81
94
  when :warn
82
- 'warning'
95
+ "warning"
83
96
  else
84
- 'info'
97
+ "info"
85
98
  end
86
99
  end
87
100
  end
@@ -1,10 +1,11 @@
1
1
  begin
2
- require 'elasticsearch'
2
+ require "elasticsearch"
3
3
  rescue LoadError
4
- raise 'Gem elasticsearch is required for logging to Elasticsearch. Please add the gem "elasticsearch" to your Gemfile.'
4
+ raise LoadError,
5
+ 'Gem elasticsearch is required for logging to Elasticsearch. Please add the gem "elasticsearch" to your Gemfile.'
5
6
  end
6
7
 
7
- require 'date'
8
+ require "date"
8
9
 
9
10
  # Forward all log messages to Elasticsearch.
10
11
  #
@@ -17,7 +18,8 @@ require 'date'
17
18
  module SemanticLogger
18
19
  module Appender
19
20
  class Elasticsearch < SemanticLogger::Subscriber
20
- attr_accessor :url, :index, :date_pattern, :type, :client, :flush_interval, :timeout_interval, :batch_size, :elasticsearch_args
21
+ attr_accessor :url, :index, :date_pattern, :type, :client, :flush_interval, :timeout_interval, :batch_size,
22
+ :elasticsearch_args
21
23
 
22
24
  # Create Elasticsearch appender over persistent HTTP(S)
23
25
  #
@@ -123,16 +125,17 @@ module SemanticLogger
123
125
  # send_get_body_as [String]
124
126
  # Specify the HTTP method to use for GET requests with a body.
125
127
  # Default: 'GET'
126
- def initialize(url: 'http://localhost:9200',
127
- index: 'semantic_logger',
128
- date_pattern: '%Y.%m.%d',
129
- type: 'log',
128
+ def initialize(url: "http://localhost:9200",
129
+ index: "semantic_logger",
130
+ date_pattern: "%Y.%m.%d",
131
+ type: "log",
130
132
  level: nil,
131
133
  formatter: nil,
132
134
  filter: nil,
133
135
  application: nil,
136
+ environment: nil,
134
137
  host: nil,
135
- metrics: false,
138
+ data_stream: false,
136
139
  **elasticsearch_args,
137
140
  &block)
138
141
 
@@ -143,8 +146,9 @@ module SemanticLogger
143
146
  @elasticsearch_args = elasticsearch_args.dup
144
147
  @elasticsearch_args[:url] = url if url && !elasticsearch_args[:hosts]
145
148
  @elasticsearch_args[:logger] = logger
149
+ @data_stream = data_stream
146
150
 
147
- super(level: level, formatter: formatter, filter: filter, application: application, host: host, metrics: false, &block)
151
+ super(level: level, formatter: formatter, filter: filter, application: application, environment: environment, host: host, metrics: false, &block)
148
152
  reopen
149
153
  end
150
154
 
@@ -172,20 +176,35 @@ module SemanticLogger
172
176
  private
173
177
 
174
178
  def write_to_elasticsearch(messages)
175
- bulk_result = @client.bulk(body: messages)
176
- return unless bulk_result['errors']
179
+ bulk_result = if @data_stream
180
+ @client.bulk(index: index, body: messages)
181
+ else
182
+ @client.bulk(body: messages)
183
+ end
177
184
 
178
- failed = bulk_result['items'].reject { |x| x['status'] == 201 }
185
+ return unless bulk_result["errors"]
186
+
187
+ failed = bulk_result["items"].reject { |x| x["status"] == 201 }
179
188
  logger.error("ElasticSearch: Write failed. Messages discarded. : #{failed}")
180
189
  end
181
190
 
182
191
  def bulk_index(log)
183
192
  expanded_index_name = log.time.strftime("#{index}-#{date_pattern}")
184
- {'index' => {'_index' => expanded_index_name, '_type' => type}}
193
+ if @data_stream
194
+ {"create" => {}}
195
+ else
196
+ {"index" => {"_index" => expanded_index_name, "_type" => type}}
197
+ end
185
198
  end
186
199
 
187
200
  def default_formatter
188
- SemanticLogger::Formatters::Raw.new(time_format: :iso_8601, time_key: :timestamp)
201
+ time_key = if @data_stream
202
+ "@timestamp"
203
+ else
204
+ :timestamp
205
+ end
206
+
207
+ SemanticLogger::Formatters::Raw.new(time_format: :iso_8601, time_key: time_key)
189
208
  end
190
209
  end
191
210
  end
@@ -1,4 +1,4 @@
1
- require 'date'
1
+ require "date"
2
2
  # Forward all log messages to Elasticsearch one at a time via a HTTP post.
3
3
  #
4
4
  # Note:
@@ -50,9 +50,9 @@ module SemanticLogger
50
50
  # application: [String]
51
51
  # Name of this application to appear in log messages.
52
52
  # Default: SemanticLogger.application
53
- def initialize(index: 'semantic_logger',
54
- type: 'log',
55
- url: 'http://localhost:9200',
53
+ def initialize(index: "semantic_logger",
54
+ type: "log",
55
+ url: "http://localhost:9200",
56
56
  **http_args,
57
57
  &block)
58
58