lorekeeper 2.2.1 → 2.3.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
  SHA256:
3
- metadata.gz: 614a3b1372eba2d9fe6a56964d25f9048d2b6dde65ac3e135c023cff6af42b99
4
- data.tar.gz: 45a541d7ccfb5f4aae3f0912dfdb69c19eb1dbca1aef86f4d1f33457df7886ec
3
+ metadata.gz: 53332589726c07831fc34d3d63b7517de62fd1a75c11d1cbf772b6088d125eed
4
+ data.tar.gz: 797d799f0268b110fe584ead9bdb9f9c3f779bca7d1e8d0fb75c796409a340c5
5
5
  SHA512:
6
- metadata.gz: 1712e531beb4c0d47853c9128ee732bca5a7c21a016418ead6f812923c33207ec3d86543f7e9e69355344d3cdc4f5720f40be17e0563da798cacd8472fdf7725
7
- data.tar.gz: 87ab1d4ae3df8fb09fa148f2d64cf2d87ebf7ab9423dcee06480a0a620f5ce2ec66d483d7a8f42243b0a41fed9c7c1d70670a490f632fc52d0c9fb65cc962fdb
6
+ metadata.gz: c773417845d13a54058bd01b1541a64fa9564bce845fec21efcd69fa23916a323da0c679d86e8950c7c7dea1fa7c4a18e02429f21b4d896c670d4bb952ade48e
7
+ data.tar.gz: f95030ee5fe64f4cecd0cd9b15217897324bf2ac6aca1daed1a20a8daea233c029412a6a021dddd8bcd7d75d94aee673aa531f35bc8a214b6c07a0e666fca377
@@ -23,6 +23,8 @@ jobs:
23
23
  with:
24
24
  ruby-version: ${{ matrix.ruby-version }}
25
25
  bundler-cache: true # runs 'bundle install' and caches installed gems automatically
26
+ - name: Run rubocop
27
+ run: bundle exec rubocop
26
28
  - name: Run tests
27
29
  run: bundle exec rspec
28
30
  - name: Run benchmark
data/.rubocop.yml CHANGED
@@ -1,6 +1,42 @@
1
- Metrics/LineLength:
2
- Max: 120
3
- # https://github.com/rubocop/rubocop/blob/20990ed3831589c0d9f202107b1b580ead8ef2c5/lib/rubocop/cop/style/single_line_methods.rb#L11
1
+ require:
2
+ - rubocop-performance
3
+
4
+ inherit_gem:
5
+ rubocop-mdsol: rubocop.yml
6
+
7
+ AllCops:
8
+ Exclude:
9
+ - '*gemspec'
10
+ # NOTE: Excludes vendor from linting. Needed by GitHub Actions.
11
+ # - https://github.com/rubocop/rubocop/issues/9832#issuecomment-873398952
12
+ #
13
+ - 'vendor/bundle/**/*'
14
+
15
+ Lint/ConstantDefinitionInBlock:
16
+ Exclude:
17
+ - 'spec/**/*'
18
+
19
+ Layout/ArgumentAlignment:
20
+ EnforcedStyle: with_fixed_indentation
21
+
22
+ Layout/FirstHashElementIndentation:
23
+ EnforcedStyle: consistent
24
+
25
+ Metrics/ParameterLists:
26
+ CountKeywordArgs: false
27
+
4
28
  # TODO: add "EnforcedStyle: allow_single_line" once all rubys are > 3.0 to autocorrect all single-line methods to endless
29
+ # https://github.com/rubocop/rubocop/blob/20990ed3831589c0d9f202107b1b580ead8ef2c5/lib/rubocop/cop/style/single_line_methods.rb#L11
30
+ #
5
31
  Style/SingleLineMethods:
6
32
  Enabled: false
33
+
34
+ Style/MissingRespondToMissing:
35
+ Enabled: false
36
+
37
+ Style/FrozenStringLiteralComment:
38
+ Enabled: true
39
+
40
+ Style/StringLiterals:
41
+ Enabled: true
42
+ EnforcedStyle: single_quotes
data/CHANGELOG.md CHANGED
@@ -1,3 +1,15 @@
1
+ # 2.3.2
2
+ * Ensure additional fields are reset after logging
3
+ * Let Oj fallback to :object mode for non-representable data
4
+ * Fix SimpleLogger to handle non-String log messages
5
+ * Run RuboCop checks on build and fix RuboCop offenses
6
+
7
+ # 2.3.1
8
+ * Fix MultiLogger to not raise ArgumentError
9
+
10
+ # 2.3.0
11
+ * Add `#write` method support to all loggers
12
+
1
13
  # 2.2.1
