activejob 7.0.10 → 7.1.0.beta1

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.
Files changed (42) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +105 -190
  3. data/MIT-LICENSE +1 -1
  4. data/README.md +2 -2
  5. data/lib/active_job/arguments.rb +14 -25
  6. data/lib/active_job/base.rb +1 -1
  7. data/lib/active_job/callbacks.rb +2 -6
  8. data/lib/active_job/configured_job.rb +4 -0
  9. data/lib/active_job/core.rb +3 -1
  10. data/lib/active_job/deprecator.rb +7 -0
  11. data/lib/active_job/enqueuing.rb +30 -0
  12. data/lib/active_job/exceptions.rb +30 -6
  13. data/lib/active_job/execution.rb +5 -1
  14. data/lib/active_job/gem_version.rb +4 -4
  15. data/lib/active_job/instrumentation.rb +18 -10
  16. data/lib/active_job/log_subscriber.rb +77 -7
  17. data/lib/active_job/queue_adapter.rb +13 -2
  18. data/lib/active_job/queue_adapters/async_adapter.rb +2 -2
  19. data/lib/active_job/queue_adapters/backburner_adapter.rb +7 -3
  20. data/lib/active_job/queue_adapters/delayed_job_adapter.rb +1 -1
  21. data/lib/active_job/queue_adapters/inline_adapter.rb +1 -1
  22. data/lib/active_job/queue_adapters/queue_classic_adapter.rb +4 -4
  23. data/lib/active_job/queue_adapters/resque_adapter.rb +1 -1
  24. data/lib/active_job/queue_adapters/sidekiq_adapter.rb +42 -14
  25. data/lib/active_job/queue_adapters/sneakers_adapter.rb +1 -1
  26. data/lib/active_job/queue_adapters/sucker_punch_adapter.rb +2 -2
  27. data/lib/active_job/queue_adapters/test_adapter.rb +2 -2
  28. data/lib/active_job/queue_adapters.rb +8 -7
  29. data/lib/active_job/queue_priority.rb +18 -1
  30. data/lib/active_job/railtie.rb +25 -6
  31. data/lib/active_job/serializers/big_decimal_serializer.rb +22 -0
  32. data/lib/active_job/serializers/duration_serializer.rb +4 -2
  33. data/lib/active_job/serializers/time_with_zone_serializer.rb +2 -11
  34. data/lib/active_job/serializers.rb +7 -3
  35. data/lib/active_job/test_helper.rb +32 -7
  36. data/lib/active_job/version.rb +1 -1
  37. data/lib/active_job.rb +26 -4
  38. data/lib/rails/generators/job/USAGE +19 -0
  39. data/lib/rails/generators/job/job_generator.rb +6 -2
  40. data/lib/rails/generators/job/templates/job.rb.tt +1 -1
  41. metadata +16 -11
  42. data/lib/active_job/queue_adapters/que_adapter.rb +0 -61
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: be497ec8b1f22b64d821aa595f4a62e69d92d4f04bb066f8eab468e96a148d9a
4
- data.tar.gz: 2a7b3b1d6e9246ebed53c5f853b65ec02da56f8d41bee74f8da8fb33887dbb02
3
+ metadata.gz: c483058510bace1163414149c1aff4177dd5dc026414417a99f240128686ccc6
4
+ data.tar.gz: 27f14766eafe75eb955ebae328ef1c154c3bd3aa42251403e6ced8a61f8dc3d1
5
5
  SHA512:
6
- metadata.gz: 14380a3a6c88fb7e1f3107decd71dc21c57fd242f058ada819da1825931986b404cb17ab185ea49b386a62b29cbed72a2020402e033588cab0ba216c33ead411
7
- data.tar.gz: e57990031c726247763c650f293daabaaa95c57c361ae2c5b43db1d6ffc65a457a168b84b07d840158a16c5de5416fa09a133a51cc9c5ef986676d618123f420
6
+ metadata.gz: eeb8e50e581068b1e9862917d02d99bc8988fc254475e4a70a4a7e231ccb61340dfa276be6d39d0f6ebd4f347a00019d3c3703c946549bb4788dcdd83b46ccc9
7
+ data.tar.gz: 23cb3701834db4e4b6ba5adbd77966a50bd0debf8aed7a75d9a83f04355895aad870baca894d6e32183757b9a4a7f62c79748a638f99928be4c497d633302cb5
data/CHANGELOG.md CHANGED
@@ -1,115 +1,164 @@
1
- ## Rails 7.0.10 (October 28, 2025) ##
1
+ ## Rails 7.1.0.beta1 (September 13, 2023) ##
2
2
 
3
- * No changes.
4
-
5
-
6
- ## Rails 7.0.9 (October 28, 2025) ##
7
-
8
- * Preserve the serialized timezone when deserializing `ActiveSupport::TimeWithZone` arguments.
9
-
10
- *Joshua Young*
11
-
12
-
13
- ## Rails 7.0.8.7 (December 10, 2024) ##
3
+ * Fix Active Job log message to correctly report a job failed to enqueue
4
+ when the adapter raises an `ActiveJob::EnqueueError`.
14
5
 
15
- * No changes.
6
+ *Ben Sheldon*
16
7
 
8
+ * Add `after_discard` method.
17
9
 
18
- ## Rails 7.0.8.6 (October 23, 2024) ##
10
+ This method lets job authors define a block which will be run when a job is about to be discarded. For example:
19
11
 
20
- * No changes.
12
+ ```ruby
13
+ class AfterDiscardJob < ActiveJob::Base
14
+ after_discard do |job, exception|
15
+ Rails.logger.info("#{job.class} raised an exception: #{exception}")
16
+ end
21
17
 
18
+ def perform
19
+ raise StandardError
20
+ end
21
+ end
22
+ ```
22
23
 
23
- ## Rails 7.0.8.5 (October 15, 2024) ##
24
+ The above job will run the block passed to `after_discard` after the job is discarded. The exception will
25
+ still be raised after the block has been run.
24
26
 
25
- * No changes.
27
+ *Rob Cardy*
26
28
 
29
+ * Fix deserialization of ActiveSupport::Duration
27
30
 
28
- ## Rails 7.0.8.4 (June 04, 2024) ##
31
+ Previously, a deserialized Duration would return an array from Duration#parts.
32
+ It will now return a hash just like a regular Duration.
29
33
 
30
- * No changes.
34
+ This also fixes an error when trying to add or subtract from a deserialized Duration
35
+ (eg `duration + 1.year`).
31
36
 
37
+ *Jonathan del Strother*
32
38
 
33
- ## Rails 7.0.8.3 (May 17, 2024) ##
39
+ * `perform_enqueued_jobs` is now compatible with all Active Job adapters
34
40
 
35
- * No changes.
41
+ This means that methods that depend on it, like Action Mailer's `assert_emails`,
42
+ will work correctly even if the test adapter is not used.
36
43
 
44
+ *Alex Ghiculescu*
37
45
 
38
- ## Rails 7.0.8.2 (May 16, 2024) ##
46
+ * Allow queue adapters to provide a custom name by implementing `queue_adapter_name`
39
47
 
40
- * No changes.
48
+ *Sander Verdonschot*
41
49
 
50
+ * Log background job enqueue callers
42
51
 
43
- ## Rails 7.0.8.1 (February 21, 2024) ##
52
+ Add `verbose_enqueue_logs` configuration option to display the caller
53
+ of background job enqueue in the log to help with debugging.
44
54
 
45
- * No changes.
55
+ Example log line:
46
56
 
57
+ ```
58
+ Enqueued AvatarThumbnailsJob (Job ID: ab528951-41fb-4c48-9129-3171791c27d6) to Sidekiq(default) with arguments: 1092412064
59
+ ↳ app/models/user.rb:421:in `generate_avatar_thumbnails'
60
+ ```
47
61
 
48
- ## Rails 7.0.8 (September 09, 2023) ##
62
+ Enabled in development only for new and upgraded applications. Not recommended for use
63
+ in the production environment since it relies on Ruby's `Kernel#caller` which is fairly slow.
49
64
 
