que-scheduler 3.4.3 → 4.0.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 4ba02202915db229bcbd1c2e859f29299803507dbf61bd460008400abca3611c
4
- data.tar.gz: 6293d7b6e6766d0e75fe65df01850f356b44b030c8b8ae539eb4c71059d9d15d
3
+ metadata.gz: f6250ff590c3c280c0219d93ba57f85758a993fba1185d2064f1ba714c8c9e4c
4
+ data.tar.gz: cb49ce9c63314888e05f48cc7cd5a98817deb0df03763b9aae756055261acdbb
5
5
  SHA512:
6
- metadata.gz: d8d18550867d7d54cfb5c03aaa68876d423876a870b972cde0fbc4e8399fb616d327ef0410ebbc8e3d9021a34d73a960774eabb808f2b33a526e11ea2fb579fe
7
- data.tar.gz: bfc0e4be1f64d2b070dacb0863cc710ce13cf58cb30924fcf9f301d2e535be4ef9530740949bdb5abb90c0173924e71f7f151e4622405caf8c14a9d7d6f0469d
6
+ metadata.gz: 9516e812e2d394d5ff7c23641db0344a34c3560ad4ed02a114cc9820beee8202da9416450fbfc68f92bfaa6aed4f5bf16d1df3d2476f487a58f6f0fb32141aa1
7
+ data.tar.gz: 4d29b9a9161713935ccf1dcea71303195131fa8c27570b05a528fdec68d146b72c316ebeed523fabecda625c0128e4accca76ba0f47ba63fb8ff1d6106c96120
data/README.md CHANGED
@@ -28,7 +28,7 @@ resque-scheduler files, but with additional features.
28
28
  ```ruby
29
29
  class CreateQueSchedulerSchema < ActiveRecord::Migration
30
30
  def change
31
- Que::Scheduler::Migrations.migrate!(version: 5)
31
+ Que::Scheduler::Migrations.migrate!(version: 6)
32
32
  end
33
33
  end
34
34
  ```
@@ -160,8 +160,11 @@ Additionally, there is the audit table `que_scheduler_audit_enqueued`. This logs
160
160
  the scheduler enqueues.
161
161
 
162
162
  When there is a major version (breaking) change, a migration should be run in. The version of the
163
- migration proceeds at a faster rate than the version of the gem. To run in all the migrations required
164
- up to a number, just migrate to that number with one line, and it will perform all the intermediary steps.
163
+ latest migration proceeds at a faster rate than the version of the gem, eg if the gem is on version
164
+ 3 then the migrations may be on version 6).
165
+
166
+ To run in all the migrations required up to a number, just migrate to that number with one line, and
167
+ it will perform all the intermediary steps.
165
168
 
166
169
  ie, This will perform all migrations necessary up to the latest version, skipping any already
167
170
  performed.
@@ -169,7 +172,7 @@ performed.
169
172
  ```ruby
170
173
  class CreateQueSchedulerSchema < ActiveRecord::Migration
171
174
  def change
172
- Que::Scheduler::Migrations.migrate!(version: 5)
175
+ Que::Scheduler::Migrations.migrate!(version: 6)
173
176
  end
174
177
  end
175
178
  ```
@@ -183,6 +186,7 @@ The changes in past migrations were:
183
186
  | 3 | Added the audit table `que_scheduler_audit_enqueued`. |
184
187
  | 4 | Updated the the audit tables to use bigints |
185
188
  | 5 | Dropped an unnecessary index |
189
+ | 6 | Enforced single scheduler job at the trigger level |
186
190
 
187
191
  ## Built in optional job for audit clear down
188
192
 
@@ -214,8 +218,8 @@ in a coherent state with the rest of your database.
214
218
  ## Concurrent scheduler detection
215
219
 
216
220
  No matter how many tasks you have defined in your schedule, you will only ever need one que-scheduler
217
- job enqueued. que-scheduler knows this, and it will check before performing any operations that
218
- there is only one of itself present.
221
+ job enqueued. que-scheduler knows this, and there are DB constraints in place to ensure there is
222
+ only ever exactly one scheduler job.
219
223
 