2
14
  * Fix MultiLogger to not raise NoMethodError
3
15
 
data/Gemfile CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  source 'https://rubygems.org'
2
4
 
3
5
  # Specify your gem's dependencies in lorekeeper.gemspec
data/Rakefile CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'benchmark'
2
4
  require 'tempfile'
3
5
  require 'securerandom'
@@ -5,7 +7,7 @@ require 'benchmark/ips'
5
7
  require 'byebug'
6
8
  require 'rbtrace'
7
9
 
8
- $LOAD_PATH.unshift(File.expand_path('../lib', __FILE__))
10
+ $LOAD_PATH.unshift(File.expand_path('lib', __dir__))
9
11
  $LOAD_PATH.uniq!
10
12
 
11
13
  require 'lorekeeper'
data/bin/console CHANGED
@@ -1,4 +1,5 @@
1
1
  #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
2
3
 
3
4
  require 'bundler/setup'
4
5
  require 'lorekeeper'
@@ -5,9 +5,9 @@ require 'logger'
5
5
  module Lorekeeper
6
6
  # Very simple, very fast logger
7
7
  class FastLogger
8
- include ::Logger::Severity # contains the levels constants: DEBUG, ERROR, etc.
9
- attr_accessor :level # Current level, default: DEBUG
10
- attr_accessor :formatter # Just for compatibility with Logger, not used
8
+ include ::Logger::Severity # contains the levels constants: DEBUG, ERROR, etc.
9
+ attr_accessor :level, # Current level, default: DEBUG
10
+ :formatter # Just for compatibility with Logger, not used
11
11
 
12
12
  def debug?; level <= DEBUG; end
13
13
  def info?; level <= INFO; end
@@ -21,12 +21,12 @@ module Lorekeeper
21
21
  @file = file # We only keep this so we can inspect where we are sending the logs
22
22
  end
23
23
 