50
- * Fix Active Job log message to correctly report a job failed to enqueue
51
- when the adapter raises an `ActiveJob::EnqueueError`.
65
+ *fatkodima*
52
66
 
53
- *Ben Sheldon*
67
+ * Set `provider_job_id` for Backburner jobs
54
68
 
69
+ *Cameron Matheson*
55
70
 
56
- ## Rails 7.0.7.2 (August 22, 2023) ##
71
+ * Add `perform_all_later` to enqueue multiple jobs at once
57
72
 
58
- * No changes.
73
+ This adds the ability to bulk enqueue jobs, without running callbacks, by
74
+ passing multiple jobs or an array of jobs. For example:
59
75
 
76
+ ```ruby
77
+ ActiveJob.perform_all_later(MyJob.new("hello", 42), MyJob.new("world", 0))
60
78
 
61
- ## Rails 7.0.7.1 (August 22, 2023) ##
79
+ user_jobs = User.pluck(:id).map { |id| UserJob.new(user_id: id) }
80
+ ActiveJob.perform_all_later(user_jobs)
81
+ ```
62
82
 
63
- * No changes.
83
+ This can greatly reduce the number of round-trips to the queue datastore.
84
+ For queue adapters that do not implement the new `enqueue_all` method, we
85
+ fall back to enqueuing jobs individually. The Sidekiq adapter implements
86
+ `enqueue_all` with `push_bulk`.
64
87
 
88
+ This method does not use the existing `enqueue.active_job` event, but adds a
89
+ new event `enqueue_all.active_job`.
65
90
 
66
- ## Rails 7.0.7 (August 09, 2023) ##
91
+ *Sander Verdonschot*
67
92
 
68
- * No changes.
93
+ * Don't double log the `job` when using `ActiveRecord::QueryLog`
69
94
 
95
+ Previously if you set `config.active_record.query_log_tags` to an array that included
96
+ `:job`, the job name would get logged twice. This bug has been fixed.
70
97
 
71
- ## Rails 7.0.6 (June 29, 2023) ##
98
+ *Alex Ghiculescu*
72
99
 
73
- * Fix error Active Job passed class with `permitted?`.
100
+ * Add support for Sidekiq's transaction-aware client
74
101
 
75
- *Alex Baldwin*
102
+ *Jonathan del Strother*
76
103
 
104
+ * Remove QueAdapter from Active Job.
77
105
 
78
- ## Rails 7.0.5.1 (June 26, 2023) ##
106
+ After maintaining Active Job QueAdapter by Rails and Que side
107
+ to support Ruby 3 keyword arguments and options provided as top level keywords,
108
+ it is quite difficult to maintain it this way.
79
109
 
80
- * No changes.
110
+ Active Job Que adapter can be included in the future version of que gem itself.
81
111
 
112
+ *Yasuo Honda*
82
113
 
83
- ## Rails 7.0.5 (May 24, 2023) ##
114
+ * Fix BigDecimal (de)serialization for adapters using JSON.
84
115
 
85
- * Make delayed job `display_name` failsafe.
116
+ Previously, BigDecimal was listed as not needing a serializer. However,
117
+ when used with an adapter storing the job arguments as JSON, it would get
118
+ serialized as a simple String, resulting in deserialization also producing
119
+ a String (instead of a BigDecimal).
86
120
 
87
- *codez*
121
+ By using a serializer, we ensure the round trip is safe.
88
122
 
89
- * Don't double log the `job` when using `ActiveRecord::QueryLog`
123
+ To ensure applications using BigDecimal job arguments are not subject to
124
+ race conditions during deployment (where a replica running a version of
125
+ Rails without BigDecimalSerializer fails to deserialize an argument
126
+ serialized with it), `ActiveJob.use_big_decimal_serializer` is disabled by
127
+ default, and can be set to true in a following deployment..
90
128
 
