inst-jobs 0.14.0 → 0.14.1
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/lib/delayed/backend/active_record.rb +8 -1
- data/lib/delayed/backend/redis/job.rb +10 -2
- data/lib/delayed/periodic.rb +0 -2
- data/lib/delayed/settings.rb +9 -0
- data/lib/delayed/version.rb +1 -1
- data/lib/delayed/worker/consul_health_check.rb +108 -0
- data/lib/delayed/worker/health_check.rb +57 -0
- data/lib/delayed/worker/null_health_check.rb +11 -0
- data/lib/delayed/worker.rb +18 -3
- data/lib/delayed_job.rb +5 -0
- data/spec/delayed/worker/consul_health_check_spec.rb +74 -0
- data/spec/delayed/worker/health_check_spec.rb +98 -0
- data/spec/shared/shared_backend.rb +13 -0
- metadata +24 -9
- data/spec/gemfiles/42.gemfile.lock +0 -182
- data/spec/gemfiles/50.gemfile.lock +0 -187
- data/spec/gemfiles/51.gemfile.lock +0 -187
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e485941f6b24b6f88e18b37c1b25e2cab3862630
|
4
|
+
data.tar.gz: 8f753f31b331870b59a226e65822619da4429ab1
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0f33b3e301a818b103d98ed74bdff5baaee8387b7073a227945931dd6c60543bb072e009847bfc16aa6aba1c67813b1166e7af3877dfea8d0db5f722134b4e41
|
7
|
+
data.tar.gz: 686bdb0292db19d3662202020e7a21fc956dab17e4d68cfe671f6b1e80646baf329dcc5b6dd1b6b1c76120520fcb1d633b4495c1104e98d60da5e0bc1235d3be
|
@@ -312,12 +312,19 @@ module Delayed
|
|
312
312
|
# on the strand but it's already running)
|
313
313
|
def self.create_singleton(options)
|
314
314
|
strand = options[:strand]
|
315
|
+
on_conflict = options.delete(:on_conflict) || :use_earliest
|
315
316
|
transaction_for_singleton(strand) do
|
316
317
|
job = self.where(:strand => strand, :locked_at => nil).order(:id).first
|
317
318
|
new_job = new(options)
|
318
319
|
if job
|
319
320
|
new_job.initialize_defaults
|
320
|
-
job.run_at =
|
321
|
+
job.run_at =
|
322
|
+
case on_conflict
|
323
|
+
when :use_earliest
|
324
|
+
[job.run_at, new_job.run_at].min
|
325
|
+
when :overwrite
|
326
|
+
new_job.run_at
|
327
|
+
end
|
321
328
|
job.save! if job.changed?
|
322
329
|
else
|
323
330
|
new_job.save!
|
@@ -360,7 +360,7 @@ class Job
|
|
360
360
|
end
|
361
361
|
|
362
362
|
# not saved, just used as a marker when creating
|
363
|
-
attr_accessor :singleton
|
363
|
+
attr_accessor :singleton, :on_conflict
|
364
364
|
|
365
365
|
def transfer_lock!(from:, to:)
|
366
366
|
lock_in_redis!(to)
|
@@ -442,7 +442,15 @@ class Job
|
|
442
442
|
# replace this job with the other for returning.
|
443
443
|
if job_id != self.id
|
444
444
|
singleton = self.class.find(job_id)
|
445
|
-
|
445
|
+
|
446
|
+
self.on_conflict ||= :use_earliest
|
447
|
+
singleton.run_at =
|
448
|
+
case self.on_conflict
|
449
|
+
when :use_earliest
|
450
|
+
[singleton.run_at, run_at].min
|
451
|
+
when :overwrite
|
452
|
+
run_at
|
453
|
+
end
|
446
454
|
singleton.save! if singleton.changed?
|
447
455
|
COLUMNS.each { |c| send("#{c}=", singleton.send(c)) }
|
448
456
|
end
|
data/lib/delayed/periodic.rb
CHANGED
@@ -20,8 +20,6 @@ class Periodic
|
|
20
20
|
self.overrides.merge!(overrides)
|
21
21
|
end
|
22
22
|
|
23
|
-
STRAND = 'periodic scheduling'
|
24
|
-
|
25
23
|
def self.cron(job_name, cron_line, job_args = {}, &block)
|
26
24
|
raise ArgumentError, "job #{job_name} already scheduled!" if self.scheduled[job_name]
|
27
25
|
cron_line = overrides[job_name] || cron_line
|
data/lib/delayed/settings.rb
CHANGED
@@ -19,6 +19,8 @@ module Delayed
|
|
19
19
|
:sleep_delay,
|
20
20
|
:sleep_delay_stagger,
|
21
21
|
:slow_exit_timeout,
|
22
|
+
:worker_health_check_type,
|
23
|
+
:worker_health_check_config,
|
22
24
|
:worker_procname_prefix,
|
23
25
|
]
|
24
26
|
SETTINGS_WITH_ARGS = [ :num_strands ]
|
@@ -69,6 +71,9 @@ module Delayed
|
|
69
71
|
self.kill_workers_on_exit = true
|
70
72
|
self.slow_exit_timeout = 20
|
71
73
|
|
74
|
+
self.worker_health_check_type = :none
|
75
|
+
self.worker_health_check_config = {}
|
76
|
+
|
72
77
|
def self.worker_config(config_filename = nil)
|
73
78
|
config_filename ||= default_worker_config_name
|
74
79
|
config = YAML.load(ERB.new(File.read(config_filename)).result)
|
@@ -117,5 +122,9 @@ module Delayed
|
|
117
122
|
raise 'Parent process configurations must be a hash!' unless Hash === new_config
|
118
123
|
@@parent_process = PARENT_PROCESS_DEFAULTS.merge(new_config)
|
119
124
|
end
|
125
|
+
|
126
|
+
def self.worker_health_check_config=(new_config)
|
127
|
+
@@worker_health_check_config = (new_config || {}).with_indifferent_access
|
128
|
+
end
|
120
129
|
end
|
121
130
|
end
|
data/lib/delayed/version.rb
CHANGED
@@ -0,0 +1,108 @@
|
|
1
|
+
require_relative 'health_check'
|
2
|
+
require 'socket'
|
3
|
+
|
4
|
+
module Delayed
|
5
|
+
class Worker
|
6
|
+
class ConsulHealthCheck < HealthCheck
|
7
|
+
self.type_name = :consul
|
8
|
+
|
9
|
+
CONSUL_CONFIG_KEYS = %w{url host port ssl token connect_timeout receive_timeout send_timeout}.map(&:freeze).freeze
|
10
|
+
DEFAULT_SERVICE_NAME = 'inst-jobs_worker'.freeze
|
11
|
+
attr_reader :agent_client, :catalog_client
|
12
|
+
|
13
|
+
SCRIPT_TEMPLATE = <<-BASH.freeze
|
14
|
+
WORKER_PID="%<pid>d" # an example, filled from ruby when the check is created
|
15
|
+
ORIGINAL_MTIME="%<mtime>d" # an example, filled from ruby when the check is created
|
16
|
+
|
17
|
+
if [ -d "/proc/$WORKER_PID" ]; then
|
18
|
+
CURRENT_MTIME=$(stat -f %%Y /proc/$WORKER_PID)
|
19
|
+
|
20
|
+
if [ "$ORIGINAL_MTIME" = "$CURRENT_MTIME" ]; then
|
21
|
+
exit 0 # Happy day
|
22
|
+
else
|
23
|
+
echo "PID still exists but procfs entry has changed, current command:"
|
24
|
+
ps -p $PID -o 'command='
|
25
|
+
exit 1 # Something is wrong, trigger a "warning" state
|
26
|
+
fi
|
27
|
+
else
|
28
|
+
exit 255 # The process is no more, trigger a "critical" state.
|
29
|
+
fi
|
30
|
+
BASH
|
31
|
+
|
32
|
+
def initialize(*args)
|
33
|
+
super
|
34
|
+
# Because we don't want the consul client to be a hard dependency we're
|
35
|
+
# only requiring it once it's absolutely needed
|
36
|
+
require 'imperium'
|
37
|
+
|
38
|
+
if config.keys.any? { |k| CONSUL_CONFIG_KEYS.include?(k) }
|
39
|
+
consul_config = Imperium::Configuration.new.tap do |conf|
|
40
|
+
CONSUL_CONFIG_KEYS.each do |key|
|
41
|
+
conf.send("#{key}=", config[key]) if config[key]
|
42
|
+
end
|
43
|
+
end
|
44
|
+
@agent_client = Imperium::Agent.new(consul_config)
|
45
|
+
@catalog_client = Imperium::Catalog.new(consul_config)
|
46
|
+
else
|
47
|
+
@agent_client = Imperium::Agent.default_client
|
48
|
+
@catalog_client = Imperium::Catalog.default_client
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
def start
|
53
|
+
service = Imperium::Service.new({
|
54
|
+
id: worker_name,
|
55
|
+
name: service_name,
|
56
|
+
})
|
57
|
+
service.add_check(check_attributes)
|
58
|
+
response = @agent_client.register_service(service)
|
59
|
+
response.ok?
|
60
|
+
end
|
61
|
+
|
62
|
+
def stop
|
63
|
+
response = @agent_client.deregister_service(worker_name)
|
64
|
+
response.ok? || response.not_found?
|
65
|
+
end
|
66
|
+
|
67
|
+
def live_workers
|
68
|
+
live_nodes = @catalog_client.list_nodes_for_service(service_name)
|
69
|
+
if live_nodes.ok?
|
70
|
+
live_nodes.map(&:service_id)
|
71
|
+
else
|
72
|
+
raise "Unable to read from Consul catalog: #{live_nodes.content}"
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
private
|
77
|
+
|
78
|
+
def check_attributes
|
79
|
+
{
|
80
|
+
script: check_script,
|
81
|
+
status: 'passing',
|
82
|
+
interval: @config.fetch(:check_interval, '5m'),
|
83
|
+
deregister_critical_service_after: @config.fetch(:deregister_service_delay, '10m'),
|
84
|
+
}.tap do |h|
|
85
|
+
h[:docker_container_id] = docker_container_id if @config['docker']
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
def check_script
|
90
|
+
return @check_script if @check_script
|
91
|
+
stat = File::Stat.new("/proc/#{Process.pid}")
|
92
|
+
@check_script = sprintf(SCRIPT_TEMPLATE, {pid: Process.pid, mtime: stat.mtime.to_i})
|
93
|
+
end
|
94
|
+
|
95
|
+
# This method is horrible, it takes advantage of the fact that docker uses
|
96
|
+
# cgroups for part of its magic and also uses the container id as the cgroup name
|
97
|
+
def docker_container_id
|
98
|
+
return @docker_container_id if @docker_container_id
|
99
|
+
content = File.read("/proc/1/cgroup").split("\n")
|
100
|
+
@docker_container_id = content.last.split("/").last
|
101
|
+
end
|
102
|
+
|
103
|
+
def service_name
|
104
|
+
@service_name ||= @config.fetch('service_name', DEFAULT_SERVICE_NAME)
|
105
|
+
end
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
@@ -0,0 +1,57 @@
|
|
1
|
+
module Delayed
|
2
|
+
class Worker
|
3
|
+
class HealthCheck
|
4
|
+
@subclasses = []
|
5
|
+
|
6
|
+
class << self
|
7
|
+
attr_accessor :type_name
|
8
|
+
attr_reader :subclasses
|
9
|
+
|
10
|
+
def inherited(subclass)
|
11
|
+
@subclasses << subclass
|
12
|
+
end
|
13
|
+
|
14
|
+
def build(type:, worker_name:, config: {})
|
15
|
+
type = type.to_sym
|
16
|
+
klass = @subclasses.find { |sc| sc.type_name == type }
|
17
|
+
raise ArgumentError, "Unable to build a HealthCheck for type #{type}" unless klass
|
18
|
+
klass.new(worker_name: worker_name, config: config)
|
19
|
+
end
|
20
|
+
|
21
|
+
def reschedule_abandoned_jobs
|
22
|
+
checker = Worker::HealthCheck.build(
|
23
|
+
type: Settings.worker_health_check_type,
|
24
|
+
config: Settings.worker_health_check_config,
|
25
|
+
worker_name: 'cleanup-crew'
|
26
|
+
)
|
27
|
+
live_workers = checker.live_workers
|
28
|
+
|
29
|
+
Delayed::Job.running_jobs.each do |job|
|
30
|
+
unless live_workers.include?(job.locked_by)
|
31
|
+
job.reschedule
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
attr_accessor :config, :worker_name
|
38
|
+
|
39
|
+
def initialize(worker_name:, config: {})
|
40
|
+
@config = config.with_indifferent_access
|
41
|
+
@worker_name = worker_name
|
42
|
+
end
|
43
|
+
|
44
|
+
def start
|
45
|
+
raise NotImplementedError
|
46
|
+
end
|
47
|
+
|
48
|
+
def stop
|
49
|
+
raise NotImplementedError
|
50
|
+
end
|
51
|
+
|
52
|
+
def live_workers
|
53
|
+
raise NotImplementedError
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
data/lib/delayed/worker.rb
CHANGED
@@ -51,6 +51,8 @@ class Worker
|
|
51
51
|
@max_job_count = options[:worker_max_job_count].to_i
|
52
52
|
@max_memory_usage = options[:worker_max_memory_usage].to_i
|
53
53
|
@work_queue = options.delete(:work_queue) || WorkQueue::InProcess.new
|
54
|
+
@health_check_type = Settings.worker_health_check_type
|
55
|
+
@health_check_config = Settings.worker_health_check_config
|
54
56
|
@config = options
|
55
57
|
@job_count = 0
|
56
58
|
|
@@ -99,6 +101,8 @@ class Worker
|
|
99
101
|
trap(sig) { @signal_queue << sig; wake_up }
|
100
102
|
end
|
101
103
|
|
104
|
+
health_check.start
|
105
|
+
|
102
106
|
signal_processor = Thread.new do
|
103
107
|
loop do
|
104
108
|
@self_pipe[0].read(1)
|
@@ -121,14 +125,17 @@ class Worker
|
|
121
125
|
end
|
122
126
|
end
|
123
127
|
|
124
|
-
work_queue.close
|
125
|
-
signal_processor.kill
|
126
|
-
signal_processor.join
|
127
128
|
logger.info "Stopping worker"
|
128
129
|
rescue => e
|
129
130
|
Rails.logger.fatal("Child process died: #{e.inspect}") rescue nil
|
130
131
|
self.class.lifecycle.run_callbacks(:exceptional_exit, self, e) { }
|
131
132
|
ensure
|
133
|
+
health_check.stop
|
134
|
+
work_queue.close
|
135
|
+
if signal_processor
|
136
|
+
signal_processor.kill
|
137
|
+
signal_processor.join
|
138
|
+
end
|
132
139
|
Delayed::Job.clear_locks!(name)
|
133
140
|
end
|
134
141
|
|
@@ -248,6 +255,14 @@ class Worker
|
|
248
255
|
ENV['TMPDIR'] = previous_tmpdir
|
249
256
|
end
|
250
257
|
|
258
|
+
def health_check
|
259
|
+
@health_check ||= HealthCheck.build(
|
260
|
+
type: @health_check_type,
|
261
|
+
worker_name: name,
|
262
|
+
config: @health_check_config
|
263
|
+
)
|
264
|
+
end
|
265
|
+
|
251
266
|
# `sample` reports KB, not B
|
252
267
|
if File.directory?("/proc")
|
253
268
|
# linux w/ proc fs
|
data/lib/delayed_job.rb
CHANGED
@@ -36,6 +36,11 @@ require 'delayed/periodic'
|
|
36
36
|
require 'delayed/plugin'
|
37
37
|
require 'delayed/pool'
|
38
38
|
require 'delayed/worker'
|
39
|
+
|
40
|
+
require 'delayed/worker/health_check'
|
41
|
+
require 'delayed/worker/consul_health_check'
|
42
|
+
require 'delayed/worker/null_health_check'
|
43
|
+
|
39
44
|
require 'delayed/work_queue/in_process'
|
40
45
|
require 'delayed/work_queue/parent_process'
|
41
46
|
|
@@ -0,0 +1,74 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
require 'imperium'
|
3
|
+
|
4
|
+
RSpec.describe Delayed::Worker::ConsulHealthCheck do
|
5
|
+
let(:health_check) { Delayed::Worker::ConsulHealthCheck.new(worker_name: 'foobar') }
|
6
|
+
|
7
|
+
# can't use a verifying double for the response because the methods we're
|
8
|
+
# tryig to stub are actually on HTTP::Message
|
9
|
+
let(:response) { double('Imperium::Response') }
|
10
|
+
let(:agent_client) { instance_double(Imperium::Agent) }
|
11
|
+
|
12
|
+
before do
|
13
|
+
allow(Imperium::Agent).to receive(:default_client).and_return(agent_client)
|
14
|
+
end
|
15
|
+
|
16
|
+
describe '#initialize' do
|
17
|
+
it 'must use the default agent client when the config is mostly empty' do
|
18
|
+
check = Delayed::Worker::ConsulHealthCheck.new({worker_name: 'foobar'})
|
19
|
+
expect(check.agent_client).to eq Imperium::Agent.default_client
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'must create a new agent API client when the config has relevant keys set' do
|
23
|
+
check = Delayed::Worker::ConsulHealthCheck.new(worker_name: 'foobar', config: {url: 'http://consul.example.com:8500'})
|
24
|
+
agent_client = check.agent_client
|
25
|
+
expect(agent_client).to_not eq Imperium::Agent.default_client
|
26
|
+
expect(agent_client.config.url.to_s).to eq 'http://consul.example.com:8500'
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
describe '#start' do
|
31
|
+
it 'must register this process as a service with consul' do
|
32
|
+
expect(response).to receive(:ok?).and_return(true)
|
33
|
+
expect(agent_client).to receive(:register_service)
|
34
|
+
.with(an_instance_of(Imperium::Service))
|
35
|
+
.and_return(response)
|
36
|
+
health_check.start
|
37
|
+
end
|
38
|
+
|
39
|
+
|
40
|
+
it 'must supply a script style check' do
|
41
|
+
allow(response).to receive(:ok?).and_return(true)
|
42
|
+
allow(agent_client).to receive(:register_service) { |service|
|
43
|
+
check = service.checks.first
|
44
|
+
expect(check.script).to_not be_nil
|
45
|
+
response
|
46
|
+
}
|
47
|
+
health_check.start
|
48
|
+
end
|
49
|
+
|
50
|
+
it 'must include the docker container id when the docker option is set to true' do
|
51
|
+
local_health_check = Delayed::Worker::ConsulHealthCheck.new(
|
52
|
+
worker_name: 'foobar',
|
53
|
+
config: {docker: true}
|
54
|
+
)
|
55
|
+
allow(response).to receive(:ok?).and_return(true)
|
56
|
+
allow(agent_client).to receive(:register_service) { |service|
|
57
|
+
check = service.checks.first
|
58
|
+
expect(check.docker_container_id).to_not be_nil
|
59
|
+
response
|
60
|
+
}
|
61
|
+
local_health_check.start
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
describe '#stop' do
|
66
|
+
it 'must deregister the service from consul' do
|
67
|
+
allow(response).to receive(:ok?).and_return(true)
|
68
|
+
expect(agent_client).to receive(:deregister_service)
|
69
|
+
.with(health_check.worker_name)
|
70
|
+
.and_return(response)
|
71
|
+
health_check.stop
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
@@ -0,0 +1,98 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
RSpec.describe Delayed::Worker::HealthCheck do
|
4
|
+
let(:klass) { Class.new(Delayed::Worker::HealthCheck) { self.type_name = :test } }
|
5
|
+
|
6
|
+
before do
|
7
|
+
klass # Gotta make sure the class has been defined before we try to use it
|
8
|
+
end
|
9
|
+
|
10
|
+
after do
|
11
|
+
Delayed::Worker::HealthCheck.subclasses.delete(klass)
|
12
|
+
end
|
13
|
+
|
14
|
+
it "must maintain a list of its subclasses" do
|
15
|
+
klass
|
16
|
+
expect(Delayed::Worker::HealthCheck.subclasses).to include klass
|
17
|
+
end
|
18
|
+
|
19
|
+
describe '.build(type:, config: {})' do
|
20
|
+
it 'must select the concrete class to use by the type_name in the subclass' do
|
21
|
+
check = Delayed::Worker::HealthCheck.build(type: 'test', worker_name: 'foobar')
|
22
|
+
expect(check).to be_a(klass)
|
23
|
+
end
|
24
|
+
|
25
|
+
it "must raise ArgumentError when the specified type doesn't exist" do
|
26
|
+
expect {
|
27
|
+
Delayed::Worker::HealthCheck.build(type: 'nope', config: {worker_name: 'foobar'})
|
28
|
+
}.to raise_error ArgumentError
|
29
|
+
end
|
30
|
+
|
31
|
+
it 'must initiaize the specified class using the supplied config' do
|
32
|
+
config = {foo: 'bar'}.with_indifferent_access
|
33
|
+
check = Delayed::Worker::HealthCheck.build(type: 'test', worker_name: 'foobar', config: config)
|
34
|
+
expect(check.config).to eq config
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
describe '.reschedule_abandoned_jobs' do
|
39
|
+
let(:klass) { Class.new(Delayed::Worker::HealthCheck) {
|
40
|
+
self.type_name = :fake
|
41
|
+
class << self
|
42
|
+
attr_accessor :live_workers
|
43
|
+
end
|
44
|
+
|
45
|
+
def live_workers
|
46
|
+
self.class.live_workers
|
47
|
+
end
|
48
|
+
} }
|
49
|
+
|
50
|
+
let(:initial_run_at) { Time.zone.now }
|
51
|
+
|
52
|
+
before do
|
53
|
+
klass.live_workers = %w{alive}
|
54
|
+
Delayed.select_backend(Delayed::Backend::ActiveRecord::Job)
|
55
|
+
|
56
|
+
2.times { Delayed::Job.enqueue(SimpleJob.new, run_at: initial_run_at, max_attempts: 4) }
|
57
|
+
@alive_job = Delayed::Job.first
|
58
|
+
@alive_job.update_attributes!({
|
59
|
+
locked_by: 'alive',
|
60
|
+
locked_at: initial_run_at
|
61
|
+
})
|
62
|
+
@dead_job = Delayed::Job.last
|
63
|
+
@dead_job.update_attributes!({
|
64
|
+
locked_by: 'dead',
|
65
|
+
locked_at: initial_run_at
|
66
|
+
})
|
67
|
+
Delayed::Settings.worker_health_check_type = :fake
|
68
|
+
Delayed::Settings.worker_health_check_config = {}
|
69
|
+
Delayed::Worker::HealthCheck.reschedule_abandoned_jobs
|
70
|
+
end
|
71
|
+
|
72
|
+
after do
|
73
|
+
Delayed::Worker::HealthCheck.subclasses.delete(klass)
|
74
|
+
Delayed::Settings.worker_health_check_type = :none
|
75
|
+
Delayed::Settings.worker_health_check_config = {}
|
76
|
+
end
|
77
|
+
|
78
|
+
it 'must leave jobs locked by live workers alone' do
|
79
|
+
@alive_job.reload
|
80
|
+
expect(@alive_job.run_at.to_i).to eq initial_run_at.to_i
|
81
|
+
expect(@alive_job.locked_at.to_i).to eq initial_run_at.to_i
|
82
|
+
expect(@alive_job.locked_by).to eq 'alive'
|
83
|
+
end
|
84
|
+
|
85
|
+
it 'must reschedule jobs locked by dead workers' do
|
86
|
+
@dead_job.reload
|
87
|
+
expect(@dead_job.run_at).to be > initial_run_at
|
88
|
+
expect(@dead_job.locked_at).to be_nil
|
89
|
+
expect(@dead_job.locked_by).to be_nil
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
describe '#initialize' do
|
94
|
+
it 'must raise ArgumentError when the worker name is not supplied' do
|
95
|
+
expect { klass.new }.to raise_error ArgumentError
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
@@ -356,6 +356,19 @@ shared_examples_for 'a backend' do
|
|
356
356
|
# it should be scheduled to run immediately
|
357
357
|
Delayed::Job.get_and_lock_next_available('w1').should == job1
|
358
358
|
end
|
359
|
+
|
360
|
+
it "should update existing job to a later date if requested" do
|
361
|
+
t1 = 1.hour.from_now
|
362
|
+
t2 = 2.hours.from_now
|
363
|
+
job1 = create_job(singleton: 'myjobs', run_at: t1)
|
364
|
+
job2 = create_job(singleton: 'myjobs', run_at: t2)
|
365
|
+
job2.should == job1
|
366
|
+
job2.run_at.to_i.should == t1.to_i
|
367
|
+
|
368
|
+
job3 = create_job(singleton: 'myjobs', run_at: t2, on_conflict: :overwrite)
|
369
|
+
job3.should == job1
|
370
|
+
job3.run_at.to_i.should == t2.to_i
|
371
|
+
end
|
359
372
|
end
|
360
373
|
end
|
361
374
|
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: inst-jobs
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.14.
|
4
|
+
version: 0.14.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Tobias Luetke
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: exe
|
11
11
|
cert_chain: []
|
12
|
-
date: 2017-
|
12
|
+
date: 2017-11-13 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: after_transaction_commit
|
@@ -255,6 +255,20 @@ dependencies:
|
|
255
255
|
- - ">="
|
256
256
|
- !ruby/object:Gem::Version
|
257
257
|
version: '0'
|
258
|
+
- !ruby/object:Gem::Dependency
|
259
|
+
name: imperium
|
260
|
+
requirement: !ruby/object:Gem::Requirement
|
261
|
+
requirements:
|
262
|
+
- - ">="
|
263
|
+
- !ruby/object:Gem::Version
|
264
|
+
version: 0.2.3
|
265
|
+
type: :development
|
266
|
+
prerelease: false
|
267
|
+
version_requirements: !ruby/object:Gem::Requirement
|
268
|
+
requirements:
|
269
|
+
- - ">="
|
270
|
+
- !ruby/object:Gem::Version
|
271
|
+
version: 0.2.3
|
258
272
|
description:
|
259
273
|
email:
|
260
274
|
- brianp@instructure.com
|
@@ -325,6 +339,9 @@ files:
|
|
325
339
|
- lib/delayed/work_queue/parent_process/client.rb
|
326
340
|
- lib/delayed/work_queue/parent_process/server.rb
|
327
341
|
- lib/delayed/worker.rb
|
342
|
+
- lib/delayed/worker/consul_health_check.rb
|
343
|
+
- lib/delayed/worker/health_check.rb
|
344
|
+
- lib/delayed/worker/null_health_check.rb
|
328
345
|
- lib/delayed/yaml_extensions.rb
|
329
346
|
- lib/delayed_job.rb
|
330
347
|
- lib/inst-jobs.rb
|
@@ -337,13 +354,12 @@ files:
|
|
337
354
|
- spec/delayed/work_queue/parent_process/client_spec.rb
|
338
355
|
- spec/delayed/work_queue/parent_process/server_spec.rb
|
339
356
|
- spec/delayed/work_queue/parent_process_spec.rb
|
357
|
+
- spec/delayed/worker/consul_health_check_spec.rb
|
358
|
+
- spec/delayed/worker/health_check_spec.rb
|
340
359
|
- spec/delayed/worker_spec.rb
|
341
360
|
- spec/gemfiles/42.gemfile
|
342
|
-
- spec/gemfiles/42.gemfile.lock
|
343
361
|
- spec/gemfiles/50.gemfile
|
344
|
-
- spec/gemfiles/50.gemfile.lock
|
345
362
|
- spec/gemfiles/51.gemfile
|
346
|
-
- spec/gemfiles/51.gemfile.lock
|
347
363
|
- spec/migrate/20140924140513_add_story_table.rb
|
348
364
|
- spec/redis_job_spec.rb
|
349
365
|
- spec/sample_jobs.rb
|
@@ -374,7 +390,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
374
390
|
version: '0'
|
375
391
|
requirements: []
|
376
392
|
rubyforge_project:
|
377
|
-
rubygems_version: 2.6.
|
393
|
+
rubygems_version: 2.6.10
|
378
394
|
signing_key:
|
379
395
|
specification_version: 4
|
380
396
|
summary: Instructure-maintained fork of delayed_job
|
@@ -388,13 +404,12 @@ test_files:
|
|
388
404
|
- spec/delayed/work_queue/parent_process/client_spec.rb
|
389
405
|
- spec/delayed/work_queue/parent_process/server_spec.rb
|
390
406
|
- spec/delayed/work_queue/parent_process_spec.rb
|
407
|
+
- spec/delayed/worker/consul_health_check_spec.rb
|
408
|
+
- spec/delayed/worker/health_check_spec.rb
|
391
409
|
- spec/delayed/worker_spec.rb
|
392
410
|
- spec/gemfiles/42.gemfile
|
393
|
-
- spec/gemfiles/42.gemfile.lock
|
394
411
|
- spec/gemfiles/50.gemfile
|
395
|
-
- spec/gemfiles/50.gemfile.lock
|
396
412
|
- spec/gemfiles/51.gemfile
|
397
|
-
- spec/gemfiles/51.gemfile.lock
|
398
413
|
- spec/migrate/20140924140513_add_story_table.rb
|
399
414
|
- spec/redis_job_spec.rb
|
400
415
|
- spec/sample_jobs.rb
|
@@ -1,182 +0,0 @@
|
|
1
|
-
PATH
|
2
|
-
remote: ../..
|
3
|
-
specs:
|
4
|
-
inst-jobs (0.13.4)
|
5
|
-
after_transaction_commit (>= 1.0, < 3)
|
6
|
-
rails (>= 4.2)
|
7
|
-
redis (> 3.0)
|
8
|
-
redis-scripting (~> 1.0.1)
|
9
|
-
rufus-scheduler (~> 3.4)
|
10
|
-
|
11
|
-
GEM
|
12
|
-
remote: https://rubygems.org/
|
13
|
-
specs:
|
14
|
-
actionmailer (4.2.9)
|
15
|
-
actionpack (= 4.2.9)
|
16
|
-
actionview (= 4.2.9)
|
17
|
-
activejob (= 4.2.9)
|
18
|
-
mail (~> 2.5, >= 2.5.4)
|
19
|
-
rails-dom-testing (~> 1.0, >= 1.0.5)
|
20
|
-
actionpack (4.2.9)
|
21
|
-
actionview (= 4.2.9)
|
22
|
-
activesupport (= 4.2.9)
|
23
|
-
rack (~> 1.6)
|
24
|
-
rack-test (~> 0.6.2)
|
25
|
-
rails-dom-testing (~> 1.0, >= 1.0.5)
|
26
|
-
rails-html-sanitizer (~> 1.0, >= 1.0.2)
|
27
|
-
actionview (4.2.9)
|
28
|
-
activesupport (= 4.2.9)
|
29
|
-
builder (~> 3.1)
|
30
|
-
erubis (~> 2.7.0)
|
31
|
-
rails-dom-testing (~> 1.0, >= 1.0.5)
|
32
|
-
rails-html-sanitizer (~> 1.0, >= 1.0.3)
|
33
|
-
activejob (4.2.9)
|
34
|
-
activesupport (= 4.2.9)
|
35
|
-
globalid (>= 0.3.0)
|
36
|
-
activemodel (4.2.9)
|
37
|
-
activesupport (= 4.2.9)
|
38
|
-
builder (~> 3.1)
|
39
|
-
activerecord (4.2.9)
|
40
|
-
activemodel (= 4.2.9)
|
41
|
-
activesupport (= 4.2.9)
|
42
|
-
arel (~> 6.0)
|
43
|
-
activesupport (4.2.9)
|
44
|
-
i18n (~> 0.7)
|
45
|
-
minitest (~> 5.1)
|
46
|
-
thread_safe (~> 0.3, >= 0.3.4)
|
47
|
-
tzinfo (~> 1.1)
|
48
|
-
after_transaction_commit (1.1.2)
|
49
|
-
activerecord (>= 4.0)
|
50
|
-
arel (6.0.4)
|
51
|
-
backports (3.8.0)
|
52
|
-
builder (3.2.3)
|
53
|
-
bump (0.5.4)
|
54
|
-
byebug (9.0.6)
|
55
|
-
coderay (1.1.1)
|
56
|
-
concurrent-ruby (1.0.5)
|
57
|
-
database_cleaner (1.6.1)
|
58
|
-
diff-lcs (1.3)
|
59
|
-
erubis (2.7.0)
|
60
|
-
et-orbi (1.0.5)
|
61
|
-
tzinfo
|
62
|
-
globalid (0.4.0)
|
63
|
-
activesupport (>= 4.2.0)
|
64
|
-
i18n (0.8.6)
|
65
|
-
loofah (2.0.3)
|
66
|
-
nokogiri (>= 1.5.9)
|
67
|
-
mail (2.6.6)
|
68
|
-
mime-types (>= 1.16, < 4)
|
69
|
-
method_source (0.8.2)
|
70
|
-
mime-types (3.1)
|
71
|
-
mime-types-data (~> 3.2015)
|
72
|
-
mime-types-data (3.2016.0521)
|
73
|
-
mini_portile2 (2.2.0)
|
74
|
-
minitest (5.10.3)
|
75
|
-
multi_json (1.12.1)
|
76
|
-
nokogiri (1.8.0)
|
77
|
-
mini_portile2 (~> 2.2.0)
|
78
|
-
pg (0.21.0)
|
79
|
-
pry (0.10.4)
|
80
|
-
coderay (~> 1.1.0)
|
81
|
-
method_source (~> 0.8.1)
|
82
|
-
slop (~> 3.4)
|
83
|
-
rack (1.6.8)
|
84
|
-
rack-protection (1.5.3)
|
85
|
-
rack
|
86
|
-
rack-test (0.6.3)
|
87
|
-
rack (>= 1.0)
|
88
|
-
rails (4.2.9)
|
89
|
-
actionmailer (= 4.2.9)
|
90
|
-
actionpack (= 4.2.9)
|
91
|
-
actionview (= 4.2.9)
|
92
|
-
activejob (= 4.2.9)
|
93
|
-
activemodel (= 4.2.9)
|
94
|
-
activerecord (= 4.2.9)
|
95
|
-
activesupport (= 4.2.9)
|
96
|
-
bundler (>= 1.3.0, < 2.0)
|
97
|
-
railties (= 4.2.9)
|
98
|
-
sprockets-rails
|
99
|
-
rails-deprecated_sanitizer (1.0.3)
|
100
|
-
activesupport (>= 4.2.0.alpha)
|
101
|
-
rails-dom-testing (1.0.8)
|
102
|
-
activesupport (>= 4.2.0.beta, < 5.0)
|
103
|
-
nokogiri (~> 1.6)
|
104
|
-
rails-deprecated_sanitizer (>= 1.0.1)
|
105
|
-
rails-html-sanitizer (1.0.3)
|
106
|
-
loofah (~> 2.0)
|
107
|
-
railties (4.2.9)
|
108
|
-
actionpack (= 4.2.9)
|
109
|
-
activesupport (= 4.2.9)
|
110
|
-
rake (>= 0.8.7)
|
111
|
-
thor (>= 0.18.1, < 2.0)
|
112
|
-
rake (12.0.0)
|
113
|
-
redis (3.3.3)
|
114
|
-
redis-scripting (1.0.1)
|
115
|
-
redis (>= 3.0)
|
116
|
-
rspec (3.4.0)
|
117
|
-
rspec-core (~> 3.4.0)
|
118
|
-
rspec-expectations (~> 3.4.0)
|
119
|
-
rspec-mocks (~> 3.4.0)
|
120
|
-
rspec-core (3.4.4)
|
121
|
-
rspec-support (~> 3.4.0)
|
122
|
-
rspec-expectations (3.4.0)
|
123
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
124
|
-
rspec-support (~> 3.4.0)
|
125
|
-
rspec-mocks (3.4.1)
|
126
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
127
|
-
rspec-support (~> 3.4.0)
|
128
|
-
rspec-support (3.4.1)
|
129
|
-
rufus-scheduler (3.4.2)
|
130
|
-
et-orbi (~> 1.0)
|
131
|
-
sinatra (1.4.8)
|
132
|
-
rack (~> 1.5)
|
133
|
-
rack-protection (~> 1.4)
|
134
|
-
tilt (>= 1.3, < 3)
|
135
|
-
sinatra-contrib (1.4.7)
|
136
|
-
backports (>= 2.0)
|
137
|
-
multi_json
|
138
|
-
rack-protection
|
139
|
-
rack-test
|
140
|
-
sinatra (~> 1.4.0)
|
141
|
-
tilt (>= 1.3, < 3)
|
142
|
-
slop (3.6.0)
|
143
|
-
sprockets (3.7.1)
|
144
|
-
concurrent-ruby (~> 1.0)
|
145
|
-
rack (> 1, < 3)
|
146
|
-
sprockets-rails (3.2.0)
|
147
|
-
actionpack (>= 4.0)
|
148
|
-
activesupport (>= 4.0)
|
149
|
-
sprockets (>= 3.0.0)
|
150
|
-
test_after_commit (0.4.1)
|
151
|
-
activerecord (>= 3.2)
|
152
|
-
thor (0.19.4)
|
153
|
-
thread_safe (0.3.6)
|
154
|
-
tilt (2.0.8)
|
155
|
-
timecop (0.7.1)
|
156
|
-
tzinfo (1.2.3)
|
157
|
-
thread_safe (~> 0.1)
|
158
|
-
wwtd (1.3.0)
|
159
|
-
|
160
|
-
PLATFORMS
|
161
|
-
ruby
|
162
|
-
|
163
|
-
DEPENDENCIES
|
164
|
-
after_transaction_commit (< 2)
|
165
|
-
bump
|
166
|
-
byebug
|
167
|
-
database_cleaner (= 1.6.1)
|
168
|
-
inst-jobs!
|
169
|
-
pg
|
170
|
-
pry
|
171
|
-
rack-test
|
172
|
-
rails (~> 4.2.5)
|
173
|
-
rake
|
174
|
-
rspec (= 3.4.0)
|
175
|
-
sinatra
|
176
|
-
sinatra-contrib
|
177
|
-
test_after_commit (= 0.4.1)
|
178
|
-
timecop (= 0.7.1)
|
179
|
-
wwtd (~> 1.3.0)
|
180
|
-
|
181
|
-
BUNDLED WITH
|
182
|
-
1.15.3
|
@@ -1,187 +0,0 @@
|
|
1
|
-
PATH
|
2
|
-
remote: ../..
|
3
|
-
specs:
|
4
|
-
inst-jobs (0.13.4)
|
5
|
-
after_transaction_commit (>= 1.0, < 3)
|
6
|
-
rails (>= 4.2)
|
7
|
-
redis (> 3.0)
|
8
|
-
redis-scripting (~> 1.0.1)
|
9
|
-
rufus-scheduler (~> 3.4)
|
10
|
-
|
11
|
-
GEM
|
12
|
-
remote: https://rubygems.org/
|
13
|
-
specs:
|
14
|
-
actioncable (5.0.5)
|
15
|
-
actionpack (= 5.0.5)
|
16
|
-
nio4r (>= 1.2, < 3.0)
|
17
|
-
websocket-driver (~> 0.6.1)
|
18
|
-
actionmailer (5.0.5)
|
19
|
-
actionpack (= 5.0.5)
|
20
|
-
actionview (= 5.0.5)
|
21
|
-
activejob (= 5.0.5)
|
22
|
-
mail (~> 2.5, >= 2.5.4)
|
23
|
-
rails-dom-testing (~> 2.0)
|
24
|
-
actionpack (5.0.5)
|
25
|
-
actionview (= 5.0.5)
|
26
|
-
activesupport (= 5.0.5)
|
27
|
-
rack (~> 2.0)
|
28
|
-
rack-test (~> 0.6.3)
|
29
|
-
rails-dom-testing (~> 2.0)
|
30
|
-
rails-html-sanitizer (~> 1.0, >= 1.0.2)
|
31
|
-
actionview (5.0.5)
|
32
|
-
activesupport (= 5.0.5)
|
33
|
-
builder (~> 3.1)
|
34
|
-
erubis (~> 2.7.0)
|
35
|
-
rails-dom-testing (~> 2.0)
|
36
|
-
rails-html-sanitizer (~> 1.0, >= 1.0.3)
|
37
|
-
activejob (5.0.5)
|
38
|
-
activesupport (= 5.0.5)
|
39
|
-
globalid (>= 0.3.6)
|
40
|
-
activemodel (5.0.5)
|
41
|
-
activesupport (= 5.0.5)
|
42
|
-
activerecord (5.0.5)
|
43
|
-
activemodel (= 5.0.5)
|
44
|
-
activesupport (= 5.0.5)
|
45
|
-
arel (~> 7.0)
|
46
|
-
activesupport (5.0.5)
|
47
|
-
concurrent-ruby (~> 1.0, >= 1.0.2)
|
48
|
-
i18n (~> 0.7)
|
49
|
-
minitest (~> 5.1)
|
50
|
-
tzinfo (~> 1.1)
|
51
|
-
after_transaction_commit (2.0.0)
|
52
|
-
activerecord (>= 5.0)
|
53
|
-
arel (7.1.4)
|
54
|
-
backports (3.8.0)
|
55
|
-
builder (3.2.3)
|
56
|
-
bump (0.5.4)
|
57
|
-
byebug (9.0.6)
|
58
|
-
coderay (1.1.1)
|
59
|
-
concurrent-ruby (1.0.5)
|
60
|
-
database_cleaner (1.6.1)
|
61
|
-
diff-lcs (1.3)
|
62
|
-
erubis (2.7.0)
|
63
|
-
et-orbi (1.0.5)
|
64
|
-
tzinfo
|
65
|
-
globalid (0.4.0)
|
66
|
-
activesupport (>= 4.2.0)
|
67
|
-
i18n (0.8.6)
|
68
|
-
loofah (2.0.3)
|
69
|
-
nokogiri (>= 1.5.9)
|
70
|
-
mail (2.6.6)
|
71
|
-
mime-types (>= 1.16, < 4)
|
72
|
-
method_source (0.8.2)
|
73
|
-
mime-types (3.1)
|
74
|
-
mime-types-data (~> 3.2015)
|
75
|
-
mime-types-data (3.2016.0521)
|
76
|
-
mini_portile2 (2.2.0)
|
77
|
-
minitest (5.10.3)
|
78
|
-
multi_json (1.12.1)
|
79
|
-
mustermann (1.0.0.beta2)
|
80
|
-
nio4r (2.1.0)
|
81
|
-
nokogiri (1.8.0)
|
82
|
-
mini_portile2 (~> 2.2.0)
|
83
|
-
pg (0.21.0)
|
84
|
-
pry (0.10.4)
|
85
|
-
coderay (~> 1.1.0)
|
86
|
-
method_source (~> 0.8.1)
|
87
|
-
slop (~> 3.4)
|
88
|
-
rack (2.0.3)
|
89
|
-
rack-protection (2.0.0.beta2)
|
90
|
-
rack
|
91
|
-
rack-test (0.6.3)
|
92
|
-
rack (>= 1.0)
|
93
|
-
rails (5.0.5)
|
94
|
-
actioncable (= 5.0.5)
|
95
|
-
actionmailer (= 5.0.5)
|
96
|
-
actionpack (= 5.0.5)
|
97
|
-
actionview (= 5.0.5)
|
98
|
-
activejob (= 5.0.5)
|
99
|
-
activemodel (= 5.0.5)
|
100
|
-
activerecord (= 5.0.5)
|
101
|
-
activesupport (= 5.0.5)
|
102
|
-
bundler (>= 1.3.0)
|
103
|
-
railties (= 5.0.5)
|
104
|
-
sprockets-rails (>= 2.0.0)
|
105
|
-
rails-dom-testing (2.0.3)
|
106
|
-
activesupport (>= 4.2.0)
|
107
|
-
nokogiri (>= 1.6)
|
108
|
-
rails-html-sanitizer (1.0.3)
|
109
|
-
loofah (~> 2.0)
|
110
|
-
railties (5.0.5)
|
111
|
-
actionpack (= 5.0.5)
|
112
|
-
activesupport (= 5.0.5)
|
113
|
-
method_source
|
114
|
-
rake (>= 0.8.7)
|
115
|
-
thor (>= 0.18.1, < 2.0)
|
116
|
-
rake (12.0.0)
|
117
|
-
redis (3.3.3)
|
118
|
-
redis-scripting (1.0.1)
|
119
|
-
redis (>= 3.0)
|
120
|
-
rspec (3.4.0)
|
121
|
-
rspec-core (~> 3.4.0)
|
122
|
-
rspec-expectations (~> 3.4.0)
|
123
|
-
rspec-mocks (~> 3.4.0)
|
124
|
-
rspec-core (3.4.4)
|
125
|
-
rspec-support (~> 3.4.0)
|
126
|
-
rspec-expectations (3.4.0)
|
127
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
128
|
-
rspec-support (~> 3.4.0)
|
129
|
-
rspec-mocks (3.4.1)
|
130
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
131
|
-
rspec-support (~> 3.4.0)
|
132
|
-
rspec-support (3.4.1)
|
133
|
-
rufus-scheduler (3.4.2)
|
134
|
-
et-orbi (~> 1.0)
|
135
|
-
sinatra (2.0.0.beta2)
|
136
|
-
mustermann (= 1.0.0.beta2)
|
137
|
-
rack (~> 2.0)
|
138
|
-
rack-protection (= 2.0.0.beta2)
|
139
|
-
tilt (~> 2.0)
|
140
|
-
sinatra-contrib (2.0.0.beta2)
|
141
|
-
backports (>= 2.0)
|
142
|
-
multi_json
|
143
|
-
mustermann (= 1.0.0.beta2)
|
144
|
-
rack-protection (= 2.0.0.beta2)
|
145
|
-
rack-test
|
146
|
-
sinatra (= 2.0.0.beta2)
|
147
|
-
tilt (>= 1.3, < 3)
|
148
|
-
slop (3.6.0)
|
149
|
-
sprockets (3.7.1)
|
150
|
-
concurrent-ruby (~> 1.0)
|
151
|
-
rack (> 1, < 3)
|
152
|
-
sprockets-rails (3.2.0)
|
153
|
-
actionpack (>= 4.0)
|
154
|
-
activesupport (>= 4.0)
|
155
|
-
sprockets (>= 3.0.0)
|
156
|
-
thor (0.19.4)
|
157
|
-
thread_safe (0.3.6)
|
158
|
-
tilt (2.0.8)
|
159
|
-
timecop (0.7.1)
|
160
|
-
tzinfo (1.2.3)
|
161
|
-
thread_safe (~> 0.1)
|
162
|
-
websocket-driver (0.6.5)
|
163
|
-
websocket-extensions (>= 0.1.0)
|
164
|
-
websocket-extensions (0.1.2)
|
165
|
-
wwtd (1.3.0)
|
166
|
-
|
167
|
-
PLATFORMS
|
168
|
-
ruby
|
169
|
-
|
170
|
-
DEPENDENCIES
|
171
|
-
bump
|
172
|
-
byebug
|
173
|
-
database_cleaner (= 1.6.1)
|
174
|
-
inst-jobs!
|
175
|
-
pg
|
176
|
-
pry
|
177
|
-
rack-test
|
178
|
-
rails (~> 5.0.0)
|
179
|
-
rake
|
180
|
-
rspec (= 3.4.0)
|
181
|
-
sinatra (= 2.0.0.beta2)
|
182
|
-
sinatra-contrib (= 2.0.0.beta2)
|
183
|
-
timecop (= 0.7.1)
|
184
|
-
wwtd (~> 1.3.0)
|
185
|
-
|
186
|
-
BUNDLED WITH
|
187
|
-
1.15.3
|
@@ -1,187 +0,0 @@
|
|
1
|
-
PATH
|
2
|
-
remote: ../..
|
3
|
-
specs:
|
4
|
-
inst-jobs (0.13.3)
|
5
|
-
after_transaction_commit (~> 1.0)
|
6
|
-
rails (>= 4.2)
|
7
|
-
redis (> 3.0)
|
8
|
-
redis-scripting (~> 1.0.1)
|
9
|
-
rufus-scheduler (~> 3.4)
|
10
|
-
|
11
|
-
GEM
|
12
|
-
remote: https://rubygems.org/
|
13
|
-
specs:
|
14
|
-
actioncable (5.1.1)
|
15
|
-
actionpack (= 5.1.1)
|
16
|
-
nio4r (~> 2.0)
|
17
|
-
websocket-driver (~> 0.6.1)
|
18
|
-
actionmailer (5.1.1)
|
19
|
-
actionpack (= 5.1.1)
|
20
|
-
actionview (= 5.1.1)
|
21
|
-
activejob (= 5.1.1)
|
22
|
-
mail (~> 2.5, >= 2.5.4)
|
23
|
-
rails-dom-testing (~> 2.0)
|
24
|
-
actionpack (5.1.1)
|
25
|
-
actionview (= 5.1.1)
|
26
|
-
activesupport (= 5.1.1)
|
27
|
-
rack (~> 2.0)
|
28
|
-
rack-test (~> 0.6.3)
|
29
|
-
rails-dom-testing (~> 2.0)
|
30
|
-
rails-html-sanitizer (~> 1.0, >= 1.0.2)
|
31
|
-
actionview (5.1.1)
|
32
|
-
activesupport (= 5.1.1)
|
33
|
-
builder (~> 3.1)
|
34
|
-
erubi (~> 1.4)
|
35
|
-
rails-dom-testing (~> 2.0)
|
36
|
-
rails-html-sanitizer (~> 1.0, >= 1.0.3)
|
37
|
-
activejob (5.1.1)
|
38
|
-
activesupport (= 5.1.1)
|
39
|
-
globalid (>= 0.3.6)
|
40
|
-
activemodel (5.1.1)
|
41
|
-
activesupport (= 5.1.1)
|
42
|
-
activerecord (5.1.1)
|
43
|
-
activemodel (= 5.1.1)
|
44
|
-
activesupport (= 5.1.1)
|
45
|
-
arel (~> 8.0)
|
46
|
-
activesupport (5.1.1)
|
47
|
-
concurrent-ruby (~> 1.0, >= 1.0.2)
|
48
|
-
i18n (~> 0.7)
|
49
|
-
minitest (~> 5.1)
|
50
|
-
tzinfo (~> 1.1)
|
51
|
-
after_transaction_commit (1.1.2)
|
52
|
-
activerecord (>= 4.0)
|
53
|
-
arel (8.0.0)
|
54
|
-
backports (3.7.0)
|
55
|
-
builder (3.2.3)
|
56
|
-
bump (0.5.3)
|
57
|
-
byebug (9.0.6)
|
58
|
-
coderay (1.1.1)
|
59
|
-
concurrent-ruby (1.0.5)
|
60
|
-
database_cleaner (1.6.1)
|
61
|
-
diff-lcs (1.3)
|
62
|
-
erubi (1.6.0)
|
63
|
-
et-orbi (1.0.3)
|
64
|
-
tzinfo
|
65
|
-
globalid (0.4.0)
|
66
|
-
activesupport (>= 4.2.0)
|
67
|
-
i18n (0.8.4)
|
68
|
-
loofah (2.0.3)
|
69
|
-
nokogiri (>= 1.5.9)
|
70
|
-
mail (2.6.6)
|
71
|
-
mime-types (>= 1.16, < 4)
|
72
|
-
method_source (0.8.2)
|
73
|
-
mime-types (3.1)
|
74
|
-
mime-types-data (~> 3.2015)
|
75
|
-
mime-types-data (3.2016.0521)
|
76
|
-
mini_portile2 (2.2.0)
|
77
|
-
minitest (5.10.2)
|
78
|
-
multi_json (1.12.1)
|
79
|
-
mustermann (1.0.0.beta2)
|
80
|
-
nio4r (2.1.0)
|
81
|
-
nokogiri (1.8.0)
|
82
|
-
mini_portile2 (~> 2.2.0)
|
83
|
-
pg (0.21.0)
|
84
|
-
pry (0.10.4)
|
85
|
-
coderay (~> 1.1.0)
|
86
|
-
method_source (~> 0.8.1)
|
87
|
-
slop (~> 3.4)
|
88
|
-
rack (2.0.3)
|
89
|
-
rack-protection (2.0.0.beta2)
|
90
|
-
rack
|
91
|
-
rack-test (0.6.3)
|
92
|
-
rack (>= 1.0)
|
93
|
-
rails (5.1.1)
|
94
|
-
actioncable (= 5.1.1)
|
95
|
-
actionmailer (= 5.1.1)
|
96
|
-
actionpack (= 5.1.1)
|
97
|
-
actionview (= 5.1.1)
|
98
|
-
activejob (= 5.1.1)
|
99
|
-
activemodel (= 5.1.1)
|
100
|
-
activerecord (= 5.1.1)
|
101
|
-
activesupport (= 5.1.1)
|
102
|
-
bundler (>= 1.3.0, < 2.0)
|
103
|
-
railties (= 5.1.1)
|
104
|
-
sprockets-rails (>= 2.0.0)
|
105
|
-
rails-dom-testing (2.0.3)
|
106
|
-
activesupport (>= 4.2.0)
|
107
|
-
nokogiri (>= 1.6)
|
108
|
-
rails-html-sanitizer (1.0.3)
|
109
|
-
loofah (~> 2.0)
|
110
|
-
railties (5.1.1)
|
111
|
-
actionpack (= 5.1.1)
|
112
|
-
activesupport (= 5.1.1)
|
113
|
-
method_source
|
114
|
-
rake (>= 0.8.7)
|
115
|
-
thor (>= 0.18.1, < 2.0)
|
116
|
-
rake (12.0.0)
|
117
|
-
redis (3.3.3)
|
118
|
-
redis-scripting (1.0.1)
|
119
|
-
redis (>= 3.0)
|
120
|
-
rspec (3.4.0)
|
121
|
-
rspec-core (~> 3.4.0)
|
122
|
-
rspec-expectations (~> 3.4.0)
|
123
|
-
rspec-mocks (~> 3.4.0)
|
124
|
-
rspec-core (3.4.4)
|
125
|
-
rspec-support (~> 3.4.0)
|
126
|
-
rspec-expectations (3.4.0)
|
127
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
128
|
-
rspec-support (~> 3.4.0)
|
129
|
-
rspec-mocks (3.4.1)
|
130
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
131
|
-
rspec-support (~> 3.4.0)
|
132
|
-
rspec-support (3.4.1)
|
133
|
-
rufus-scheduler (3.4.0)
|
134
|
-
et-orbi (~> 1.0)
|
135
|
-
sinatra (2.0.0.beta2)
|
136
|
-
mustermann (= 1.0.0.beta2)
|
137
|
-
rack (~> 2.0)
|
138
|
-
rack-protection (= 2.0.0.beta2)
|
139
|
-
tilt (~> 2.0)
|
140
|
-
sinatra-contrib (2.0.0.beta2)
|
141
|
-
backports (>= 2.0)
|
142
|
-
multi_json
|
143
|
-
mustermann (= 1.0.0.beta2)
|
144
|
-
rack-protection (= 2.0.0.beta2)
|
145
|
-
rack-test
|
146
|
-
sinatra (= 2.0.0.beta2)
|
147
|
-
tilt (>= 1.3, < 3)
|
148
|
-
slop (3.6.0)
|
149
|
-
sprockets (3.7.1)
|
150
|
-
concurrent-ruby (~> 1.0)
|
151
|
-
rack (> 1, < 3)
|
152
|
-
sprockets-rails (3.2.0)
|
153
|
-
actionpack (>= 4.0)
|
154
|
-
activesupport (>= 4.0)
|
155
|
-
sprockets (>= 3.0.0)
|
156
|
-
thor (0.19.4)
|
157
|
-
thread_safe (0.3.6)
|
158
|
-
tilt (2.0.7)
|
159
|
-
timecop (0.7.1)
|
160
|
-
tzinfo (1.2.3)
|
161
|
-
thread_safe (~> 0.1)
|
162
|
-
websocket-driver (0.6.5)
|
163
|
-
websocket-extensions (>= 0.1.0)
|
164
|
-
websocket-extensions (0.1.2)
|
165
|
-
wwtd (1.3.0)
|
166
|
-
|
167
|
-
PLATFORMS
|
168
|
-
ruby
|
169
|
-
|
170
|
-
DEPENDENCIES
|
171
|
-
bump
|
172
|
-
byebug
|
173
|
-
database_cleaner (= 1.6.1)
|
174
|
-
inst-jobs!
|
175
|
-
pg
|
176
|
-
pry
|
177
|
-
rack-test
|
178
|
-
rails (~> 5.1.0)
|
179
|
-
rake
|
180
|
-
rspec (= 3.4.0)
|
181
|
-
sinatra (= 2.0.0.beta2)
|
182
|
-
sinatra-contrib (= 2.0.0.beta2)
|
183
|
-
timecop (= 0.7.1)
|
184
|
-
wwtd (~> 1.3.0)
|
185
|
-
|
186
|
-
BUNDLED WITH
|
187
|
-
1.14.6
|