24
- LOGGING_METHODS = [
25
- :debug,
26
- :info,
27
- :warn,
28
- :error,
29
- :fatal
24
+ LOGGING_METHODS = %i[
25
+ debug
26
+ info
27
+ warn
28
+ error
29
+ fatal
30
30
  ].freeze
31
31
 
32
32
  METHOD_SEVERITY_MAP = {
@@ -56,7 +56,8 @@ module Lorekeeper
56
56
  # This is part of the standard Logger API, we need this to be compatible
57
57
  def add(severity, message_param = nil, progname = nil, &block)
58
58
  return true if severity < @level
59
- message = (block && block.call) || message_param || progname
59
+
60
+ message = block&.call || message_param || progname
60
61
  log_data(severity, message.freeze)
61
62
  end
62
63
 
@@ -65,20 +66,22 @@ module Lorekeeper
65
66
  # To avoid needing to monkey-patch Lorekeeper just to get this method, we are adding a simple
66
67
  # non-functional version here.
67
68
  def silence_logger(&block)
68
- yield if block_given?
69
+ yield if block
69
70
  end
70
71
 
71
72
  # activerecord-session_store v2 is now simply calling silence instead of silence_logger
72
73
  def silence(&block)
73
- yield if block_given?
74
+ yield if block
74
75
  end
75
76
 
76
77
  # inherited classes probably want to reimplement this
77
78
  def log_data(_severity, message)
78
- @iodevice.write(message)
79
+ write(message)
79
80
  end
80
81
 
81
- private
82
+ def write(message)
83
+ @iodevice.write(message)
84
+ end
82
85
 
83
86
  require 'monitor'
84
87
  # Mutex to avoid broken lines when multiple threads access the log file
@@ -106,11 +109,12 @@ module Lorekeeper
106
109
  def to_iodevice(file)
107
110
  return nil unless file
108
111
 
109
- iodevice = if file.respond_to?(:write) && file.respond_to?(:close)
110
- file
111
- else
112
- open_logfile(file)
113
- end
112
+ iodevice =
113
+ if file.respond_to?(:write) && file.respond_to?(:close)
114
+ file
115
+ else
116
+ open_logfile(file)
117
+ end
114
118
 
115
119
  iodevice.sync = true if iodevice.respond_to?(:sync=)
116
120
  iodevice
@@ -128,5 +132,7 @@ module Lorekeeper
128
132
  open_logfile(filename)
129
133
  end
130
134
  end
135
+
136
+ private_constant :LogDeviceMutex, :LogDevice
131
137
  end
132
138
  end
@@ -28,13 +28,14 @@ module Lorekeeper
28
28
  # Delegates methods to the existing Logger instance
29
29
  # We are extending the logger API with methods error_with_data, etc
30
30
  LOGGING_METHODS.each do |method_name|
31
- define_method "#{method_name}_with_data", ->(message_param = nil, data = {}, &block) do
31
+ define_method "#{method_name}_with_data", ->(message_param = nil, data = {}, &block) {
32
32
  return true if METHOD_SEVERITY_MAP[method_name] < @level
33
+
33
34
  extra_fields = { DATA => (data || {}) }
34
- with_extra_fields(extra_fields) { # Using do/end here only valid on Ruby>= 2.3
35
+ with_extra_fields(extra_fields) do
35
36
  add(METHOD_SEVERITY_MAP[method_name], message_param, nil, &block)
36
- }
37
- end
37
+ end
38
+ }
38
39
  end
39
40
 
40
41
  def add_thread_unsafe_fields(fields)
@@ -65,7 +66,7 @@ module Lorekeeper
65
66
  # By default message comes from exception.message
66
67
  # Optional and named parameters to overwrite message, level and add data
67
68
  def exception(exception, custom_message = nil, custom_data = nil, custom_level = :error,
68
- message: nil, data: nil, level: nil) # Backwards compatible named params
69
+ message: nil, data: nil, level: nil) # Backwards compatible named params
69
70
 
70
71
  param_level = level || custom_level
71
72
  param_data = data || custom_data
@@ -94,8 +95,22 @@ module Lorekeeper
94
95
  "Lorekeeper JSON logger. IO: #{@file.inspect}"
95
96
  end
96
97
 
98
+ def write(message)
99
+ super(json_message(message) << "\n")
100
+ end
101
+
97
102
  private
98
103
 
104
+ def json_message(message)
105
+ Oj.dump(message, mode: :compat, cache_keys: true, cache_str: 5)
106
+ rescue JSON::GeneratorError
107
+ begin
108
+ Oj.dump(message)
109
+ rescue => e
110
+ Oj.dump(MESSAGE => e.message)
111
+ end
112
+ end
113
+
99
114
  # Some instrumentation libraries pollute the stacktrace and create a large output which may
100
115
  # cause problems with certain logging backends.
101
116
  # Hardcording newrelic, active_support/callbacks and zipkin-tracer now here.
@@ -126,12 +141,13 @@ module Lorekeeper
126
141
  def with_extra_fields(fields)
127
142
  state[:extra_fields] = fields
128
143
  yield
144
+ ensure
129
145
  state[:extra_fields] = {}
130
146
  end
131
147
 
132
148
  def remove_invalid_fields(fields)
133
149
  fields.delete_if do |_, v|
134
- v.nil? || v.respond_to?(:empty?) && v.empty?
150
+ v.nil? || (v.respond_to?(:empty?) && v.empty?)
135
151
  end
136
152
  end
137
153
 
@@ -139,16 +155,16 @@ module Lorekeeper
139
155
  current_state = state # Accessing state is slow. Do it only once per call.
140
156
  # merging is slow, we do not want to merge with empty hash if possible
141
157
  fields_to_log = if current_state[:extra_fields].empty?
142
- current_state[:base_fields]
143
- else
144
- current_state[:base_fields].merge(current_state[:extra_fields])
145
- end
158
+ current_state[:base_fields]
159
+ else
160
+ current_state[:base_fields].merge(current_state[:extra_fields])
161
+ end
146
162
 
147
163
  fields_to_log[MESSAGE] = message
148
164
  fields_to_log[TIMESTAMP] = Time.now.utc.strftime(DATE_FORMAT)
149
165
  fields_to_log[LEVEL] = SEVERITY_NAMES_MAP[severity]
150
166
 
151
- @iodevice.write(Oj.dump(fields_to_log, mode: :compat, cache_keys: true, cache_str: 5) << "\n")
167
+ write(fields_to_log)
152
168
  end
153
169
  end
154
170
  end
@@ -19,24 +19,14 @@ module Lorekeeper
19
19
  # Define all common logging methods within Multilogger to avoid NoMethodError
20
20
  def debug(*args, &block); call_loggers(:debug, *args, &block); end
21
21
 
22
- def debug_with_data(*args, &block); call_loggers(:debug, *args, &block); end
23
-
24
22
  def info(*args, &block); call_loggers(:info, *args, &block); end
25
23
 
26
- def info_with_data(*args, &block); call_loggers(:info, *args, &block); end
27
-
28
24
  def warn(*args, &block); call_loggers(:warn, *args, &block); end
29
25
 
30
- def warn_with_data(*args, &block); call_loggers(:warn, *args, &block); end
31
-
32
26
  def error(*args, &block); call_loggers(:error, *args, &block); end
33
27
 
34
- def error_with_data(*args, &block); call_loggers(:error, *args, &block); end
35
-
36
28
  def fatal(*args, &block); call_loggers(:fatal, *args, &block); end
37
29
 
38
- def fatal_with_data(*args, &block); call_loggers(:fatal, *args, &block); end
39
-
40
30
  def write(*args); call_loggers(:write, *args); end
41
31
 
42
32
  def respond_to?(method, all_included: false)
@@ -28,7 +28,8 @@ module Lorekeeper
28
28
  # \e[colorm sets a color \e[0m resets all properties
29
29
  def log_data(severity, message)
30
30
  color = SEVERITY_TO_COLOR_MAP[severity]
31
- @iodevice.write("\e[#{color}m#{message.gsub('\n', "\n").gsub('\t', "\t")}\e[0m\n")
31
+ message = message.to_s
32
+ write("\e[#{color}m#{message.gsub('\n', "\n").gsub('\t', "\t")}\e[0m\n")
32
33
  end
33
34
 
34
35
  def inspect
@@ -37,22 +38,28 @@ module Lorekeeper
37
38
 
38
39
  # Extending the logger API with methods error_with_data, etc
39
40
  LOGGING_METHODS.each do |method_name|
40
- define_method "#{method_name}_with_data", ->(message_param = nil, data = {}, &block) do
41
+ define_method "#{method_name}_with_data", ->(message_param = nil, data = {}) {
41
42
  return true if METHOD_SEVERITY_MAP[method_name] < @level
43
+
42
44
  log_data(METHOD_SEVERITY_MAP[method_name], "#{message_param}, data: #{data}")
43
- end
45
+ }
44
46
  end
45
47
 
46
48
  # To not raise NoMethodError for the methods defined in JSONLogger
47
49
  def current_fields(*); end
50
+
48
51
  def state(*); end
52
+
49
53
  def add_thread_unsafe_fields(*); end
54
+
50
55
  def remove_thread_unsafe_fields(*); end
56
+
51
57
  def add_fields(*); end
58
+
52
59
  def remove_fields(*); end
53
60
 
54
61
  def exception(exception, custom_message = nil, custom_data = nil, custom_level = :error,
55
- message: nil, data: nil, level: nil)
62
+ message: nil, data: nil, level: nil)
56
63
 
