loga 2.6.0 → 2.7.0

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: 5366cef0d19c0384219e570b910635edeced8c13f7d27a7726f76397de78b492
4
- data.tar.gz: 1015b91450e060ca3d705a93c50decf6111136a51d4819429f3be45f97687e53
3
+ metadata.gz: 8a97eae050b9e31ef0ddb1e6f327563c4e0f54eb1a42ea7bb53b03e22c8fb9c9
4
+ data.tar.gz: 771373253651884fead19e93038d5c7e31827d3c562d2cd748e0acd66f31124e
5
5
  SHA512:
6
- metadata.gz: 151f8dddb93eeaf02ed792e45d51e7c694f349d6d397d18602ac6928953844f7047abaf7ae31b681cfa068f75842799d54eb90a948c75cead9e3b2edd1200175
7
- data.tar.gz: 80a2b4f443aaea2403388de748fb181aeea34c81f6e693cc08b50b6b9893a48bcfed447c747d0f241823d99904b28772b64e7495870ac03426b71b0be6991f97
6
+ metadata.gz: 28d17a44bf2c8c0a919916438c8935a4033e14176185ca87ff69987ee03507dee5ae854c2887ff89d174c78fd0fa846b8d8237392b6705eb552365202f2f7680
7
+ data.tar.gz: 45bf838fa85c9a3a01ba1134034b2ab2e577cd9f9c28ecceaf175935ff69627f156856dc8e383b5212829636934657ee4fb0c40f5e5e992a54eb1027ee47d74f
data/.circleci/config.yml CHANGED
@@ -30,10 +30,6 @@ test_build: &test_build
30
30
 
31
31
  version: 2
32
32
  jobs:
33
- ruby-2.4:
34
- docker:
35
- - image: circleci/ruby:2.4
36
- <<: *test_build
37
33
  ruby-2.5:
38
34
  docker:
39
35
  - image: circleci/ruby:2.5
@@ -45,10 +41,12 @@ jobs:
45
41
  ruby-2.7:
46
42
  docker:
47
43
  - image: cimg/ruby:2.7
44
+ - image: redis:7
48
45
  <<: *test_build
49
46
  ruby-3.0:
50
47
  docker:
51
48
  - image: cimg/ruby:3.0
49
+ - image: redis:7
52
50
  <<: *test_build
53
51
  rubocop:
54
52
  <<: *basic_build
@@ -83,10 +81,6 @@ workflows:
83
81
  filters:
84
82
  tags:
85
83
  only: /.*/
86
- - ruby-2.4:
87
- filters:
88
- tags:
89
- only: /.*/
90
84
  - ruby-2.5:
91
85
  filters:
92
86
  tags:
@@ -112,7 +106,6 @@ workflows:
112
106
  ignore: /.*/
113
107
  requires:
114
108
  - rubocop
115
- - ruby-2.4
116
109
  - ruby-2.5
117
110
  - ruby-2.6
118
111
  - ruby-2.7
data/Appraisals CHANGED
@@ -1,13 +1,3 @@
1
- if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.4.0')
2
- appraise 'rails32' do
3
- gem 'rails', '~> 3.2.0'
4
- end
5
-
6
- appraise 'rails40' do
7
- gem 'rails', '~> 4.0.0'
8
- end
9
- end
10
-
11
1
  if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.7.0')
12
2
  appraise 'rails42' do
13
3
  gem 'rails', '~> 4.2.0'
@@ -31,8 +21,28 @@ if Gem::Version.new(RUBY_VERSION) > Gem::Version.new('2.5.0')
31
21
  gem 'rails', '~> 6.0.0'
32
22
  end
33
23
 
34
- appraise 'sidekiq6' do
35
- gem 'sidekiq', '~> 6.0'
24
+ appraise 'sidekiq60' do
25
+ gem 'sidekiq', '~> 6.0.0'
26
+ end
27
+
28
+ appraise 'sidekiq61' do
29
+ gem 'sidekiq', '~> 6.1.0'
30
+ end
31
+
32
+ appraise 'sidekiq62' do
33
+ gem 'sidekiq', '~> 6.2.0'
34
+ end
35
+
36
+ appraise 'sidekiq63' do
37
+ gem 'sidekiq', '~> 6.3.0'
38
+ end
39
+
40
+ appraise 'sidekiq64' do
41
+ gem 'sidekiq', '~> 6.4.0'
42
+ end
43
+
44
+ appraise 'sidekiq65' do
45
+ gem 'sidekiq', '~> 6.5.0'
36
46
  end