91
- Previously if you set `config.active_record.query_log_tags` to an array that included
92
- `:job`, the job name would get logged twice. This bug has been fixed.
129
+ *Sam Bostock*
93
130
 
94
- *Alex Ghiculescu*
131
+ * Preserve full-precision `enqueued_at` timestamps for serialized jobs,
132
+ allowing more accurate reporting of how long a job spent waiting in the
133
+ queue before it was performed.
95
134
 
135
+ Retains IS08601 format compatibility.
96
136
 
97
- ## Rails 7.0.4.3 (March 13, 2023) ##
137
+ *Jeremy Daer*
98
138
 
99
- * No changes.
139
+ * Add `--parent` option to job generator to specify parent class of job.
100
140
 
141
+ Example:
101
142
 
102
- ## Rails 7.0.4.2 (January 24, 2023) ##
143
+ `bin/rails g job process_payment --parent=payment_job` generates:
103
144
 
104
- * No changes.
145
+ ```ruby
146
+ class ProcessPaymentJob < PaymentJob
147
+ # ...
148
+ end
149
+ ```
105
150
 
151
+ *Gannon McGibbon*
106
152
 
107
- ## Rails 7.0.4.1 (January 17, 2023) ##
153
+ * Add more detailed description to job generator.
108
154
 
109
- * No changes.
155
+ *Gannon McGibbon*
110
156
 
157
+ * `perform.active_job` notification payloads now include `:db_runtime`, which
158
+ is the total time (in ms) taken by database queries while performing a job.
159
+ This value can be used to better understand how a job's time is spent.
111
160
 
112
- ## Rails 7.0.4 (September 09, 2022) ##
161
+ *Jonathan Hefner*
113
162
 
114
163
  * Update `ActiveJob::QueueAdapters::QueAdapter` to remove deprecation warning.
115
164
 
@@ -118,13 +167,6 @@
118
167
 
119
168
  *Damir Zekic* and *Adis Hasovic*
120
169
 
121
- ## Rails 7.0.3.1 (July 12, 2022) ##
122
-
123
- * No changes.
124
-
125
-
126
- ## Rails 7.0.3 (May 09, 2022) ##
127
-
128
170
  * Add missing `bigdecimal` require in `ActiveJob::Arguments`
129
171
 
130
172
  Could cause `uninitialized constant ActiveJob::Arguments::BigDecimal (NameError)`
@@ -132,40 +174,13 @@
132
174
 
133
175
  *Jean Boussier*
134
176
 
135
- ## Rails 7.0.2.4 (April 26, 2022) ##
136
-
137
- * No changes.
138
-
139
-
140
- ## Rails 7.0.2.3 (March 08, 2022) ##
141
-
142
- * No changes.
143
-
144
-
145
- ## Rails 7.0.2.2 (February 11, 2022) ##
146
-
147
- * No changes.
148
-
149
-
150
- ## Rails 7.0.2.1 (February 11, 2022) ##
151
-
152
- * No changes.
153
-
154
-
155
- ## Rails 7.0.2 (February 08, 2022) ##
156
-
157
- * No changes.
158
-
159
-
160
- ## Rails 7.0.1 (January 06, 2022) ##
161
-
162
177
  * Allow testing `discard_on/retry_on ActiveJob::DeserializationError`
163
178
 
164
179
  Previously in `perform_enqueued_jobs`, `deserialize_arguments_if_needed`
165
180
  was called before calling `perform_now`. When a record no longer exists
166
181
  and is serialized using GlobalID this led to raising
167
182
  an `ActiveJob::DeserializationError` before reaching `perform_now` call.
168
- This behaviour makes difficult testing the job `discard_on/retry_on` logic.
183
+ This behavior makes difficult testing the job `discard_on/retry_on` logic.
169
184
 
170
185
  Now `deserialize_arguments_if_needed` call is postponed to when `perform_now`
171
186
  is called.
@@ -190,104 +205,4 @@
190
205
 
191
206
  *Jacopo Beschi*
192
207
 