220
224
  It also follows que job design [best practices](https://github.com/chanks/que/blob/master/docs/writing_reliable_jobs.md),
221
225
  using ACID guarantees, to ensure that it will never run multiple times. If the scheduler crashes for any reason,
@@ -267,6 +271,10 @@ The scheduler will then continue to retry indefinitely.
267
271
  que-scheduler uses [semantic versioning](https://semver.org/), so major version changes will usually
268
272
  require additional actions to be taken upgrading from one major version to another.
269
273
 
274
+ ## Changelog
275
+
276
+ A full changelog can be found here: [CHANGELOG.md](https://github.com/hlascelles/que-scheduler/blob/master/CHANGELOG.md)
277
+
270
278
  ## System requirements
271
279
 
272
280
  Your [postgres](https://www.postgresql.org/) database must be at least version 9.4.0.
@@ -277,9 +285,9 @@ This gem was inspired by the makers of the excellent [Que](https://github.com/ch
277
285
 
278
286
  ## Contributors
279
287
 
288
+ * @bnauta
289
+ * @JackDanger
280
290
  * @jish
281
291
  * @joehorsnell
282
- * @bnauta
283
- * @papodaca
284
292
  * @krzyzak
285
- * @JackDanger
293
+ * @papodaca
@@ -0,0 +1,7 @@
1
+ DROP TRIGGER que_scheduler_prevent_job_deletion_trigger ON que_jobs;
2
+
3
+ DROP FUNCTION que_scheduler_prevent_job_deletion();
4
+
5
+ DROP FUNCTION que_scheduler_check_job_exists();
6
+
7
+ DROP INDEX que_scheduler_job_in_que_jobs_unique_index;
@@ -0,0 +1,26 @@
1
+ -- Ensure there is no more than one scheduler
2
+ CREATE UNIQUE INDEX que_scheduler_job_in_que_jobs_unique_index ON que_jobs(job_class)
3
+ WHERE job_class = 'Que::Scheduler::SchedulerJob';
4
+
5
+ -- Ensure there is at least one scheduler
6
+ CREATE OR REPLACE FUNCTION que_scheduler_check_job_exists() RETURNS bool AS $$
7
+ SELECT EXISTS(SELECT * FROM que_jobs WHERE job_class = 'Que::Scheduler::SchedulerJob');
8
+ $$ LANGUAGE SQL;
9
+
10
+ CREATE OR REPLACE FUNCTION que_scheduler_prevent_job_deletion() RETURNS TRIGGER AS
11
+ $BODY$
12
+ DECLARE
13
+ BEGIN
14
+ IF OLD.job_class = 'Que::Scheduler::SchedulerJob' THEN
15
+ IF NOT que_scheduler_check_job_exists() THEN
16
+ raise exception 'Deletion of que_scheduler job % prevented. Deleting the que_scheduler job is almost certainly a mistake.', OLD.job_id;
17
+ END IF;
18
+ END IF;
19
+ RETURN OLD;
20
+ END;
21
+ $BODY$
22
+ LANGUAGE 'plpgsql';
23
+
24
+ CREATE CONSTRAINT TRIGGER que_scheduler_prevent_job_deletion_trigger AFTER UPDATE OR DELETE ON que_jobs
25
+ DEFERRABLE INITIALLY DEFERRED
26
+ FOR EACH ROW EXECUTE PROCEDURE que_scheduler_prevent_job_deletion();
@@ -16,8 +16,8 @@ module Que
16
16
  class SchedulerJob < Que::Job
17
17
  SCHEDULER_FREQUENCY = 60
18
18
 
19
- Que::Scheduler::VersionSupport.set_priority(self, 0)
20
- Que::Scheduler::VersionSupport.apply_retry_semantics(self)
19
+ VersionSupport.set_priority(self, 0)
20
+ VersionSupport.apply_retry_semantics(self)
21
21
 
22
22
  def run(options = nil)
23
23
  Que::Scheduler::Db.transaction do
@@ -27,12 +27,13 @@ module Que
27
27
  logs = ["que-scheduler last ran at #{scheduler_job_args.last_run_time}."]
28
28
  result = EnqueueingCalculator.parse(Scheduler.schedule.values, scheduler_job_args)
29
29
  enqueued_jobs = enqueue_required_jobs(result, logs)
30
+ # Remove this job and schedule self again
31
+ destroy
30
32
  enqueue_self_again(
31
33
  scheduler_job_args, scheduler_job_args.as_time, result.job_dictionary, enqueued_jobs
32
34
  )
33
35
  # Only now we're sure nothing errored, log the results
34
36
  logs.each { |str| ::Que.log(event: "que-scheduler".to_sym, message: str) }
35
- destroy
36
37
  end
37
38
  end
38
39
 
@@ -59,7 +60,7 @@ module Que
59
60
 
60
61
  def enqueue_self_again(scheduler_job_args, last_full_execution, job_dictionary, enqueued_jobs)
61
62
  # Log last run...
62
- job_id = Que::Scheduler::VersionSupport.job_attributes(self).fetch(:job_id)
63
+ job_id = VersionSupport.job_attributes(self).fetch(:job_id)
63
64
  Audit.append(job_id, scheduler_job_args.as_time, enqueued_jobs)
64
65
 
65
66
  # And rerun...
@@ -72,7 +73,7 @@ module Que
72
73
  )
73
74
 
74
75
  # rubocop:disable Style/GuardClause This reads better as a conditional
75
- unless Que::Scheduler::VersionSupport.job_attributes(enqueued_job).fetch(:job_id)
76
+ unless enqueued_job && VersionSupport.job_attributes(enqueued_job).fetch(:job_id)
76
77
  raise "SchedulerJob could not self-schedule. Has `.enqueue` been monkey patched?"
77
78
  end
78
79
  # rubocop:enable Style/GuardClause
@@ -8,7 +8,6 @@ module Que
8
8
  class << self
9
9
  def check
10
10
  assert_db_migrated
11
- assert_one_scheduler_job
12
11
  end
13
12
 
14
13
  private
@@ -60,21 +59,6 @@ module Que
60
59
  synchronously. This will fail as que-scheduler needs the above tables to work.
61
60
  ERR
62
61
  end
63
-
64
- def assert_one_scheduler_job
65
- schedulers = Que::Scheduler::Db.count_schedulers
66
- return if schedulers == 1
67
-
68
- raise(<<-ERR)
69
- Only one #{Que::Scheduler::SchedulerJob.name} should be enqueued. #{schedulers} were found.
70
-
71
- que-scheduler works by running a self-enqueueing version of itself that determines which
72
- jobs should be enqueued based on the provided config. If two or more que-schedulers were
73
- to run at once, then duplicate jobs would occur.
74
-
75
- To resolve this problem, please remove any duplicate scheduler jobs from the que_jobs table.
76
- ERR
77
- end
78
62
  end
79
63
  end
80
64
  end
@@ -1,5 +1,5 @@
1
1
  module Que
2
2
  module Scheduler
3
- VERSION = "3.4.3".freeze
3
+ VERSION = "4.0.0".freeze
4
4
  end
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: que-scheduler
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.4.3
4
+ version: 4.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Harry Lascelles
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-10-28 00:00:00.000000000 Z
11
+ date: 2020-11-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -335,6 +335,8 @@ files:
335
335
  - lib/que/scheduler/migrations/4/up.sql
336
336
  - lib/que/scheduler/migrations/5/down.sql
337
337
  - lib/que/scheduler/migrations/5/up.sql
338
+ - lib/que/scheduler/migrations/6/down.sql
339
+ - lib/que/scheduler/migrations/6/up.sql
338
340
  - lib/que/scheduler/schedule.rb
339
341
  - lib/que/scheduler/scheduler_job.rb
340
342
  - lib/que/scheduler/scheduler_job_args.rb