37
47
  end
38
48
 
@@ -44,6 +54,18 @@ if Gem::Version.new(RUBY_VERSION) > Gem::Version.new('2.7.0')
44
54
  appraise 'rails70' do
45
55
  gem 'rails', '~> 7.0.0'
46
56
  end
57
+
58
+ appraise 'sidekiq7' do
59
+ gem 'sidekiq', '~> 7.0'
60
+ end
61
+
62
+ appraise 'sidekiq70' do
63
+ gem 'sidekiq', '~> 7.0.0'
64
+ end
65
+
66
+ appraise 'sidekiq71' do
67
+ gem 'sidekiq', '~> 7.1.0'
68
+ end
47
69
  end
48
70
 
49
71
  appraise 'sidekiq51' do
data/CHANGELOG.md CHANGED
@@ -4,6 +4,14 @@ All notable changes to this project will be documented in this file.
4
4
  The format is based on [Keep a Changelog](http://keepachangelog.com/)
5
5
  and this project adheres to [Semantic Versioning](http://semver.org/).
6
6
 
7
+ ## [2.7.0] - 2023-03-28
8
+ ### Added
9
+ - Support for sidekiq 7
10
+
11
+ ## [2.6.1] - 2022-02-22
12
+ ### Fixed
13
+ - Fix compatibility with sidekiq 6.4.1
14
+
7
15
  ## [2.6.0] - 2021-12-22
8
16
  ### Added
9
17
  - Allow using the gem with rails 7
data/README.md CHANGED
@@ -150,7 +150,7 @@ LOGA_FORMAT=simple rackup
150
150
 
151
151
  ### Sidekiq
152
152
 
153
- Loga `2.3` provides an out-of-the-box support for `Sidekiq ~> 5.0`.
153
+ Loga `2.7` provides an out-of-the-box support for `Sidekiq ~> 7.0`.
154
154
 
155
155
  ## Output Example
156
156
 
@@ -2,10 +2,10 @@
2
2
 
3
3
  source "https://rubygems.org"
4
4
 
5
- gem "rails", "~> 3.2.0"
5
+ gem "sidekiq", "~> 6.0.0"
6
6
 
7
7
  group :test do
8
- gem "simplecov"
8
+ gem "simplecov", "~> 0.17.0"
9
9
  end
10
10
 
11
11
  gemspec path: "../"
@@ -2,10 +2,10 @@
2
2
 
3
3
  source "https://rubygems.org"
4
4
 
5
- gem "rails", "~> 4.0.0"
5
+ gem "sidekiq", "~> 6.1.0"
6
6
 
7
7
  group :test do
8
- gem "simplecov"
8
+ gem "simplecov", "~> 0.17.0"
9
9
  end
10
10
 
11
11
  gemspec path: "../"
@@ -0,0 +1,11 @@
1
+ # This file was generated by Appraisal
2
+
3
+ source "https://rubygems.org"
4
+
5
+ gem "sidekiq", "~> 6.2.0"
6
+
7
+ group :test do
8
+ gem "simplecov", "~> 0.17.0"
9
+ end
10
+
11
+ gemspec path: "../"
@@ -0,0 +1,11 @@
1
+ # This file was generated by Appraisal
2
+
3
+ source "https://rubygems.org"
4
+
5
+ gem "sidekiq", "~> 6.3.0"
6
+
7
+ group :test do
8
+ gem "simplecov", "~> 0.17.0"
9
+ end
10
+
11
+ gemspec path: "../"
@@ -0,0 +1,11 @@
1
+ # This file was generated by Appraisal
2
+
3
+ source "https://rubygems.org"
4
+
5
+ gem "sidekiq", "~> 6.4.0"
6
+
7
+ group :test do
8
+ gem "simplecov", "~> 0.17.0"
9
+ end
10
+
11
+ gemspec path: "../"
@@ -0,0 +1,11 @@
1
+ # This file was generated by Appraisal
2
+
3
+ source "https://rubygems.org"
4
+
5
+ gem "sidekiq", "~> 6.5.0"
6
+
7
+ group :test do
8
+ gem "simplecov", "~> 0.17.0"
9
+ end
10
+
11
+ gemspec path: "../"
@@ -2,7 +2,7 @@
2
2
 
3
3
  source "https://rubygems.org"
4
4
 
5
- gem "sidekiq", "~> 6.0"
5
+ gem "sidekiq", "~> 7.0"
6
6
 
7
7
  group :test do
8
8
  gem "simplecov", "~> 0.17.0"
@@ -0,0 +1,11 @@
1
+ # This file was generated by Appraisal
2
+
3
+ source "https://rubygems.org"
4
+
5
+ gem "sidekiq", "~> 7.0.0"
6
+
7
+ group :test do
8
+ gem "simplecov", "~> 0.17.0"
9
+ end
10
+
11
+ gemspec path: "../"
@@ -0,0 +1,11 @@
1
+ # This file was generated by Appraisal
2
+
3
+ source "https://rubygems.org"
4
+
5
+ gem "sidekiq", "~> 7.1.0"
6
+
7
+ group :test do
8
+ gem "simplecov", "~> 0.17.0"
9
+ end
10
+
11
+ gemspec path: "../"
data/lib/loga/sidekiq.rb CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Loga
2
4
  module Sidekiq
3
5
  def self.configure_logging
@@ -5,20 +7,41 @@ module Loga
5
7
  return if Gem::Version.new(::Sidekiq::VERSION) < Gem::Version.new('5.0')
6
8
 
7
9
  if Gem::Version.new(::Sidekiq::VERSION) < Gem::Version.new('6.0')
8
- require 'loga/sidekiq5/job_logger'
9
-
10
- ::Sidekiq.configure_server do |config|
11
- config.options[:job_logger] = Loga::Sidekiq5::JobLogger
12
- end
10
+ configure_for_sidekiq5
13
11
  elsif Gem::Version.new(::Sidekiq::VERSION) < Gem::Version.new('7.0')
14
- require 'loga/sidekiq6/job_logger'
12
+ configure_for_sidekiq6
13
+ elsif Gem::Version.new(::Sidekiq::VERSION) < Gem::Version.new('8.0')
14
+ configure_for_sidekiq7
15
+ end
16
+ end
15
17
 
16
- ::Sidekiq.configure_server do |config|
17
- config.options[:job_logger] = Loga::Sidekiq6::JobLogger
18
- end
18
+ def self.configure_for_sidekiq5
19
+ require 'loga/sidekiq5/job_logger'
20
+
21
+ ::Sidekiq.configure_server do |config|
22
+ config.options[:job_logger] = Loga::Sidekiq5::JobLogger
19
23
  end
20
24
 
21
25
  ::Sidekiq.logger = Loga.configuration.logger
22
26
  end
27
+
28
+ def self.configure_for_sidekiq6
29
+ require 'loga/sidekiq6/job_logger'
30
+
31
+ ::Sidekiq.configure_server do |config|
32
+ config.options[:job_logger] = Loga::Sidekiq6::JobLogger
33
+ end
34
+
35
+ ::Sidekiq.logger = Loga.configuration.logger
36
+ end
37
+
38
+ def self.configure_for_sidekiq7
39
+ require 'loga/sidekiq7/job_logger'
40
+
41
+ ::Sidekiq.configure_server do |config|
42
+ config[:job_logger] = Loga::Sidekiq7::JobLogger
43
+ config.logger = Loga.configuration.logger
44
+ end
45
+ end
23
46
  end
24
47
  end
@@ -10,22 +10,27 @@ module Loga
10
10
 
11
11
  yield
12
12
 
13
- with_elapsed_time_context(start) do
14
- loga_log(
15
- message: "#{item['class']} with jid: '#{item['jid']}' done", item: item,
16
- )
17
- end
13
+ ::Sidekiq::Context.current[:elapsed] = elapsed(start)
14
+
15
+ loga_log(message: "#{item['class']} with jid: '#{item['jid']}' done", item: item)
18
16
  rescue Exception => e # rubocop:disable Lint/RescueException
19
- with_elapsed_time_context(start) do
20
- loga_log(
21
- message: "#{item['class']} with jid: '#{item['jid']}' fail", item: item,
22
- exception: e
23
- )
24
- end
17
+ ::Sidekiq::Context.current[:elapsed] = elapsed(start)
18
+
19
+ loga_log(
20
+ message: "#{item['class']} with jid: '#{item['jid']}' fail", item: item,
21
+ exception: e
22
+ )
25
23
 
26
24
  raise
27
25
  end
28
26
 
27
+ def prepare(job_hash, &block)
28
+ super
29
+ ensure
30
+ # For sidekiq version < 6.4
31
+ Thread.current[:sidekiq_context] = nil
32
+ end
33
+
29
34
  private
30
35
 
31
36
  def loga_log(message:, item:, exception: nil)
@@ -0,0 +1,51 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'sidekiq/job_logger'
4
+
5
+ module Loga
6
+ module Sidekiq7
7
+ class JobLogger < ::Sidekiq::JobLogger
8
+ EVENT_TYPE = 'sidekiq'.freeze
9
+
10
+ def call(item, _queue)
11
+ start = ::Process.clock_gettime(::Process::CLOCK_MONOTONIC)
12
+
13
+ yield
14
+
15
+ ::Sidekiq::Context.add(:elapsed, elapsed(start))
16
+
17
+ loga_log(message: "#{item['class']} with jid: '#{item['jid']}' done", item: item)
18
+ rescue Exception => e # rubocop:disable Lint/RescueException
19
+ ::Sidekiq::Context.add(:elapsed, elapsed(start))
20
+
21
+ loga_log(
22
+ message: "#{item['class']} with jid: '#{item['jid']}' fail", item: item,
23
+ exception: e
24
+ )
25
+
26
+ raise
27
+ end
28
+
29
+ private
30
+
31
+ def loga_log(message:, item:, exception: nil)
32
+ data = item.select do |k, _v|
33
+ %w[created_at enqueued_at jid queue retry
34
+ class].include? k
35
+ end
36
+
37
+ data['params'] = item['args']
38
+
39
+ data['exception'] = exception if exception
40
+
41
+ event = Event.new(type: EVENT_TYPE, message: message, data: data)
42
+
43
+ if exception
44
+ @logger.warn(event)
45
+ else
46
+ @logger.info(event)
47
+ end
48
+ end
49
+ end
50
+ end
51
+ end
data/lib/loga/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module Loga
2
- VERSION = '2.6.0'.freeze
2
+ VERSION = '2.7.0'.freeze
3
3
  end
@@ -0,0 +1,180 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'timecop'
5
+ require 'fakeredis'
6
+
7
+ dummy_redis_config = ConnectionPool.new(size: 5) { Redis.new }
8
+
9
+ Sidekiq.configure_client do |config|
10
+ config.redis = dummy_redis_config
11
+ end
12
+
13
+ Sidekiq.configure_server do |config|
14
+ config.redis = dummy_redis_config
15
+ end
16
+
17
+ class MySidekiqWorker
18
+ include Sidekiq::Worker
19
+
20
+ def perform(_name)
21
+ logger.info('Hello from MySidekiqWorker')
22
+ end
23
+ end
24
+
25
+ describe 'Sidekiq client logger' do
26
+ let(:mgr) do
27
+ # https://github.com/mperham/sidekiq/blob/v6.0.0/test/test_actors.rb#L57:79
28
+ Class.new do
29
+ attr_reader :latest_error
30
+ attr_reader :mutex
31
+ attr_reader :cond
32
+
33
+ def initialize
34
+ @mutex = ::Mutex.new
35
+ @cond = ::ConditionVariable.new
36
+ end
37
+
38
+ def processor_died(_inst, err)
39
+ @latest_error = err
40
+ @mutex.synchronize do
41
+ @cond.signal
42
+ end
43
+ end
44
+
45
+ def processor_stopped(_inst)
46
+ @mutex.synchronize do
47
+ @cond.signal
48
+ end
49
+ end
50
+
51
+ def options
52
+ {
53
+ concurrency: 3,
54
+ job_logger: Loga::Sidekiq6::JobLogger,
55
+ queues: ['default'],
56
+ }
57
+ end
58
+ end
59
+ end
60
+
61
+ let(:target) { StringIO.new }
62
+
63
+ def read_json_log(line:)
64
+ target.rewind
65
+ JSON.parse(target.each_line.drop(line - 1).first)
66
+ end
67
+
68
+ def dump_log
69
+ offset = target.pos
70
+
71
+ target.rewind
72
+ target.each_line { puts _1 }
73
+
74
+ target.pos = offset
75
+ end
76
+
77
+ before do
78
+ Redis.current.flushall
79
+
80
+ Loga.reset
81
+
82
+ Loga.configure(
83
+ service_name: 'hello_world_app',
84
+ service_version: '1.0',
85
+ device: target,
86
+ format: :gelf,
87
+ )
88
+ end
89
+
90
+ it 'has the proper job logger' do
91
+ expect(Sidekiq.options[:job_logger]).to eq Loga::Sidekiq6::JobLogger
92
+ end
93
+
94
+ it 'has the proper logger for Sidekiq.logger' do
95
+ expect(Sidekiq.logger).to eq Loga.logger
96
+ end
97
+
98
+ it 'pushes a new element in the default queue' do
99
+ MySidekiqWorker.perform_async('Bob')
100
+
101
+ last_element = JSON.parse(Redis.current.lpop('queue:default'))
102
+
103
+ aggregate_failures do
104
+ expect(last_element['class']).to eq 'MySidekiqWorker'
105
+ expect(last_element['args']).to eq ['Bob']
106
+ expect(last_element['retry']).to eq true
107
+ expect(last_element['queue']).to eq 'default'
108
+ end
109
+ end
110
+
111
+ def test_log_from_worker(json_line)
112
+ aggregate_failures do
113
+ expect(json_line).to include(
114
+ '_class' => 'MySidekiqWorker',
115
+ '_service.name' => 'hello_world_app',
116
+ '_service.version' => '1.0',
117
+ '_tags' => '',
118
+ 'level' => 6,
119
+ 'version' => '1.1',
120
+ 'short_message' => 'Hello from MySidekiqWorker',
121
+ )
122
+
123
+ %w[_jid timestamp host].each do |key|
124
+ expect(json_line).to have_key(key)
125
+ end
126
+
127
+ expect(json_line).not_to include('_duration')
128
+ end
129
+ end
130
+
131
+ def test_job_end_log(json_line) # rubocop:disable Metrics/MethodLength
132
+ aggregate_failures do
133
+ expect(json_line).to include(
134
+ '_queue' => 'default',
135
+ '_retry' => true,
136
+ '_params' => ['Bob'],
137
+ '_class' => 'MySidekiqWorker',
138
+ '_type' => 'sidekiq',
139
+ '_service.name' => 'hello_world_app',
140
+ '_service.version' => '1.0',
141
+ '_tags' => '',
142
+ 'level' => 6,
143
+ 'version' => '1.1',
144
+ )
145
+
146
+ %w[_created_at _enqueued_at _jid _duration timestamp host].each do |key|
147
+ expect(json_line).to have_key(key)
148
+ end
149
+
150
+ expect(json_line['_duration']).to be < 500
151
+ expect(json_line['short_message']).to match(/MySidekiqWorker with jid:*/)
152
+ end
153
+ end
154
+
155
+ it 'logs the job processing event' do
156
+ MySidekiqWorker.perform_async('Bob')
157
+
158
+ require 'sidekiq/processor'
159
+
160
+ Sidekiq::Processor.new(mgr.new).start
161
+
162
+ sleep 0.5
163
+
164
+ test_log_from_worker(read_json_log(line: 1))
165
+ test_job_end_log(read_json_log(line: 2))
166
+
167
+ # This was a bug - the duration was constantly incresing based on when
168
+ # the logger was created. https://github.com/FundingCircle/loga/pull/117
169
+ #
170
+ # Test that after sleeping for few seconds the duration is still under 500ms
171
+ sleep 1
172
+
173
+ MySidekiqWorker.perform_async('Bob')
174
+
175
+ sleep 1
176
+
177
+ test_log_from_worker(read_json_log(line: 3))
178
+ test_job_end_log(read_json_log(line: 4))
179
+ end
180
+ end