193
-
194
- ## Rails 7.0.0 (December 15, 2021) ##
195
-
196
- * No changes.
197
-
198
-
199
- ## Rails 7.0.0.rc3 (December 14, 2021) ##
200
-
201
- * No changes.
202
-
203
-
204
- ## Rails 7.0.0.rc2 (December 14, 2021) ##
205
-
206
- * No changes.
207
-
208
- ## Rails 7.0.0.rc1 (December 06, 2021) ##
209
-
210
- * Remove deprecated `:return_false_on_aborted_enqueue` option.
211
-
212
- *Rafael Mendonça França*
213
-
214
- * Deprecated `Rails.config.active_job.skip_after_callbacks_if_terminated`.
215
-
216
- *Rafael Mendonça França*
217
-
218
- * Removed deprecated behavior that was not halting `after_enqueue`/`after_perform` callbacks when a
219
- previous callback was halted with `throw :abort`.
220
-
221
- *Rafael Mendonça França*
222
-
223
- * Raise an `SerializationError` in `Serializer::ModuleSerializer`
224
- if the module name is not present.
225
-
226
- *Veerpal Brar*
227
-
228
-
229
- ## Rails 7.0.0.alpha2 (September 15, 2021) ##
230
-
231
- * No changes.
232
-
233
-
234
- ## Rails 7.0.0.alpha1 (September 15, 2021) ##
235
-
236
- * Allow a job to retry indefinitely
237
-
238
- The `attempts` parameter of the `retry_on` method now accepts the
239
- symbol reference `:unlimited` in addition to a specific number of retry
240
- attempts to allow a developer to specify that a job should retry
241
- forever until it succeeds.
242
-
243
- class MyJob < ActiveJob::Base
244
- retry_on(AlwaysRetryException, attempts: :unlimited)
245
-
246
- # the actual job code
247
- end
248
-
249
- *Daniel Morton*
250
-
251
- * Added possibility to check on `:priority` in test helper methods
252
- `assert_enqueued_with` and `assert_performed_with`.
253
-
254
- *Wojciech Wnętrzak*
255
-
256
- * OpenSSL constants are now used for Digest computations.
257
-
258
- *Dirkjan Bussink*
259
-
260
- * Add a Serializer for the Range class.
261
-
262
- This should allow things like `MyJob.perform_later(range: 1..100)`.
263
-
264
- * Communicate enqueue failures to callers of `perform_later`.
265
-
266
- `perform_later` can now optionally take a block which will execute after
267
- the adapter attempts to enqueue the job. The block will receive the job
268
- instance as an argument even if the enqueue was not successful.
269
- Additionally, `ActiveJob` adapters now have the ability to raise an
270
- `ActiveJob::EnqueueError` which will be caught and stored in the job
271
- instance so code attempting to enqueue jobs can inspect any raised
272
- `EnqueueError` using the block.
273
-
274
- MyJob.perform_later do |job|
275
- unless job.successfully_enqueued?
276
- if job.enqueue_error&.message == "Redis was unavailable"
277
- # invoke some code that will retry the job after a delay
278
- end
279
- end
280
- end
281
-
282
- *Daniel Morton*
283
-
284
- * Don't log rescuable exceptions defined with `rescue_from`.
285
-
286
- *Hu Hailin*
287
-
288
- * Allow `rescue_from` to rescue all exceptions.
289
-
290
- *Adrianna Chang*, *Étienne Barrié*
291
-
292
-
293
- Please check [6-1-stable](https://github.com/rails/rails/blob/6-1-stable/activejob/CHANGELOG.md) for previous changes.
208
+ Please check [7-0-stable](https://github.com/rails/rails/blob/7-0-stable/activejob/CHANGELOG.md) for previous changes.
data/MIT-LICENSE CHANGED
@@ -1,4 +1,4 @@
1
- Copyright (c) 2014-2022 David Heinemeier Hansson
1
+ Copyright (c) David Heinemeier Hansson
2
2
 
3
3
  Permission is hereby granted, free of charge, to any person obtaining
4
4
  a copy of this software and associated documentation files (the
data/README.md CHANGED
@@ -10,14 +10,14 @@ that makes it easy to turn any mailing into a job for running later. That's
10
10
  one of the most common jobs in a modern web application: sending emails outside
11
11
  the request-response cycle, so the user doesn't have to wait on it.
12
12
 
13
- The main point is to ensure that all Rails apps will have a job infrastructure
13
+ The main point is to ensure that all \Rails apps will have a job infrastructure
14
14
  in place, even if it's in the form of an "immediate runner". We can then have
15
15
  framework features and other gems build on top of that, without having to worry
16
16
  about API differences between Delayed Job and Resque. Picking your queuing
17
17
  backend becomes more of an operational concern, then. And you'll be able to
18
18
  switch between them without having to rewrite your jobs.
19
19
 
20
- You can read more about Active Job in the [Active Job Basics](https://edgeguides.rubyonrails.org/active_job_basics.html) guide.
20
+ You can read more about Active Job in the [Active Job Basics](https://guides.rubyonrails.org/active_job_basics.html) guide.
21
21
 
22
22
  ## Usage
23
23
 
@@ -47,7 +47,7 @@ module ActiveJob
47
47
 
48
48
  private
49
49
  # :nodoc:
50
- PERMITTED_TYPES = [ NilClass, String, Integer, Float, BigDecimal, TrueClass, FalseClass ]
50
+ PERMITTED_TYPES = [ NilClass, String, Integer, Float, TrueClass, FalseClass ]
51
51
  # :nodoc:
52
52
  GLOBALID_KEY = "_aj_globalid"
53
53
  # :nodoc:
@@ -70,28 +70,6 @@ module ActiveJob
70
70
  private_constant :PERMITTED_TYPES, :RESERVED_KEYS, :GLOBALID_KEY,
71
71
  :SYMBOL_KEYS_KEY, :RUBY2_KEYWORDS_KEY, :WITH_INDIFFERENT_ACCESS_KEY
72
72
 
73
- unless Hash.respond_to?(:ruby2_keywords_hash?) && Hash.respond_to?(:ruby2_keywords_hash)
74
- using Module.new {
75
- refine Hash do
76
- class << Hash
77
- def ruby2_keywords_hash?(hash)
78
- !new(*[hash]).default.equal?(hash)
79
- end
80
-
81
- def ruby2_keywords_hash(hash)
82
- _ruby2_keywords_hash(**hash)
83
- end
84
-
85
- private
86
- def _ruby2_keywords_hash(*args)
87
- args.last
88
- end
89
- ruby2_keywords(:_ruby2_keywords_hash)
90
- end
91
- end
92
- }
93
- end
94
-
95
73
  def serialize_argument(argument)
96
74
  case argument
97
75
  when *PERMITTED_TYPES
@@ -115,16 +93,27 @@ module ActiveJob
115
93
  when -> (arg) { arg.respond_to?(:permitted?) && arg.respond_to?(:to_h) }
116
94
  serialize_indifferent_hash(argument.to_h)
117
95
  else
96
+ if BigDecimal === argument && !ActiveJob.use_big_decimal_serializer
97
+ ActiveJob.deprecator.warn(<<~MSG)
98
+ Primitive serialization of BigDecimal job arguments is deprecated as it may serialize via .to_s using certain queue adapters.
99
+ Enable config.active_job.use_big_decimal_serializer to use BigDecimalSerializer instead, which will be mandatory in Rails 7.2.
100
+
101
+ Note that if you application has multiple replicas, you should only enable this setting after successfully deploying your app to Rails 7.1 first.
102
+ This will ensure that during your deployment all replicas are capable of deserializing arguments serialized with BigDecimalSerializer.
103
+ MSG
104
+ return argument
105
+ end
106
+
118
107
  Serializers.serialize(argument)
119
108
  end
120
109
  end
121
110
 
122
111
  def deserialize_argument(argument)
123
112
  case argument
124
- when String
125
- argument
126
113
  when *PERMITTED_TYPES
127
114
  argument
115
+ when BigDecimal # BigDecimal may have been legacy serialized; Remove in 7.2
116
+ argument
128
117
  when Array
129
118
  argument.map { |arg| deserialize_argument(arg) }
130
119
  when Hash
@@ -15,7 +15,7 @@ require "active_job/timezones"
15
15
  require "active_job/translation"
16
16
 
17
17
  module ActiveJob # :nodoc:
18
- # = Active Job
18
+ # = Active Job \Base
19
19
  #
20
20
  # Active Job objects can be configured to work with different backend
21
21
  # queuing frameworks. To specify a queue adapter to use:
@@ -4,7 +4,7 @@ require "active_support/callbacks"
4
4
  require "active_support/core_ext/module/attribute_accessors"
5
5
 
6
6
  module ActiveJob
7
- # = Active Job Callbacks
7
+ # = Active Job \Callbacks
8
8
  #
9
9
  # Active Job provides hooks during the life cycle of a job. Callbacks allow you
10
10
  # to trigger logic during this cycle. Available callbacks are:
@@ -28,9 +28,6 @@ module ActiveJob
28
28
  end
29
29
 
30
30
  included do
31
- cattr_accessor :skip_after_callbacks_if_terminated, instance_accessor: false, default: false
32
- singleton_class.deprecate :skip_after_callbacks_if_terminated, :skip_after_callbacks_if_terminated=
33
-
34
31
  define_callbacks :perform, skip_after_callbacks_if_terminated: true
35
32
  define_callbacks :enqueue, skip_after_callbacks_if_terminated: true
36
33
  end
@@ -135,8 +132,7 @@ module ActiveJob
135
132
  # queue_as :default
136
133
  #
137
134
  # after_enqueue do |job|
138
- # result = job.successfully_enqueued? ? "success" : "failure"
139
- # $statsd.increment "enqueue-video-job.#{result}"
135
+ # $statsd.increment "enqueue-video-job.success"
140
136
  # end
141
137
  #
142
138
  # def perform(video_id)
@@ -14,5 +14,9 @@ module ActiveJob
14
14
  def perform_later(...)
15
15
  @job_class.new(...).enqueue @options
16
16
  end
17
+
18
+ def perform_all_later(multi_args)
19
+ @job_class.perform_all_later(multi_args, options: @options)
20
+ end
17
21
  end
18
22
  end
@@ -1,6 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module ActiveJob
4
+ # = Active Job \Core
5
+ #
4
6
  # Provides general behavior that will be included into every Active Job
5
7
  # object that inherits from ActiveJob::Base.
6
8
  module Core
@@ -113,7 +115,7 @@ module ActiveJob
113
115
  "exception_executions" => exception_executions,
114
116
  "locale" => I18n.locale.to_s,
115
117
  "timezone" => timezone,
116
- "enqueued_at" => Time.now.utc.iso8601
118
+ "enqueued_at" => Time.now.utc.iso8601(9)
117
119
  }
118
120
  end
119
121
 
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveJob
4
+ def self.deprecator # :nodoc:
5
+ @deprecator ||= ActiveSupport::Deprecation.new
6
+ end
7
+ end
@@ -9,6 +9,36 @@ module ActiveJob
9
9
  # why the adapter was unexpectedly unable to enqueue a job.
10
10
  class EnqueueError < StandardError; end
11
11
 
12
+ class << self
13
+ # Push many jobs onto the queue at once without running enqueue callbacks.
14
+ # Queue adapters may communicate the enqueue status of each job by setting
15
+ # successfully_enqueued and/or enqueue_error on the passed-in job instances.
16
+ def perform_all_later(*jobs)
17
+ jobs.flatten!
18
+ jobs.group_by(&:queue_adapter).each do |queue_adapter, adapter_jobs|
19
+ instrument_enqueue_all(queue_adapter, adapter_jobs) do
20
+ if queue_adapter.respond_to?(:enqueue_all)
21
+ queue_adapter.enqueue_all(adapter_jobs)
22
+ else
23
+ adapter_jobs.each do |job|
24
+ job.successfully_enqueued = false
25
+ if job.scheduled_at
26
+ queue_adapter.enqueue_at(job, job.scheduled_at)
27
+ else
28
+ queue_adapter.enqueue(job)
29
+ end
30
+ job.successfully_enqueued = true
31
+ rescue EnqueueError => e
32
+ job.enqueue_error = e
33
+ end
34
+ adapter_jobs.count(&:successfully_enqueued?)
35
+ end
36
+ end
37
+ end
38
+ nil
39
+ end
40
+ end
41
+
12
42
  module Enqueuing
13
43
  extend ActiveSupport::Concern
14
44
 
@@ -9,6 +9,7 @@ module ActiveJob
9
9
 
10
10
  included do
11
11
  class_attribute :retry_jitter, instance_accessor: false, instance_predicate: false, default: 0.0
12
+ class_attribute :after_discard_procs, default: []
12
13
  end
13
14
 
14
15
  module ClassMethods
@@ -20,9 +21,6 @@ module ActiveJob
20
21
  # You can also pass a block that'll be invoked if the retry attempts fail for custom logic rather than letting
21
22
  # the exception bubble up. This block is yielded with the job instance as the first and the error instance as the second parameter.
22
23
  #
23
- # `retry_on` and `discard_on` handlers are searched from bottom to top, and up the class hierarchy. The handler of the first class for
24
- # which <tt>exception.is_a?(klass)</tt> holds true is the one invoked, if any.
25
- #
26
24
  # ==== Options
27
25
  # * <tt>:wait</tt> - Re-enqueues the job with a delay specified either in seconds (default: 3 seconds),
28
26
  # as a computing proc that takes the number of executions so far as an argument, or as a symbol reference of
@@ -68,8 +66,10 @@ module ActiveJob
68
66
  instrument :retry_stopped, error: error do
69
67
  yield self, error
70
68
  end
69
+ run_after_discard_procs(error)
71
70
  else
72
71
  instrument :retry_stopped, error: error
72
+ run_after_discard_procs(error)
73
73
  raise error
74
74
  end
75
75
  end
@@ -81,9 +81,6 @@ module ActiveJob
81
81
  #
82
82
  # You can also pass a block that'll be invoked. This block is yielded with the job instance as the first and the error instance as the second parameter.
83
83
  #
84
- # `retry_on` and `discard_on` handlers are searched from bottom to top, and up the class hierarchy. The handler of the first class for
85
- # which <tt>exception.is_a?(klass)</tt> holds true is the one invoked, if any.
86
- #
87
84
  # ==== Example
88
85
  #
89
86
  # class SearchIndexingJob < ActiveJob::Base
@@ -101,9 +98,26 @@ module ActiveJob
101
98
  rescue_from(*exceptions) do |error|
102
99
  instrument :discard, error: error do
103
100
  yield self, error if block_given?
101
+ run_after_discard_procs(error)
104
102
  end
105
103
  end
106
104
  end
105
+
106
+ # A block to run when a job is about to be discarded for any reason.
107
+ #
108
+ # ==== Example
109
+ #
110
+ # class WorkJob < ActiveJob::Base
111
+ # after_discard do |job, exception|
112
+ # ExceptionNotifier.report(exception)
113
+ # end
114
+ #
115
+ # ...
116
+ #
117
+ # end
118
+ def after_discard(&blk)
119
+ self.after_discard_procs += [blk]
120
+ end
107
121
  end
108
122
 
109
123
  # Reschedules the job to be re-executed. This is useful in combination with
@@ -171,5 +185,15 @@ module ActiveJob
171
185
  executions
172
186
  end
173
187
  end
188
+
189
+ def run_after_discard_procs(exception)
190
+ exceptions = []
191
+ after_discard_procs.each do |blk|
192
+ instance_exec(self, exception, &blk)
193
+ rescue StandardError => e
194
+ exceptions << e
195
+ end
196
+ raise exceptions.last unless exceptions.empty?
197
+ end
174
198
  end
175
199
  end