HornsAndHooves-sidekiq-limit_fetch 4.5.0
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 +7 -0
- data/.gitignore +4 -0
- data/.rspec +5 -0
- data/.rubocop.yml +34 -0
- data/.ruby-gemset +1 -0
- data/.ruby-version +1 -0
- data/CHANGELOG.md +37 -0
- data/Gemfile +4 -0
- data/LICENSE +22 -0
- data/README.md +165 -0
- data/Rakefile +14 -0
- data/bench/compare.rb +56 -0
- data/demo/Gemfile +8 -0
- data/demo/README.md +37 -0
- data/demo/Rakefile +100 -0
- data/demo/app/workers/a_worker.rb +10 -0
- data/demo/app/workers/b_worker.rb +10 -0
- data/demo/app/workers/c_worker.rb +10 -0
- data/demo/app/workers/fast_worker.rb +10 -0
- data/demo/app/workers/slow_worker.rb +10 -0
- data/demo/config/application.rb +13 -0
- data/demo/config/boot.rb +4 -0
- data/demo/config/environment.rb +4 -0
- data/demo/config/environments/development.rb +11 -0
- data/lib/sidekiq/extensions/manager.rb +21 -0
- data/lib/sidekiq/extensions/queue.rb +27 -0
- data/lib/sidekiq/limit_fetch/global/monitor.rb +83 -0
- data/lib/sidekiq/limit_fetch/global/selector.rb +130 -0
- data/lib/sidekiq/limit_fetch/global/semaphore.rb +190 -0
- data/lib/sidekiq/limit_fetch/instances.rb +29 -0
- data/lib/sidekiq/limit_fetch/queues.rb +197 -0
- data/lib/sidekiq/limit_fetch/unit_of_work.rb +28 -0
- data/lib/sidekiq/limit_fetch.rb +76 -0
- data/lib/sidekiq-limit_fetch.rb +3 -0
- data/sidekiq-limit_fetch.gemspec +30 -0
- data/spec/sidekiq/extensions/manager_spec.rb +13 -0
- data/spec/sidekiq/extensions/queue_spec.rb +96 -0
- data/spec/sidekiq/limit_fetch/global/monitor_spec.rb +114 -0
- data/spec/sidekiq/limit_fetch/queues_spec.rb +127 -0
- data/spec/sidekiq/limit_fetch/semaphore_spec.rb +65 -0
- data/spec/sidekiq/limit_fetch_spec.rb +58 -0
- data/spec/spec_helper.rb +34 -0
- metadata +179 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA256:
|
|
3
|
+
metadata.gz: 87f74cf9c2b4a225260785a8793e7616f99f4e49215517b6edbc352fd055a9a9
|
|
4
|
+
data.tar.gz: '0439c9cd2c4950cc826e67245e5cb7a7c377d49158a8a4cdc16d4e0a08d497d6'
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: 25bbb48cfa97773220546d0fe1bd0dce302b1b5f155fa2b36949ea8bb8fdd3204ece5d8ef107b3abf0164a6fcadc169119b959ed67a80552a1a6b4d1e5c3af29
|
|
7
|
+
data.tar.gz: 10e9df0a5823b98eeb684ba0ed4787b057b6bd2a7b62780f6fc288419bf6ac5ab67d678b8c7b1a911cd318f8ef3058aad4c12e6d3f35627f4d4269e87f80456b
|
data/.gitignore
ADDED
data/.rspec
ADDED
data/.rubocop.yml
ADDED
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
AllCops:
|
|
2
|
+
NewCops: enable
|
|
3
|
+
SuggestExtensions: false
|
|
4
|
+
TargetRubyVersion: 2.7
|
|
5
|
+
Exclude:
|
|
6
|
+
- 'gemfiles/*'
|
|
7
|
+
|
|
8
|
+
Style/Documentation:
|
|
9
|
+
Enabled: false
|
|
10
|
+
|
|
11
|
+
Metrics/BlockLength:
|
|
12
|
+
Exclude:
|
|
13
|
+
- 'spec/**/*.rb'
|
|
14
|
+
- 'demo/Rakefile'
|
|
15
|
+
|
|
16
|
+
Metrics/ModuleLength:
|
|
17
|
+
Exclude:
|
|
18
|
+
- 'lib/sidekiq/limit_fetch/queues.rb'
|
|
19
|
+
|
|
20
|
+
Metrics/ClassLength:
|
|
21
|
+
Exclude:
|
|
22
|
+
- 'lib/sidekiq/limit_fetch/global/semaphore.rb'
|
|
23
|
+
|
|
24
|
+
Naming/VariableNumber:
|
|
25
|
+
EnforcedStyle: snake_case
|
|
26
|
+
|
|
27
|
+
Naming/FileName:
|
|
28
|
+
Exclude:
|
|
29
|
+
- lib/sidekiq-limit_fetch.rb
|
|
30
|
+
|
|
31
|
+
Gemspec/DevelopmentDependencies:
|
|
32
|
+
EnforcedStyle: gemspec
|
|
33
|
+
Exclude:
|
|
34
|
+
- 'demo/*'
|
data/.ruby-gemset
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
sidekiq-limit_fetch
|
data/.ruby-version
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
3.3.9
|
data/CHANGELOG.md
ADDED
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
## [4.5.0] - 2026-06-15
|
|
4
|
+
|
|
5
|
+
This project was taken over by [@HornsAndHooves](https://github.com/HornsAndHooves)
|
|
6
|
+
|
|
7
|
+
- Remove compatibility with Sidekiq < 8
|
|
8
|
+
- Fix issue with queue weights specified via CLI not processing jobs
|
|
9
|
+
|
|
10
|
+
## [4.3.2] - 2022-09-01
|
|
11
|
+
|
|
12
|
+
- #139 - Fix Redis deprecation warnings from [@adamzapasnik](https://github.com/adamzapasnik)
|
|
13
|
+
|
|
14
|
+
## [4.3.1] - 2022-08-23
|
|
15
|
+
|
|
16
|
+
- #137 - Fix deprecation of passing timeout as positional argument to brpop from [@cgunther](https://github.com/cgunther)
|
|
17
|
+
|
|
18
|
+
## [4.3.0] - 2022-08-16
|
|
19
|
+
|
|
20
|
+
- #135 - Some extra fixes for Sidekiq 6.5 (fixes #128, #130, #131) from [@BobbyMcWho](https://github.com/BobbyMcWho)
|
|
21
|
+
|
|
22
|
+
## [4.2.0] - 2022-06-09
|
|
23
|
+
|
|
24
|
+
- #127 - Fix for Sidekiq 6.5 internal change vias PR #128 from [@evgeniradev][https://github.com/evgeniradev]
|
|
25
|
+
- testing changes: stop supporting Sidekiq < 6, add tests for Sidekiq 6.5, stop testing on ruby 2.6 EOL
|
|
26
|
+
|
|
27
|
+
## [4.1.0] - 2022-03-29
|
|
28
|
+
|
|
29
|
+
- #101 - Fix stuck queues bug on Redis restart from [@907th](https://github.com/907th).
|
|
30
|
+
|
|
31
|
+
## [4.0.0] - 2022-03-26
|
|
32
|
+
|
|
33
|
+
This project was taken over by [@deanpcmad](https://github.com/deanpcmad)
|
|
34
|
+
|
|
35
|
+
- #120 - Migrate CI to GitHub Actions from [@petergoldstein](https://github.com/petergoldstein).
|
|
36
|
+
- #124 - Fixed redis v4.6.0 pipelines deprecation warning from [@iurev](https://github.com/iurev).
|
|
37
|
+
- #83 - Processing dynamic queues from [@alexey-yanchenko](https://github.com/alexey-yanchenko).
|
data/Gemfile
ADDED
data/LICENSE
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2022 Dean Perry
|
|
4
|
+
Copyright (c) 2013 brainopia
|
|
5
|
+
|
|
6
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
7
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
8
|
+
in the Software without restriction, including without limitation the rights
|
|
9
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
10
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
11
|
+
furnished to do so, subject to the following conditions:
|
|
12
|
+
|
|
13
|
+
The above copyright notice and this permission notice shall be included in all
|
|
14
|
+
copies or substantial portions of the Software.
|
|
15
|
+
|
|
16
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
17
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
18
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
19
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
20
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
21
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
22
|
+
SOFTWARE.
|
data/README.md
ADDED
|
@@ -0,0 +1,165 @@
|
|
|
1
|
+
## Description
|
|
2
|
+
|
|
3
|
+
*This is a fork of <https://github.com/deanpcmad/sidekiq-limit_fetch>. This version does not support Sidekiq < 8, if you are using a Sidekiq version below v8 you must use the original gem.*
|
|
4
|
+
|
|
5
|
+
Sidekiq strategy to support a granular queue control – limiting, pausing, blocking, querying.
|
|
6
|
+
|
|
7
|
+
### Installation
|
|
8
|
+
|
|
9
|
+
Add this line to your application's Gemfile:
|
|
10
|
+
|
|
11
|
+
```
|
|
12
|
+
gem 'HornsAndHooves-sidekiq-limit_fetch'
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
Then `bundle install`.
|
|
16
|
+
|
|
17
|
+
### Limitations
|
|
18
|
+
|
|
19
|
+
> [!WARNING]
|
|
20
|
+
> At this moment, `sidekiq-limit_fetch` is incompatible with
|
|
21
|
+
> Sidekiq Pro's [super_fetch](https://github.com/sidekiq/sidekiq/wiki/Reliability#using-super_fetch),
|
|
22
|
+
> [sidekiq-rate-limiter](https://github.com/enova/sidekiq-rate-limiter),
|
|
23
|
+
> and any other plugin that rewrites fetch strategy of Sidekiq.
|
|
24
|
+
|
|
25
|
+
### Usage
|
|
26
|
+
|
|
27
|
+
If you are using this with Rails, you don't need to require it as it's done automatically.
|
|
28
|
+
|
|
29
|
+
To use this Gem in other Ruby projects, just add `require 'HornsAndHooves-sidekiq-limit_fetch'`.
|
|
30
|
+
|
|
31
|
+
### Limits
|
|
32
|
+
|
|
33
|
+
Specify limits which you want to place on queues inside `sidekiq.yml`:
|
|
34
|
+
|
|
35
|
+
```yaml
|
|
36
|
+
:limits:
|
|
37
|
+
queue_name1: 5
|
|
38
|
+
queue_name2: 10
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
Or set it dynamically in your code:
|
|
42
|
+
```ruby
|
|
43
|
+
Sidekiq::Queue['queue_name1'].limit = 5
|
|
44
|
+
Sidekiq::Queue['queue_name2'].limit = 10
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
In these examples, tasks for the `queue_name1` will be run by at most 5
|
|
48
|
+
workers at the same time and the `queue_name2` will have no more than 10
|
|
49
|
+
workers simultaneously.
|
|
50
|
+
|
|
51
|
+
Ability to set limits dynamically allows you to resize worker
|
|
52
|
+
distribution among queues any time you want.
|
|
53
|
+
|
|
54
|
+
### Limits per process
|
|
55
|
+
|
|
56
|
+
If you use multiple Sidekiq processes then you can specify limits per process:
|
|
57
|
+
|
|
58
|
+
```yaml
|
|
59
|
+
:process_limits:
|
|
60
|
+
queue_name: 2
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
Or set it in your code:
|
|
64
|
+
|
|
65
|
+
```ruby
|
|
66
|
+
Sidekiq::Queue['queue_name'].process_limit = 2
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
### Busy workers by queue
|
|
70
|
+
|
|
71
|
+
You can see how many workers currently handling a queue:
|
|
72
|
+
|
|
73
|
+
```ruby
|
|
74
|
+
Sidekiq::Queue['name'].busy # number of busy workers
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
### Pauses
|
|
78
|
+
|
|
79
|
+
You can also pause your queues temporarily. Upon continuing their limits
|
|
80
|
+
will be preserved.
|
|
81
|
+
|
|
82
|
+
```ruby
|
|
83
|
+
Sidekiq::Queue['name'].pause # prevents workers from running tasks from this queue
|
|
84
|
+
Sidekiq::Queue['name'].paused? # => true
|
|
85
|
+
Sidekiq::Queue['name'].unpause # allows workers to use the queue
|
|
86
|
+
Sidekiq::Queue['name'].pause_for_ms(1000) # will pause for a second
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
### Blocking queue mode
|
|
90
|
+
|
|
91
|
+
If you use strict queue ordering (it will be used if you don't specify queue weights)
|
|
92
|
+
then you can set blocking status for queues. It means if a blocking
|
|
93
|
+
queue task is executing then no new task from lesser priority queues will
|
|
94
|
+
be ran. Eg,
|
|
95
|
+
|
|
96
|
+
```yaml
|
|
97
|
+
:queues:
|
|
98
|
+
- a
|
|
99
|
+
- b
|
|
100
|
+
- c
|
|
101
|
+
:blocking:
|
|
102
|
+
- b
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
In this case when a task for `b` queue is ran no new task from `c` queue
|
|
106
|
+
will be started.
|
|
107
|
+
|
|
108
|
+
You can also enable and disable blocking mode for queues on the fly:
|
|
109
|
+
|
|
110
|
+
```ruby
|
|
111
|
+
Sidekiq::Queue['name'].block
|
|
112
|
+
Sidekiq::Queue['name'].blocking? # => true
|
|
113
|
+
Sidekiq::Queue['name'].unblock
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
### Advanced blocking queues
|
|
117
|
+
|
|
118
|
+
You can also block on array of queues. It means when any of them is
|
|
119
|
+
running only queues higher and queues from their blocking group can
|
|
120
|
+
run. It will be easier to understand with an example:
|
|
121
|
+
|
|
122
|
+
```yaml
|
|
123
|
+
:queues:
|
|
124
|
+
- a
|
|
125
|
+
- b
|
|
126
|
+
- c
|
|
127
|
+
- d
|
|
128
|
+
:blocking:
|
|
129
|
+
- [b, c]
|
|
130
|
+
```
|
|
131
|
+
|
|
132
|
+
In this case tasks from `d` will be blocked when a task from queue `b` or `c` is executed.
|
|
133
|
+
|
|
134
|
+
You can dynamically set exceptions for queue blocking:
|
|
135
|
+
|
|
136
|
+
```ruby
|
|
137
|
+
Sidekiq::Queue['queue1'].block_except 'queue2'
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
### Dynamic queues
|
|
141
|
+
|
|
142
|
+
You can support dynamic queues (that are not listed in `sidekiq.yml` but
|
|
143
|
+
that have tasks pushed to them (usually with `Sidekiq::Client.push`)).
|
|
144
|
+
|
|
145
|
+
To use this mode you need to specify a following line in `sidekiq.yml`:
|
|
146
|
+
|
|
147
|
+
```yaml
|
|
148
|
+
:dynamic: true
|
|
149
|
+
```
|
|
150
|
+
|
|
151
|
+
or
|
|
152
|
+
|
|
153
|
+
```yaml
|
|
154
|
+
:dynamic:
|
|
155
|
+
:exclude:
|
|
156
|
+
- excluded_queue
|
|
157
|
+
```
|
|
158
|
+
|
|
159
|
+
to exclude `excluded_queue` from dynamic queue
|
|
160
|
+
|
|
161
|
+
Dynamic queues will be ran at the lowest priority.
|
|
162
|
+
|
|
163
|
+
### Maintenance
|
|
164
|
+
|
|
165
|
+
If you use `flushdb`, restart the Sidekiq process to re-populate the dynamic configuration.
|
data/Rakefile
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'bundler/gem_tasks'
|
|
4
|
+
require 'rspec/core/rake_task'
|
|
5
|
+
|
|
6
|
+
RSpec::Core::RakeTask.new
|
|
7
|
+
|
|
8
|
+
task :default do
|
|
9
|
+
rspec = Rake::Task[:spec]
|
|
10
|
+
rspec.invoke
|
|
11
|
+
ENV['namespace'] = 'namespace'
|
|
12
|
+
rspec.reenable
|
|
13
|
+
rspec.invoke
|
|
14
|
+
end
|
data/bench/compare.rb
ADDED
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'benchmark'
|
|
4
|
+
require 'sidekiq/cli'
|
|
5
|
+
require 'sidekiq/api'
|
|
6
|
+
|
|
7
|
+
total = (ARGV.shift || 50).to_i
|
|
8
|
+
concurrency = ARGV.shift || 1
|
|
9
|
+
limit = ARGV.shift
|
|
10
|
+
|
|
11
|
+
if limit
|
|
12
|
+
limit = nil if limit == 'nil'
|
|
13
|
+
|
|
14
|
+
$LOAD_PATH.unshift File.expand_path '../lib'
|
|
15
|
+
require 'sidekiq-limit_fetch'
|
|
16
|
+
Sidekiq::Queue['inline'].limit = limit
|
|
17
|
+
Sidekiq.redis { |it| it.del 'limit_fetch:probed:inline' }
|
|
18
|
+
Sidekiq::LimitFetch::Queues.send(:define_method, :set) { |*| } # rubocop:disable Lint/EmptyBlock
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
Sidekiq::Queue.new('inline').clear
|
|
22
|
+
|
|
23
|
+
class FastJob
|
|
24
|
+
include Sidekiq::Worker
|
|
25
|
+
sidekiq_options queue: :inline
|
|
26
|
+
|
|
27
|
+
def perform(index)
|
|
28
|
+
puts "job N#{index} is finished"
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
class FinishJob
|
|
33
|
+
include Sidekiq::Worker
|
|
34
|
+
sidekiq_options queue: :inline
|
|
35
|
+
|
|
36
|
+
def perform
|
|
37
|
+
Process.kill 'INT', 0
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
total.times { |i| FastJob.perform_async i + 1 }
|
|
42
|
+
FinishJob.perform_async
|
|
43
|
+
|
|
44
|
+
Sidekiq::CLI.instance.tap do |cli|
|
|
45
|
+
%w[validate! boot_system].each { |stub| cli.define_singleton_method(stub) {} } # rubocop:disable Lint/EmptyBlock
|
|
46
|
+
cli.parse ['-q inline', '-q other', "-c #{concurrency}"]
|
|
47
|
+
|
|
48
|
+
# rubocop:disable Lint/RescueException
|
|
49
|
+
# rubocop:disable Lint/SuppressedException
|
|
50
|
+
puts Benchmark.measure do
|
|
51
|
+
cli.run
|
|
52
|
+
rescue Exception
|
|
53
|
+
end
|
|
54
|
+
# rubocop:enable Lint/SuppressedException
|
|
55
|
+
# rubocop:enable Lint/RescueException
|
|
56
|
+
end
|
data/demo/Gemfile
ADDED
data/demo/README.md
ADDED
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
This is a demo rails app with a configured sidekiq-limit_fetch.
|
|
2
|
+
|
|
3
|
+
Its purpose is to check whether plugin works in certain situations.
|
|
4
|
+
|
|
5
|
+
Application is preconfigured with two workers:
|
|
6
|
+
- `app/workers/fast_worker.rb` which does `sleep 0.2`
|
|
7
|
+
- `app/workers/slow_worker.rb` which does `sleep 1`
|
|
8
|
+
|
|
9
|
+
There is also a rake task which can be invoked as `bundle exec rake demo:limit`:
|
|
10
|
+
|
|
11
|
+
- it prefills sidekiq tasks
|
|
12
|
+
|
|
13
|
+
```ruby
|
|
14
|
+
100.times do
|
|
15
|
+
SlowWorker.perform_async
|
|
16
|
+
FastWorker.perform_async
|
|
17
|
+
end
|
|
18
|
+
```
|
|
19
|
+
- sets sidekiq config
|
|
20
|
+
|
|
21
|
+
```yaml
|
|
22
|
+
:verbose: false
|
|
23
|
+
:concurrency: 4
|
|
24
|
+
:queues:
|
|
25
|
+
- slow
|
|
26
|
+
- fast
|
|
27
|
+
:limits:
|
|
28
|
+
slow: 1
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
- and launches a sidekiq admin page with overview of queues in browser.
|
|
32
|
+
The page is set to live-poll so effects of limits can be seen directly.
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
To change simulation modify `Rakefile` or workers.
|
|
36
|
+
|
|
37
|
+
Any bugs related to the plugin should be demonstrated with a reproduction from this base app.
|
data/demo/Rakefile
ADDED
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require File.expand_path('config/application', __dir__)
|
|
4
|
+
Demo::Application.load_tasks
|
|
5
|
+
|
|
6
|
+
namespace :demo do
|
|
7
|
+
task limit: :environment do
|
|
8
|
+
puts '=> Creating sidekiq tasks'
|
|
9
|
+
|
|
10
|
+
100.times do
|
|
11
|
+
SlowWorker.perform_async
|
|
12
|
+
FastWorker.perform_async
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
run_sidekiq_monitoring
|
|
16
|
+
run_sidekiq_workers config: <<-YAML
|
|
17
|
+
:verbose: false
|
|
18
|
+
:concurrency: 4
|
|
19
|
+
:queues:
|
|
20
|
+
- slow
|
|
21
|
+
- fast
|
|
22
|
+
:limits:
|
|
23
|
+
slow: 1
|
|
24
|
+
YAML
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
task blocking: :environment do
|
|
28
|
+
puts '=> Creating sidekiq tasks'
|
|
29
|
+
|
|
30
|
+
AWorker.perform_async
|
|
31
|
+
BWorker.perform_async
|
|
32
|
+
CWorker.perform_async
|
|
33
|
+
|
|
34
|
+
run_sidekiq_monitoring
|
|
35
|
+
run_sidekiq_workers config: <<-YAML
|
|
36
|
+
:verbose: false
|
|
37
|
+
:concurrency: 4
|
|
38
|
+
:queues:
|
|
39
|
+
- a
|
|
40
|
+
- b
|
|
41
|
+
- c
|
|
42
|
+
:blocking:
|
|
43
|
+
- a
|
|
44
|
+
YAML
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
task advanced_blocking: :environment do
|
|
48
|
+
puts '=> Creating sidekiq tasks'
|
|
49
|
+
|
|
50
|
+
AWorker.perform_async
|
|
51
|
+
BWorker.perform_async
|
|
52
|
+
CWorker.perform_async
|
|
53
|
+
|
|
54
|
+
run_sidekiq_monitoring
|
|
55
|
+
run_sidekiq_workers config: <<-YAML
|
|
56
|
+
:verbose: false
|
|
57
|
+
:concurrency: 4
|
|
58
|
+
:queues:
|
|
59
|
+
- a
|
|
60
|
+
- b
|
|
61
|
+
- c
|
|
62
|
+
:blocking:
|
|
63
|
+
- [a, b]
|
|
64
|
+
YAML
|
|
65
|
+
end
|
|
66
|
+
def with_sidekiq_config(config)
|
|
67
|
+
whitespace_offset = config[/\A */].size
|
|
68
|
+
config.gsub!(/^ {#{whitespace_offset}}/, '')
|
|
69
|
+
|
|
70
|
+
puts "=> Use sidekiq config:\n#{config}"
|
|
71
|
+
File.write 'config/sidekiq.yml', config
|
|
72
|
+
yield
|
|
73
|
+
ensure
|
|
74
|
+
FileUtils.rm 'config/sidekiq.yml'
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
def run_sidekiq_monitoring
|
|
78
|
+
require 'sidekiq/web'
|
|
79
|
+
Thread.new do
|
|
80
|
+
Rack::Server.start app: Sidekiq::Web, Port: 3000
|
|
81
|
+
end
|
|
82
|
+
sleep 1
|
|
83
|
+
Launchy.open 'http://127.0.0.1:3000/busy?poll=true'
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
def run_sidekiq_workers(options)
|
|
87
|
+
require 'sidekiq/cli'
|
|
88
|
+
cli = Sidekiq::CLI.instance
|
|
89
|
+
|
|
90
|
+
%w[validate! boot_system].each do |stub|
|
|
91
|
+
cli.define_singleton_method(stub) {} # rubocop:disable Lint/EmptyBlock
|
|
92
|
+
end
|
|
93
|
+
|
|
94
|
+
with_sidekiq_config options[:config] do
|
|
95
|
+
cli.send :setup_options, []
|
|
96
|
+
end
|
|
97
|
+
|
|
98
|
+
cli.run
|
|
99
|
+
end
|
|
100
|
+
end
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require File.expand_path('boot', __dir__)
|
|
4
|
+
|
|
5
|
+
require 'action_controller/railtie'
|
|
6
|
+
require 'action_mailer/railtie'
|
|
7
|
+
require 'sprockets/railtie'
|
|
8
|
+
|
|
9
|
+
Bundler.require(:default, Rails.env)
|
|
10
|
+
|
|
11
|
+
module Demo
|
|
12
|
+
Application = Class.new Rails::Application
|
|
13
|
+
end
|
data/demo/config/boot.rb
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
Demo::Application.configure do
|
|
4
|
+
config.cache_classes = false
|
|
5
|
+
config.eager_load = false
|
|
6
|
+
config.consider_all_requests_local = true
|
|
7
|
+
config.action_controller.perform_caching = false
|
|
8
|
+
config.action_mailer.raise_delivery_errors = false
|
|
9
|
+
config.active_support.deprecation = :log
|
|
10
|
+
config.assets.debug = true
|
|
11
|
+
end
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Sidekiq
|
|
4
|
+
class Manager
|
|
5
|
+
module InitLimitFetch
|
|
6
|
+
def initialize(capsule)
|
|
7
|
+
capsule.config[:fetch_class] = Sidekiq::LimitFetch
|
|
8
|
+
super
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def start
|
|
12
|
+
# In sidekiq 6.5.0 the variable @options has been renamed to @config
|
|
13
|
+
Sidekiq::LimitFetch::Queues.start @config
|
|
14
|
+
Sidekiq::LimitFetch::Global::Monitor.start!
|
|
15
|
+
super
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
prepend InitLimitFetch
|
|
20
|
+
end
|
|
21
|
+
end
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Sidekiq
|
|
4
|
+
class Queue
|
|
5
|
+
extend Forwardable
|
|
6
|
+
extend LimitFetch::Instances
|
|
7
|
+
attr_reader :rname
|
|
8
|
+
|
|
9
|
+
def_delegators :lock,
|
|
10
|
+
:limit, :limit=, :limit_changed?,
|
|
11
|
+
:process_limit, :process_limit=,
|
|
12
|
+
:acquire, :release,
|
|
13
|
+
:pause, :pause_for_ms, :unpause,
|
|
14
|
+
:block, :unblock,
|
|
15
|
+
:paused?, :blocking?,
|
|
16
|
+
:unblocked, :block_except,
|
|
17
|
+
:probed, :busy,
|
|
18
|
+
:increase_busy, :decrease_busy,
|
|
19
|
+
:local_busy?, :explain,
|
|
20
|
+
:remove_locks_except!,
|
|
21
|
+
:clear_limits
|
|
22
|
+
|
|
23
|
+
def lock
|
|
24
|
+
@lock ||= LimitFetch::Global::Semaphore.new name
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|