delayed_job 4.1.2 → 4.1.3
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 +4 -4
- data/CHANGELOG.md +10 -0
- data/README.md +8 -3
- data/delayed_job.gemspec +2 -2
- data/lib/delayed/backend/base.rb +4 -7
- data/lib/delayed/backend/job_preparer.rb +3 -1
- data/lib/delayed/backend/shared_spec.rb +6 -0
- data/lib/delayed/command.rb +6 -1
- data/lib/delayed/exceptions.rb +1 -1
- data/lib/delayed/lifecycle.rb +1 -1
- data/lib/delayed/message_sending.rb +27 -25
- data/lib/delayed/performable_method.rb +2 -0
- data/lib/delayed/psych_ext.rb +1 -1
- data/lib/delayed/worker.rb +13 -3
- data/lib/delayed_job.rb +2 -1
- data/lib/generators/delayed_job/delayed_job_generator.rb +1 -1
- data/spec/autoloaded/clazz.rb +1 -2
- data/spec/autoloaded/instance_clazz.rb +1 -2
- data/spec/autoloaded/instance_struct.rb +1 -2
- data/spec/autoloaded/struct.rb +1 -2
- data/spec/message_sending_spec.rb +9 -5
- data/spec/performable_method_spec.rb +1 -2
- data/spec/worker_spec.rb +9 -1
- metadata +5 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 5e2fe748c9a94faf96700fa8f87466b6fe7fd079
|
4
|
+
data.tar.gz: 21d55a1f49084db05123ad5573711ef7a52f7c29
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: cadfae1e2a548b451dc336f033ae671bd005c5b17fa311c5af3a306851b6d5642fcc88bee79ebbc9826032e9dccdf5f58eb0315de63e3357106987f496009f69
|
7
|
+
data.tar.gz: 2a07509ecd676d248ca983a3ba87062cf1b11a8bdc67f0cd63ab91a2c975e8f840b323bba8ae9596aa15db2435702484763acd7688adaf39b492910fffead165
|
data/CHANGELOG.md
CHANGED
@@ -1,4 +1,14 @@
|
|
1
|
+
4.1.3 - 2017-05-26
|
2
|
+
=================
|
3
|
+
* Don't mutate the options hash (#877)
|
4
|
+
* Log an error message when a deserialization error occurs (#894)
|
5
|
+
* Adding the queue name to the log output (#917)
|
6
|
+
* Don't include ClassMethods with MessageSending (#924)
|
7
|
+
* Fix YAML deserialization error if original object is soft-deleted (#947)
|
8
|
+
* Add support for Rails 5.1 (#982)
|
9
|
+
|
1
10
|
4.1.2 - 2016-05-16
|
11
|
+
==================
|
2
12
|
* Added Delayed::Worker.queue_attributes
|
3
13
|
* Limit what we require in ActiveSupport
|
4
14
|
* Fix pid file creation when there is no tmp directory
|
data/README.md
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
**If you're viewing this at https://github.com/collectiveidea/delayed_job,
|
2
2
|
you're reading the documentation for the master branch.
|
3
3
|
[View documentation for the latest release
|
4
|
-
(4.1.
|
4
|
+
(4.1.3).](https://github.com/collectiveidea/delayed_job/tree/v4.1.3)**
|
5
5
|
|
6
6
|
Delayed::Job
|
7
7
|
============
|
@@ -37,8 +37,7 @@ multitude of core tasks. Amongst those tasks are:
|
|
37
37
|
|
38
38
|
Installation
|
39
39
|
============
|
40
|
-
delayed_job 3.0.0 only supports Rails 3.0+.
|
41
|
-
branch](https://github.com/collectiveidea/delayed_job/tree/v2.0) for Rails 2.
|
40
|
+
delayed_job 3.0.0 only supports Rails 3.0+.
|
42
41
|
|
43
42
|
delayed_job supports multiple backends for storing the job queue. [See the wiki
|
44
43
|
for other backends](https://github.com/collectiveidea/delayed_job/wiki/Backends).
|
@@ -220,6 +219,12 @@ Configured queue priorities can be overriden by passing priority to the delay me
|
|
220
219
|
object.delay(:queue => 'high_priority', priority: 0).method
|
221
220
|
```
|
222
221
|
|
222
|
+
You can start processes to only work certain queues with the `queue` and `queues`
|
223
|
+
options defined below. Processes started without specifying a queue will run jobs
|
224
|
+
from **any** queue. To effectively have a process that runs jobs where a queue is not
|
225
|
+
specified, set a default queue name with `Delayed::Worker.default_queue_name` and
|
226
|
+
have the processes run that queue.
|
227
|
+
|
223
228
|
Running Jobs
|
224
229
|
============
|
225
230
|
`script/delayed_job` can be used to manage a background process which will
|
data/delayed_job.gemspec
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
# -*- encoding: utf-8 -*-
|
2
2
|
|
3
3
|
Gem::Specification.new do |spec|
|
4
|
-
spec.add_dependency 'activesupport', ['>= 3.0', '< 5.
|
4
|
+
spec.add_dependency 'activesupport', ['>= 3.0', '< 5.2']
|
5
5
|
spec.authors = ['Brandon Keepers', 'Brian Ryckbost', 'Chris Gaffney', 'David Genord II', 'Erik Michaels-Ober', 'Matt Griffin', 'Steve Richert', 'Tobias Lütke']
|
6
6
|
spec.description = 'Delayed_job (or DJ) encapsulates the common pattern of asynchronously executing longer tasks in the background. It is a direct extraction from Shopify where the job table is responsible for a multitude of core tasks.'
|
7
7
|
spec.email = ['brian@collectiveidea.com']
|
@@ -13,5 +13,5 @@ Gem::Specification.new do |spec|
|
|
13
13
|
spec.require_paths = ['lib']
|
14
14
|
spec.summary = 'Database-backed asynchronous priority queue system -- Extracted from Shopify'
|
15
15
|
spec.test_files = Dir.glob('spec/**/*')
|
16
|
-
spec.version = '4.1.
|
16
|
+
spec.version = '4.1.3'
|
17
17
|
end
|
data/lib/delayed/backend/base.rb
CHANGED
@@ -30,16 +30,13 @@ module Delayed
|
|
30
30
|
end
|
31
31
|
|
32
32
|
# Allow the backend to attempt recovery from reserve errors
|
33
|
-
def recover_from(_error)
|
34
|
-
end
|
33
|
+
def recover_from(_error); end
|
35
34
|
|
36
35
|
# Hook method that is called before a new worker is forked
|
37
|
-
def before_fork
|
38
|
-
end
|
36
|
+
def before_fork; end
|
39
37
|
|
40
38
|
# Hook method that is called after a new worker is forked
|
41
|
-
def after_fork
|
42
|
-
end
|
39
|
+
def after_fork; end
|
43
40
|
|
44
41
|
def work_off(num = 100)
|
45
42
|
warn '[DEPRECATION] `Delayed::Job.work_off` is deprecated. Use `Delayed::Worker.new.work_off instead.'
|
@@ -101,7 +98,7 @@ module Delayed
|
|
101
98
|
def hook(name, *args)
|
102
99
|
if payload_object.respond_to?(name)
|
103
100
|
method = payload_object.method(name)
|
104
|
-
method.arity
|
101
|
+
method.arity.zero? ? method.call : method.call(self, *args)
|
105
102
|
end
|
106
103
|
rescue DeserializationError # rubocop:disable HandleExceptions
|
107
104
|
end
|
@@ -4,7 +4,7 @@ module Delayed
|
|
4
4
|
attr_reader :options, :args
|
5
5
|
|
6
6
|
def initialize(*args)
|
7
|
-
@options = args.extract_options
|
7
|
+
@options = args.extract_options!.dup
|
8
8
|
@args = args
|
9
9
|
end
|
10
10
|
|
@@ -42,9 +42,11 @@ module Delayed
|
|
42
42
|
options[:run_at] = args[1]
|
43
43
|
end
|
44
44
|
|
45
|
+
# rubocop:disable GuardClause
|
45
46
|
unless options[:payload_object].respond_to?(:perform)
|
46
47
|
raise ArgumentError, 'Cannot enqueue items which do not respond to perform'
|
47
48
|
end
|
49
|
+
# rubocop:enabled GuardClause
|
48
50
|
end
|
49
51
|
end
|
50
52
|
end
|
@@ -113,6 +113,12 @@ shared_examples_for 'a delayed_job backend' do
|
|
113
113
|
job = described_class.enqueue M::ModuleJob.new
|
114
114
|
expect { job.invoke_job }.to change { M::ModuleJob.runs }.from(0).to(1)
|
115
115
|
end
|
116
|
+
|
117
|
+
it 'does not mutate the options hash' do
|
118
|
+
options = {:priority => 1}
|
119
|
+
described_class.enqueue SimpleJob.new, options
|
120
|
+
expect(options).to eq(:priority => 1)
|
121
|
+
end
|
116
122
|
end
|
117
123
|
|
118
124
|
context 'with delay_jobs = false' do
|
data/lib/delayed/command.rb
CHANGED
@@ -77,8 +77,11 @@ module Delayed
|
|
77
77
|
opt.on('--exit-on-complete', 'Exit when no more jobs are available to run. This will exit if all jobs are scheduled to run in the future.') do
|
78
78
|
@options[:exit_on_complete] = true
|
79
79
|
end
|
80
|
+
opt.on('--daemon-options a, b, c', Array, 'options to be passed through to daemons gem') do |daemon_options|
|
81
|
+
@daemon_options = daemon_options
|
82
|
+
end
|
80
83
|
end
|
81
|
-
@args = opts.parse!(args)
|
84
|
+
@args = opts.parse!(args) + (@daemon_options || [])
|
82
85
|
end
|
83
86
|
|
84
87
|
def daemonize # rubocop:disable PerceivedComplexity
|
@@ -88,11 +91,13 @@ module Delayed
|
|
88
91
|
if worker_pools
|
89
92
|
setup_pools
|
90
93
|
elsif @options[:identifier]
|
94
|
+
# rubocop:disable GuardClause
|
91
95
|
if worker_count > 1
|
92
96
|
raise ArgumentError, 'Cannot specify both --number-of-workers and --identifier'
|
93
97
|
else
|
94
98
|
run_process("delayed_job.#{@options[:identifier]}", @options)
|
95
99
|
end
|
100
|
+
# rubocop:enable GuardClause
|
96
101
|
else
|
97
102
|
worker_count.times do |worker_index|
|
98
103
|
process_name = worker_count == 1 ? 'delayed_job' : "delayed_job.#{worker_index}"
|
data/lib/delayed/exceptions.rb
CHANGED
data/lib/delayed/lifecycle.rb
CHANGED
@@ -6,9 +6,11 @@ module Delayed
|
|
6
6
|
@options = options
|
7
7
|
end
|
8
8
|
|
9
|
+
# rubocop:disable MethodMissing
|
9
10
|
def method_missing(method, *args)
|
10
11
|
Job.enqueue({:payload_object => @payload_class.new(@target, method.to_sym, args)}.merge(@options))
|
11
12
|
end
|
13
|
+
# rubocop:enable MethodMissing
|
12
14
|
end
|
13
15
|
|
14
16
|
module MessageSending
|
@@ -26,36 +28,36 @@ module Delayed
|
|
26
28
|
warn '[DEPRECATION] `object.send_at(time, :method)` is deprecated. Use `object.delay(:run_at => time).method'
|
27
29
|
__delay__(:run_at => time).__send__(method, *args)
|
28
30
|
end
|
31
|
+
end
|
29
32
|
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
end
|
33
|
+
module MessageSendingClassMethods
|
34
|
+
def handle_asynchronously(method, opts = {}) # rubocop:disable PerceivedComplexity
|
35
|
+
aliased_method = method.to_s.sub(/([?!=])$/, '')
|
36
|
+
punctuation = $1 # rubocop:disable PerlBackrefs
|
37
|
+
with_method = "#{aliased_method}_with_delay#{punctuation}"
|
38
|
+
without_method = "#{aliased_method}_without_delay#{punctuation}"
|
39
|
+
define_method(with_method) do |*args|
|
40
|
+
curr_opts = opts.clone
|
41
|
+
curr_opts.each_key do |key|
|
42
|
+
next unless (val = curr_opts[key]).is_a?(Proc)
|
43
|
+
curr_opts[key] = if val.arity == 1
|
44
|
+
val.call(self)
|
45
|
+
else
|
46
|
+
val.call
|
45
47
|
end
|
46
|
-
delay(curr_opts).__send__(without_method, *args)
|
47
48
|
end
|
49
|
+
delay(curr_opts).__send__(without_method, *args)
|
50
|
+
end
|
48
51
|
|
49
|
-
|
50
|
-
|
52
|
+
alias_method without_method, method
|
53
|
+
alias_method method, with_method
|
51
54
|
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
end
|
55
|
+
if public_method_defined?(without_method)
|
56
|
+
public method
|
57
|
+
elsif protected_method_defined?(without_method)
|
58
|
+
protected method
|
59
|
+
elsif private_method_defined?(without_method)
|
60
|
+
private method
|
59
61
|
end
|
60
62
|
end
|
61
63
|
end
|
@@ -30,9 +30,11 @@ module Delayed
|
|
30
30
|
object.method(sym)
|
31
31
|
end
|
32
32
|
|
33
|
+
# rubocop:disable MethodMissing
|
33
34
|
def method_missing(symbol, *args)
|
34
35
|
object.send(symbol, *args)
|
35
36
|
end
|
37
|
+
# rubocop:enable MethodMissing
|
36
38
|
|
37
39
|
def respond_to?(symbol, include_private = false)
|
38
40
|
super || object.respond_to?(symbol, include_private)
|
data/lib/delayed/psych_ext.rb
CHANGED
@@ -37,7 +37,7 @@ module Delayed
|
|
37
37
|
klass = result.class
|
38
38
|
id = result[klass.primary_key]
|
39
39
|
begin
|
40
|
-
klass.find(id)
|
40
|
+
klass.unscoped.find(id)
|
41
41
|
rescue ActiveRecord::RecordNotFound => error # rubocop:disable BlockNesting
|
42
42
|
raise Delayed::DeserializationError, "ActiveRecord::RecordNotFound, class: #{klass}, primary key: #{id} (#{error.message})"
|
43
43
|
end
|
data/lib/delayed/worker.rb
CHANGED
@@ -233,6 +233,8 @@ module Delayed
|
|
233
233
|
job_say job, format('COMPLETED after %.4f', runtime)
|
234
234
|
return true # did work
|
235
235
|
rescue DeserializationError => error
|
236
|
+
job_say job, "FAILED permanently with #{error.class.name}: #{error.message}", 'error'
|
237
|
+
|
236
238
|
job.error = error
|
237
239
|
failed(job)
|
238
240
|
rescue Exception => error # rubocop:disable RescueException
|
@@ -268,7 +270,7 @@ module Delayed
|
|
268
270
|
end
|
269
271
|
|
270
272
|
def job_say(job, text, level = default_log_level)
|
271
|
-
text = "Job #{job.name} (id=#{job.id}) #{text}"
|
273
|
+
text = "Job #{job.name} (id=#{job.id})#{say_queue(job.queue)} #{text}"
|
272
274
|
say text, level
|
273
275
|
end
|
274
276
|
|
@@ -293,6 +295,10 @@ module Delayed
|
|
293
295
|
|
294
296
|
protected
|
295
297
|
|
298
|
+
def say_queue(queue)
|
299
|
+
" (queue=#{queue})" if queue
|
300
|
+
end
|
301
|
+
|
296
302
|
def handle_failed_job(job, error)
|
297
303
|
job.error = error
|
298
304
|
job_say job, "FAILED (#{job.attempts} prior attempts) with #{error.class.name}: #{error.message}", 'error'
|
@@ -320,8 +326,12 @@ module Delayed
|
|
320
326
|
|
321
327
|
def reload!
|
322
328
|
return unless self.class.reload_app?
|
323
|
-
|
324
|
-
|
329
|
+
if defined?(ActiveSupport::Reloader)
|
330
|
+
Rails.application.reloader.reload!
|
331
|
+
else
|
332
|
+
ActionDispatch::Reloader.cleanup!
|
333
|
+
ActionDispatch::Reloader.prepare!
|
334
|
+
end
|
325
335
|
end
|
326
336
|
end
|
327
337
|
end
|
data/lib/delayed_job.rb
CHANGED
@@ -1,3 +1,4 @@
|
|
1
|
+
require 'active_support'
|
1
2
|
require 'delayed/compatibility'
|
2
3
|
require 'delayed/exceptions'
|
3
4
|
require 'delayed/message_sending'
|
@@ -19,4 +20,4 @@ require 'delayed/deserialization_error'
|
|
19
20
|
require 'delayed/railtie' if defined?(Rails::Railtie)
|
20
21
|
|
21
22
|
Object.send(:include, Delayed::MessageSending)
|
22
|
-
Module.send(:include, Delayed::
|
23
|
+
Module.send(:include, Delayed::MessageSendingClassMethods)
|
@@ -6,6 +6,6 @@ class DelayedJobGenerator < Rails::Generators::Base
|
|
6
6
|
|
7
7
|
def create_executable_file
|
8
8
|
template 'script', "#{Delayed::Compatibility.executable_prefix}/delayed_job"
|
9
|
-
chmod "#{Delayed::Compatibility.executable_prefix}/delayed_job",
|
9
|
+
chmod "#{Delayed::Compatibility.executable_prefix}/delayed_job", 0o755
|
10
10
|
end
|
11
11
|
end
|
data/spec/autoloaded/clazz.rb
CHANGED
data/spec/autoloaded/struct.rb
CHANGED
@@ -1,6 +1,11 @@
|
|
1
1
|
require 'helper'
|
2
2
|
|
3
3
|
describe Delayed::MessageSending do
|
4
|
+
it 'does not include ClassMethods along with MessageSending' do
|
5
|
+
expect { ClassMethods }.to raise_error(NameError)
|
6
|
+
expect(defined?(String::ClassMethods)).to eq(nil)
|
7
|
+
end
|
8
|
+
|
4
9
|
describe 'handle_asynchronously' do
|
5
10
|
class Story
|
6
11
|
def tell!(_arg); end
|
@@ -19,7 +24,7 @@ describe Delayed::MessageSending do
|
|
19
24
|
expect(job.payload_object.class).to eq(Delayed::PerformableMethod)
|
20
25
|
expect(job.payload_object.method_name).to eq(:tell_without_delay!)
|
21
26
|
expect(job.payload_object.args).to eq([1])
|
22
|
-
end.to
|
27
|
+
end.to(change { Delayed::Job.count })
|
23
28
|
end
|
24
29
|
|
25
30
|
describe 'with options' do
|
@@ -42,8 +47,7 @@ describe Delayed::MessageSending do
|
|
42
47
|
describe 'using a proc with parameters' do
|
43
48
|
class Yarn
|
44
49
|
attr_accessor :importance
|
45
|
-
def spin
|
46
|
-
end
|
50
|
+
def spin; end
|
47
51
|
handle_asynchronously :spin, :priority => proc { |y| y.importance }
|
48
52
|
end
|
49
53
|
|
@@ -107,7 +111,7 @@ describe Delayed::MessageSending do
|
|
107
111
|
expect do
|
108
112
|
fairy_tail.delay.tell
|
109
113
|
end.to change(fairy_tail, :happy_ending).from(nil).to(true)
|
110
|
-
end.not_to
|
114
|
+
end.not_to(change { Delayed::Job.count })
|
111
115
|
end
|
112
116
|
|
113
117
|
it 'does delay the job when delay_jobs is true' do
|
@@ -137,7 +141,7 @@ describe Delayed::MessageSending do
|
|
137
141
|
expect do
|
138
142
|
fairy_tail.delay.tell
|
139
143
|
end.to change(fairy_tail, :happy_ending).from(nil).to(true)
|
140
|
-
end.not_to
|
144
|
+
end.not_to(change { Delayed::Job.count })
|
141
145
|
end
|
142
146
|
end
|
143
147
|
end
|
@@ -30,8 +30,7 @@ describe Delayed::PerformableMethod do
|
|
30
30
|
|
31
31
|
it 'does not raise NoMethodError if target method is private' do
|
32
32
|
clazz = Class.new do
|
33
|
-
def private_method
|
34
|
-
end
|
33
|
+
def private_method; end
|
35
34
|
private :private_method
|
36
35
|
end
|
37
36
|
expect { Delayed::PerformableMethod.new(clazz.new, :private_method, []) }.not_to raise_error
|
data/spec/worker_spec.rb
CHANGED
@@ -24,15 +24,23 @@ describe Delayed::Worker do
|
|
24
24
|
describe 'job_say' do
|
25
25
|
before do
|
26
26
|
@worker = Delayed::Worker.new
|
27
|
-
@job = double('job', :id => 123, :name => 'ExampleJob')
|
27
|
+
@job = double('job', :id => 123, :name => 'ExampleJob', :queue => nil)
|
28
28
|
end
|
29
29
|
|
30
30
|
it 'logs with job name and id' do
|
31
|
+
expect(@job).to receive(:queue)
|
31
32
|
expect(@worker).to receive(:say).
|
32
33
|
with('Job ExampleJob (id=123) message', Delayed::Worker.default_log_level)
|
33
34
|
@worker.job_say(@job, 'message')
|
34
35
|
end
|
35
36
|
|
37
|
+
it 'logs with job name, queue and id' do
|
38
|
+
expect(@job).to receive(:queue).and_return('test')
|
39
|
+
expect(@worker).to receive(:say).
|
40
|
+
with('Job ExampleJob (id=123) (queue=test) message', Delayed::Worker.default_log_level)
|
41
|
+
@worker.job_say(@job, 'message')
|
42
|
+
end
|
43
|
+
|
36
44
|
it 'has a configurable default log level' do
|
37
45
|
Delayed::Worker.default_log_level = 'error'
|
38
46
|
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: delayed_job
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 4.1.
|
4
|
+
version: 4.1.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brandon Keepers
|
@@ -15,7 +15,7 @@ authors:
|
|
15
15
|
autorequire:
|
16
16
|
bindir: bin
|
17
17
|
cert_chain: []
|
18
|
-
date:
|
18
|
+
date: 2017-05-26 00:00:00.000000000 Z
|
19
19
|
dependencies:
|
20
20
|
- !ruby/object:Gem::Dependency
|
21
21
|
name: activesupport
|
@@ -26,7 +26,7 @@ dependencies:
|
|
26
26
|
version: '3.0'
|
27
27
|
- - "<"
|
28
28
|
- !ruby/object:Gem::Version
|
29
|
-
version: '5.
|
29
|
+
version: '5.2'
|
30
30
|
type: :runtime
|
31
31
|
prerelease: false
|
32
32
|
version_requirements: !ruby/object:Gem::Requirement
|
@@ -36,7 +36,7 @@ dependencies:
|
|
36
36
|
version: '3.0'
|
37
37
|
- - "<"
|
38
38
|
- !ruby/object:Gem::Version
|
39
|
-
version: '5.
|
39
|
+
version: '5.2'
|
40
40
|
description: Delayed_job (or DJ) encapsulates the common pattern of asynchronously
|
41
41
|
executing longer tasks in the background. It is a direct extraction from Shopify
|
42
42
|
where the job table is responsible for a multitude of core tasks.
|
@@ -119,7 +119,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
119
119
|
version: '0'
|
120
120
|
requirements: []
|
121
121
|
rubyforge_project:
|
122
|
-
rubygems_version: 2.
|
122
|
+
rubygems_version: 2.6.11
|
123
123
|
signing_key:
|
124
124
|
specification_version: 4
|
125
125
|
summary: Database-backed asynchronous priority queue system -- Extracted from Shopify
|