delayed_job 4.0.2 → 4.0.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 +5 -13
- data/CHANGELOG.md +7 -0
- data/README.md +12 -7
- data/Rakefile +6 -1
- data/delayed_job.gemspec +5 -5
- data/lib/delayed/backend/base.rb +18 -20
- data/lib/delayed/backend/shared_spec.rb +139 -138
- data/lib/delayed/command.rb +75 -40
- data/lib/delayed/exceptions.rb +2 -1
- data/lib/delayed/lifecycle.rb +12 -11
- data/lib/delayed/message_sending.rb +9 -10
- data/lib/delayed/performable_mailer.rb +2 -2
- data/lib/delayed/performable_method.rb +2 -2
- data/lib/delayed/psych_ext.rb +29 -93
- data/lib/delayed/recipes.rb +5 -5
- data/lib/delayed/serialization/active_record.rb +11 -9
- data/lib/delayed/syck_ext.rb +3 -3
- data/lib/delayed/tasks.rb +5 -5
- data/lib/delayed/worker.rb +42 -42
- data/lib/generators/delayed_job/delayed_job_generator.rb +2 -3
- data/spec/delayed/backend/test.rb +22 -17
- data/spec/delayed/command_spec.rb +57 -0
- data/spec/helper.rb +25 -12
- data/spec/lifecycle_spec.rb +23 -15
- data/spec/message_sending_spec.rb +34 -34
- data/spec/performable_mailer_spec.rb +11 -11
- data/spec/performable_method_spec.rb +24 -26
- data/spec/psych_ext_spec.rb +12 -0
- data/spec/sample_jobs.rb +46 -18
- data/spec/test_backend_spec.rb +3 -3
- data/spec/worker_spec.rb +27 -27
- data/spec/yaml_ext_spec.rb +16 -16
- metadata +12 -8
data/lib/delayed/recipes.rb
CHANGED
@@ -25,7 +25,7 @@ Capistrano::Configuration.instance.load do
|
|
25
25
|
end
|
26
26
|
|
27
27
|
def args
|
28
|
-
fetch(:delayed_job_args,
|
28
|
+
fetch(:delayed_job_args, '')
|
29
29
|
end
|
30
30
|
|
31
31
|
def roles
|
@@ -33,20 +33,20 @@ Capistrano::Configuration.instance.load do
|
|
33
33
|
end
|
34
34
|
|
35
35
|
def delayed_job_command
|
36
|
-
fetch(:delayed_job_command,
|
36
|
+
fetch(:delayed_job_command, 'script/delayed_job')
|
37
37
|
end
|
38
38
|
|
39
|
-
desc
|
39
|
+
desc 'Stop the delayed_job process'
|
40
40
|
task :stop, :roles => lambda { roles } do
|
41
41
|
run "cd #{current_path};#{rails_env} #{delayed_job_command} stop"
|
42
42
|
end
|
43
43
|
|
44
|
-
desc
|
44
|
+
desc 'Start the delayed_job process'
|
45
45
|
task :start, :roles => lambda { roles } do
|
46
46
|
run "cd #{current_path};#{rails_env} #{delayed_job_command} start #{args}"
|
47
47
|
end
|
48
48
|
|
49
|
-
desc
|
49
|
+
desc 'Restart the delayed_job process'
|
50
50
|
task :restart, :roles => lambda { roles } do
|
51
51
|
run "cd #{current_path};#{rails_env} #{delayed_job_command} restart #{args}"
|
52
52
|
end
|
@@ -1,15 +1,17 @@
|
|
1
1
|
if defined?(ActiveRecord)
|
2
|
-
|
3
|
-
|
2
|
+
module ActiveRecord
|
3
|
+
class Base
|
4
|
+
yaml_as 'tag:ruby.yaml.org,2002:ActiveRecord'
|
4
5
|
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
6
|
+
def self.yaml_new(klass, _tag, val)
|
7
|
+
klass.unscoped.find(val['attributes'][klass.primary_key])
|
8
|
+
rescue ActiveRecord::RecordNotFound
|
9
|
+
raise Delayed::DeserializationError, "ActiveRecord::RecordNotFound, class: #{klass} , primary key: #{val['attributes'][klass.primary_key]}"
|
10
|
+
end
|
10
11
|
|
11
|
-
|
12
|
-
|
12
|
+
def to_yaml_properties
|
13
|
+
['@attributes']
|
14
|
+
end
|
13
15
|
end
|
14
16
|
end
|
15
17
|
end
|
data/lib/delayed/syck_ext.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
class Module
|
2
|
-
yaml_as
|
2
|
+
yaml_as 'tag:ruby.yaml.org,2002:module'
|
3
3
|
|
4
|
-
def self.yaml_new(
|
4
|
+
def self.yaml_new(_klass, _tag, val)
|
5
5
|
val.constantize
|
6
6
|
end
|
7
7
|
|
@@ -20,7 +20,7 @@ class Module
|
|
20
20
|
end
|
21
21
|
|
22
22
|
class Class
|
23
|
-
yaml_as
|
23
|
+
yaml_as 'tag:ruby.yaml.org,2002:class'
|
24
24
|
remove_method :to_yaml if respond_to?(:to_yaml) && method(:to_yaml).owner == Class # use Module's to_yaml
|
25
25
|
end
|
26
26
|
|
data/lib/delayed/tasks.rb
CHANGED
@@ -1,17 +1,17 @@
|
|
1
1
|
namespace :jobs do
|
2
|
-
desc
|
2
|
+
desc 'Clear the delayed_job queue.'
|
3
3
|
task :clear => :environment do
|
4
4
|
Delayed::Job.delete_all
|
5
5
|
end
|
6
6
|
|
7
|
-
desc
|
7
|
+
desc 'Start a delayed_job worker.'
|
8
8
|
task :work => :environment_options do
|
9
9
|
Delayed::Worker.new(@worker_options).start
|
10
10
|
end
|
11
11
|
|
12
|
-
desc
|
12
|
+
desc 'Start a delayed_job worker and exit when all available jobs are complete.'
|
13
13
|
task :workoff => :environment_options do
|
14
|
-
Delayed::Worker.new(@worker_options.merge(
|
14
|
+
Delayed::Worker.new(@worker_options.merge(:exit_on_complete => true)).start
|
15
15
|
end
|
16
16
|
|
17
17
|
task :environment_options => :environment do
|
@@ -30,7 +30,7 @@ namespace :jobs do
|
|
30
30
|
unprocessed_jobs = Delayed::Job.where('attempts = 0 AND created_at < ?', Time.now - args[:max_age].to_i).count
|
31
31
|
|
32
32
|
if unprocessed_jobs > 0
|
33
|
-
|
33
|
+
raise "#{unprocessed_jobs} jobs older than #{args[:max_age]} seconds have not been processed yet"
|
34
34
|
end
|
35
35
|
|
36
36
|
end
|
data/lib/delayed/worker.rb
CHANGED
@@ -7,8 +7,7 @@ require 'logger'
|
|
7
7
|
require 'benchmark'
|
8
8
|
|
9
9
|
module Delayed
|
10
|
-
|
11
|
-
class Worker
|
10
|
+
class Worker # rubocop:disable ClassLength
|
12
11
|
DEFAULT_LOG_LEVEL = 'info'
|
13
12
|
DEFAULT_SLEEP_DELAY = 5
|
14
13
|
DEFAULT_MAX_ATTEMPTS = 25
|
@@ -19,8 +18,8 @@ module Delayed
|
|
19
18
|
DEFAULT_READ_AHEAD = 5
|
20
19
|
|
21
20
|
cattr_accessor :min_priority, :max_priority, :max_attempts, :max_run_time,
|
22
|
-
|
23
|
-
|
21
|
+
:default_priority, :sleep_delay, :logger, :delay_jobs, :queues,
|
22
|
+
:read_ahead, :plugins, :destroy_failed_jobs, :exit_on_complete
|
24
23
|
|
25
24
|
# Named queue into which jobs are enqueued by default
|
26
25
|
cattr_accessor :default_queue_name
|
@@ -70,12 +69,12 @@ module Delayed
|
|
70
69
|
require "delayed/backend/#{backend}"
|
71
70
|
backend = "Delayed::Backend::#{backend.to_s.classify}::Job".constantize
|
72
71
|
end
|
73
|
-
@@backend = backend
|
72
|
+
@@backend = backend # rubocop:disable ClassVars
|
74
73
|
silence_warnings { ::Delayed.const_set(:Job, backend) }
|
75
74
|
end
|
76
75
|
|
77
76
|
def self.guess_backend
|
78
|
-
warn
|
77
|
+
warn '[DEPRECATION] guess_backend is deprecated. Please remove it from your code.'
|
79
78
|
end
|
80
79
|
|
81
80
|
def self.before_fork
|
@@ -93,12 +92,11 @@ module Delayed
|
|
93
92
|
# Re-open file handles
|
94
93
|
@files_to_reopen.each do |file|
|
95
94
|
begin
|
96
|
-
file.reopen file.path,
|
95
|
+
file.reopen file.path, 'a+'
|
97
96
|
file.sync = true
|
98
|
-
rescue ::Exception
|
97
|
+
rescue ::Exception # rubocop:disable HandleExceptions, RescueException
|
99
98
|
end
|
100
99
|
end
|
101
|
-
|
102
100
|
backend.after_fork
|
103
101
|
end
|
104
102
|
|
@@ -106,15 +104,15 @@ module Delayed
|
|
106
104
|
@lifecycle ||= Delayed::Lifecycle.new
|
107
105
|
end
|
108
106
|
|
109
|
-
def initialize(options={})
|
110
|
-
@quiet = options.
|
107
|
+
def initialize(options = {})
|
108
|
+
@quiet = options.key?(:quiet) ? options[:quiet] : true
|
111
109
|
@failed_reserve_count = 0
|
112
110
|
|
113
111
|
[:min_priority, :max_priority, :sleep_delay, :read_ahead, :queues, :exit_on_complete].each do |option|
|
114
|
-
self.class.send("#{option}=", options[option]) if options.
|
112
|
+
self.class.send("#{option}=", options[option]) if options.key?(option)
|
115
113
|
end
|
116
114
|
|
117
|
-
|
115
|
+
plugins.each { |klass| klass.new }
|
118
116
|
end
|
119
117
|
|
120
118
|
# Every worker has a unique name which by default is the pid of the process. There are some
|
@@ -123,29 +121,27 @@ module Delayed
|
|
123
121
|
# it crashed before.
|
124
122
|
def name
|
125
123
|
return @name unless @name.nil?
|
126
|
-
"#{@name_prefix}host:#{Socket.gethostname} pid:#{Process.pid}" rescue "#{@name_prefix}pid:#{Process.pid}"
|
124
|
+
"#{@name_prefix}host:#{Socket.gethostname} pid:#{Process.pid}" rescue "#{@name_prefix}pid:#{Process.pid}" # rubocop:disable RescueModifier
|
127
125
|
end
|
128
126
|
|
129
127
|
# Sets the name of the worker.
|
130
128
|
# Setting the name to nil will reset the default worker name
|
131
|
-
|
132
|
-
@name = val
|
133
|
-
end
|
129
|
+
attr_writer :name
|
134
130
|
|
135
|
-
def start
|
131
|
+
def start # rubocop:disable CyclomaticComplexity, PerceivedComplexity
|
136
132
|
trap('TERM') do
|
137
133
|
say 'Exiting...'
|
138
134
|
stop
|
139
|
-
raise SignalException
|
135
|
+
raise SignalException, 'TERM' if self.class.raise_signal_exceptions
|
140
136
|
end
|
141
137
|
|
142
138
|
trap('INT') do
|
143
139
|
say 'Exiting...'
|
144
140
|
stop
|
145
|
-
raise SignalException
|
141
|
+
raise SignalException, 'INT' if self.class.raise_signal_exceptions && self.class.raise_signal_exceptions != :term
|
146
142
|
end
|
147
143
|
|
148
|
-
say
|
144
|
+
say 'Starting job worker'
|
149
145
|
|
150
146
|
self.class.lifecycle.run_callbacks(:execute, self) do
|
151
147
|
loop do
|
@@ -159,13 +155,13 @@ module Delayed
|
|
159
155
|
|
160
156
|
if count.zero?
|
161
157
|
if self.class.exit_on_complete
|
162
|
-
say
|
158
|
+
say 'No more jobs available. Exiting'
|
163
159
|
break
|
164
|
-
|
165
|
-
sleep(self.class.sleep_delay)
|
160
|
+
elsif !stop?
|
161
|
+
sleep(self.class.sleep_delay)
|
166
162
|
end
|
167
163
|
else
|
168
|
-
say "#{count} jobs processed at %.4f j/s, %d failed"
|
164
|
+
say format("#{count} jobs processed at %.4f j/s, %d failed", count / @realtime, @result.last)
|
169
165
|
end
|
170
166
|
|
171
167
|
break if stop?
|
@@ -189,16 +185,16 @@ module Delayed
|
|
189
185
|
num.times do
|
190
186
|
case reserve_and_run_one_job
|
191
187
|
when true
|
192
|
-
|
188
|
+
success += 1
|
193
189
|
when false
|
194
|
-
|
190
|
+
failure += 1
|
195
191
|
else
|
196
192
|
break # leave if no work could be done
|
197
193
|
end
|
198
194
|
break if stop? # leave if we're exiting
|
199
195
|
end
|
200
196
|
|
201
|
-
|
197
|
+
[success, failure]
|
202
198
|
end
|
203
199
|
|
204
200
|
def run(job)
|
@@ -207,13 +203,13 @@ module Delayed
|
|
207
203
|
Timeout.timeout(self.class.max_run_time.to_i, WorkerTimeout) { job.invoke_job }
|
208
204
|
job.destroy
|
209
205
|
end
|
210
|
-
job_say job, 'COMPLETED after %.4f'
|
206
|
+
job_say job, format('COMPLETED after %.4f', runtime)
|
211
207
|
return true # did work
|
212
208
|
rescue DeserializationError => error
|
213
209
|
job.last_error = "#{error.message}\n#{error.backtrace.join("\n")}"
|
214
210
|
failed(job)
|
215
|
-
rescue
|
216
|
-
self.class.lifecycle.run_callbacks(:error, self, job){ handle_failed_job(job, error) }
|
211
|
+
rescue => error
|
212
|
+
self.class.lifecycle.run_callbacks(:error, self, job) { handle_failed_job(job, error) }
|
217
213
|
return false # work failed
|
218
214
|
end
|
219
215
|
|
@@ -233,8 +229,14 @@ module Delayed
|
|
233
229
|
|
234
230
|
def failed(job)
|
235
231
|
self.class.lifecycle.run_callbacks(:failure, self, job) do
|
236
|
-
|
237
|
-
|
232
|
+
begin
|
233
|
+
job.hook(:failure)
|
234
|
+
rescue => error
|
235
|
+
say "Error when running failure callback: #{error}", 'error'
|
236
|
+
say error.backtrace.join("\n"), 'error'
|
237
|
+
ensure
|
238
|
+
self.class.destroy_failed_jobs ? job.destroy : job.fail!
|
239
|
+
end
|
238
240
|
end
|
239
241
|
end
|
240
242
|
|
@@ -246,13 +248,12 @@ module Delayed
|
|
246
248
|
def say(text, level = DEFAULT_LOG_LEVEL)
|
247
249
|
text = "[Worker(#{name})] #{text}"
|
248
250
|
puts text unless @quiet
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
end
|
254
|
-
logger.send(level, "#{Time.now.strftime('%FT%T%z')}: #{text}")
|
251
|
+
return unless logger
|
252
|
+
# TODO: Deprecate use of Fixnum log levels
|
253
|
+
unless level.is_a?(String)
|
254
|
+
level = Logger::Severity.constants.detect { |i| Logger::Severity.const_get(i) == level }.to_s.downcase
|
255
255
|
end
|
256
|
+
logger.send(level, "#{Time.now.strftime('%FT%T%z')}: #{text}")
|
256
257
|
end
|
257
258
|
|
258
259
|
def max_attempts(job)
|
@@ -271,14 +272,14 @@ module Delayed
|
|
271
272
|
# If no jobs are left we return nil
|
272
273
|
def reserve_and_run_one_job
|
273
274
|
job = reserve_job
|
274
|
-
self.class.lifecycle.run_callbacks(:perform, self, job){ run(job) } if job
|
275
|
+
self.class.lifecycle.run_callbacks(:perform, self, job) { run(job) } if job
|
275
276
|
end
|
276
277
|
|
277
278
|
def reserve_job
|
278
279
|
job = Delayed::Job.reserve(self)
|
279
280
|
@failed_reserve_count = 0
|
280
281
|
job
|
281
|
-
rescue Exception => error
|
282
|
+
rescue ::Exception => error # rubocop:disable RescueException
|
282
283
|
say "Error while reserving job: #{error}"
|
283
284
|
Delayed::Job.recover_from(error)
|
284
285
|
@failed_reserve_count += 1
|
@@ -286,5 +287,4 @@ module Delayed
|
|
286
287
|
nil
|
287
288
|
end
|
288
289
|
end
|
289
|
-
|
290
290
|
end
|
@@ -2,11 +2,10 @@ require 'rails/generators'
|
|
2
2
|
require 'delayed/compatibility'
|
3
3
|
|
4
4
|
class DelayedJobGenerator < Rails::Generators::Base
|
5
|
-
|
6
|
-
self.source_paths << File.join(File.dirname(__FILE__), 'templates')
|
5
|
+
source_paths << File.join(File.dirname(__FILE__), 'templates')
|
7
6
|
|
8
7
|
def create_executable_file
|
9
|
-
template
|
8
|
+
template 'script', "#{Delayed::Compatibility.executable_prefix}/delayed_job"
|
10
9
|
chmod "#{Delayed::Compatibility.executable_prefix}/delayed_job", 0755
|
11
10
|
end
|
12
11
|
end
|
@@ -25,12 +25,11 @@ module Delayed
|
|
25
25
|
self.attempts = 0
|
26
26
|
self.priority = 0
|
27
27
|
self.id = (self.class.id += 1)
|
28
|
-
hash.each{|k,v| send(:"#{k}=", v)}
|
28
|
+
hash.each { |k, v| send(:"#{k}=", v) }
|
29
29
|
end
|
30
30
|
|
31
|
-
@jobs = []
|
32
31
|
def self.all
|
33
|
-
@jobs
|
32
|
+
@jobs ||= []
|
34
33
|
end
|
35
34
|
|
36
35
|
def self.count
|
@@ -47,29 +46,33 @@ module Delayed
|
|
47
46
|
end
|
48
47
|
end
|
49
48
|
|
50
|
-
def self.create!(*args)
|
49
|
+
def self.create!(*args)
|
50
|
+
create(*args)
|
51
|
+
end
|
51
52
|
|
52
53
|
def self.clear_locks!(worker_name)
|
53
|
-
all.select{|j| j.locked_by == worker_name}.each
|
54
|
+
all.select { |j| j.locked_by == worker_name }.each do |j|
|
55
|
+
j.locked_by = nil
|
56
|
+
j.locked_at = nil
|
57
|
+
end
|
54
58
|
end
|
55
59
|
|
56
60
|
# Find a few candidate jobs to run (in case some immediately get locked by others).
|
57
|
-
def self.find_available(worker_name, limit = 5, max_run_time = Worker.max_run_time)
|
61
|
+
def self.find_available(worker_name, limit = 5, max_run_time = Worker.max_run_time) # rubocop:disable CyclomaticComplexity, PerceivedComplexity
|
58
62
|
jobs = all.select do |j|
|
59
63
|
j.run_at <= db_time_now &&
|
60
|
-
|
61
|
-
|
64
|
+
(j.locked_at.nil? || j.locked_at < db_time_now - max_run_time || j.locked_by == worker_name) &&
|
65
|
+
!j.failed?
|
62
66
|
end
|
63
|
-
|
64
|
-
jobs
|
65
|
-
jobs
|
66
|
-
jobs
|
67
|
-
jobs.sort_by{|j| [j.priority, j.run_at]}[0..limit-1]
|
67
|
+
jobs.select! { |j| j.priority <= Worker.max_priority } if Worker.max_priority
|
68
|
+
jobs.select! { |j| j.priority >= Worker.min_priority } if Worker.min_priority
|
69
|
+
jobs.select! { |j| Worker.queues.include?(j.queue) } if Worker.queues.any?
|
70
|
+
jobs.sort_by! { |j| [j.priority, j.run_at] }[0..limit - 1]
|
68
71
|
end
|
69
72
|
|
70
73
|
# Lock this job for this worker.
|
71
74
|
# Returns true if we have the lock, false otherwise.
|
72
|
-
def lock_exclusively!(
|
75
|
+
def lock_exclusively!(_max_run_time, worker)
|
73
76
|
now = self.class.db_time_now
|
74
77
|
if locked_by != worker
|
75
78
|
# We don't own this job so we will update the locked_by name and the locked_at
|
@@ -77,7 +80,7 @@ module Delayed
|
|
77
80
|
self.locked_by = worker
|
78
81
|
end
|
79
82
|
|
80
|
-
|
83
|
+
true
|
81
84
|
end
|
82
85
|
|
83
86
|
def self.db_time_now
|
@@ -85,7 +88,7 @@ module Delayed
|
|
85
88
|
end
|
86
89
|
|
87
90
|
def update_attributes(attrs = {})
|
88
|
-
attrs.each{|k,v| send(:"#{k}=", v)}
|
91
|
+
attrs.each { |k, v| send(:"#{k}=", v) }
|
89
92
|
save
|
90
93
|
end
|
91
94
|
|
@@ -100,7 +103,9 @@ module Delayed
|
|
100
103
|
true
|
101
104
|
end
|
102
105
|
|
103
|
-
def save
|
106
|
+
def save!
|
107
|
+
save
|
108
|
+
end
|
104
109
|
|
105
110
|
def reload
|
106
111
|
reset
|
@@ -0,0 +1,57 @@
|
|
1
|
+
require 'helper'
|
2
|
+
require 'delayed/command'
|
3
|
+
|
4
|
+
describe Delayed::Command do
|
5
|
+
describe 'parsing --pool argument' do
|
6
|
+
it 'should parse --pool correctly' do
|
7
|
+
command = Delayed::Command.new(['--pool=*:1', '--pool=test_queue:4', '--pool=mailers,misc:2'])
|
8
|
+
|
9
|
+
expect(command.worker_pools).to eq [
|
10
|
+
[[], 1],
|
11
|
+
[['test_queue'], 4],
|
12
|
+
[%w[mailers misc], 2]
|
13
|
+
]
|
14
|
+
end
|
15
|
+
|
16
|
+
it 'should allow * or blank to specify any pools' do
|
17
|
+
command = Delayed::Command.new(['--pool=*:4'])
|
18
|
+
expect(command.worker_pools).to eq [
|
19
|
+
[[], 4],
|
20
|
+
]
|
21
|
+
|
22
|
+
command = Delayed::Command.new(['--pool=:4'])
|
23
|
+
expect(command.worker_pools).to eq [
|
24
|
+
[[], 4],
|
25
|
+
]
|
26
|
+
end
|
27
|
+
|
28
|
+
it 'should default to one worker if not specified' do
|
29
|
+
command = Delayed::Command.new(['--pool=mailers'])
|
30
|
+
expect(command.worker_pools).to eq [
|
31
|
+
[['mailers'], 1],
|
32
|
+
]
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
describe 'running worker pools defined by multiple --pool arguments' do
|
37
|
+
it 'should run the correct worker processes' do
|
38
|
+
command = Delayed::Command.new(['--pool=*:1', '--pool=test_queue:4', '--pool=mailers,misc:2'])
|
39
|
+
|
40
|
+
expect(Dir).to receive(:mkdir).with('./tmp/pids').once
|
41
|
+
|
42
|
+
[
|
43
|
+
['delayed_job.0', {:quiet => true, :pid_dir => './tmp/pids', :queues => []}],
|
44
|
+
['delayed_job.1', {:quiet => true, :pid_dir => './tmp/pids', :queues => ['test_queue']}],
|
45
|
+
['delayed_job.2', {:quiet => true, :pid_dir => './tmp/pids', :queues => ['test_queue']}],
|
46
|
+
['delayed_job.3', {:quiet => true, :pid_dir => './tmp/pids', :queues => ['test_queue']}],
|
47
|
+
['delayed_job.4', {:quiet => true, :pid_dir => './tmp/pids', :queues => ['test_queue']}],
|
48
|
+
['delayed_job.5', {:quiet => true, :pid_dir => './tmp/pids', :queues => %w[mailers misc]}],
|
49
|
+
['delayed_job.6', {:quiet => true, :pid_dir => './tmp/pids', :queues => %w[mailers misc]}]
|
50
|
+
].each do |args|
|
51
|
+
expect(command).to receive(:run_process).with(*args).once
|
52
|
+
end
|
53
|
+
|
54
|
+
command.daemonize
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|