57
64
  param_level = level || custom_level
58
65
  param_data = data || custom_data
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Lorekeeper
4
- VERSION = '2.2.1'
4
+ VERSION = '2.3.2'
5
5
  end
data/lorekeeper.gemspec CHANGED
@@ -34,4 +34,6 @@ Gem::Specification.new do |spec|
34
34
  spec.add_development_dependency 'rbtrace', '~> 0.4'
35
35
  spec.add_development_dependency 'simplecov', '~> 0.16'
36
36
  spec.add_development_dependency 'mutant-rspec', '~> 0.8'
37
+ spec.add_development_dependency 'rubocop-mdsol', '~> 0.3'
38
+ spec.add_development_dependency 'rubocop-performance', '~> 1.14'
37
39
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: lorekeeper
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.2.1
4
+ version: 2.3.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jordi Polo
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-08-04 00:00:00.000000000 Z
11
+ date: 2022-08-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: oj
@@ -176,6 +176,34 @@ dependencies:
176
176
  - - "~>"
177
177
  - !ruby/object:Gem::Version
178
178
  version: '0.8'
179
+ - !ruby/object:Gem::Dependency
180
+ name: rubocop-mdsol
181
+ requirement: !ruby/object:Gem::Requirement
182
+ requirements:
183
+ - - "~>"
184
+ - !ruby/object:Gem::Version
185
+ version: '0.3'
186
+ type: :development
187
+ prerelease: false
188
+ version_requirements: !ruby/object:Gem::Requirement
189
+ requirements:
190
+ - - "~>"
191
+ - !ruby/object:Gem::Version
192
+ version: '0.3'
193
+ - !ruby/object:Gem::Dependency
194
+ name: rubocop-performance
195
+ requirement: !ruby/object:Gem::Requirement
196
+ requirements:
197
+ - - "~>"
198
+ - !ruby/object:Gem::Version
199
+ version: '1.14'
200
+ type: :development
201
+ prerelease: false
202
+ version_requirements: !ruby/object:Gem::Requirement
203
+ requirements:
204
+ - - "~>"
205
+ - !ruby/object:Gem::Version
206
+ version: '1.14'
179
207
  description: Opinionated logger which outputs messages in JSON format
180
208
  email:
181
209
  - mumismo@gmail.com