Make AJ::Base#enqueue return false if the job wasn't enqueued

This commit is contained in:
Kir Shatrov 2018-09-26 17:25:20 +01:00
parent 3295e23755
commit ee9fc12024
5 changed files with 56 additions and 1 deletions

View File

@ -29,6 +29,9 @@ module ActiveJob
included do
define_callbacks :perform
define_callbacks :enqueue
class_attribute :return_false_on_aborted_enqueue, instance_accessor: false, instance_predicate: false
self.return_false_on_aborted_enqueue = false
end
# These methods will be included into any Active Job object, adding

View File

@ -46,14 +46,25 @@ module ActiveJob
self.scheduled_at = options[:wait_until].to_f if options[:wait_until]
self.queue_name = self.class.queue_name_from_part(options[:queue]) if options[:queue]
self.priority = options[:priority].to_i if options[:priority]
successfully_enqueued = false
run_callbacks :enqueue do
if scheduled_at
self.class.queue_adapter.enqueue_at self, scheduled_at
else
self.class.queue_adapter.enqueue self
end
successfully_enqueued = true
end
if successfully_enqueued
self
else
if self.class.return_false_on_aborted_enqueue
false
else
ActiveSupport::Deprecation.warn "this will return false, set config.active_job.return_false_on_aborted_enqueue = true to remove deprecation."
self
end
end
self
end
end
end

View File

@ -2,6 +2,7 @@
require "helper"
require "jobs/callback_job"
require "jobs/abort_before_enqueue_job"
require "active_support/core_ext/object/inclusion"
@ -22,4 +23,32 @@ class CallbacksTest < ActiveSupport::TestCase
assert "CallbackJob ran around_enqueue_start".in? enqueued_callback_job.history
assert "CallbackJob ran around_enqueue_stop".in? enqueued_callback_job.history
end
test "#enqueue returns false when before_enqueue aborts callback chain and return_false_on_aborted_enqueue = true" do
begin
prev = ActiveJob::Base.return_false_on_aborted_enqueue
ActiveJob::Base.return_false_on_aborted_enqueue = true
assert_equal false, AbortBeforeEnqueueJob.new.enqueue
ensure
ActiveJob::Base.return_false_on_aborted_enqueue = prev
end
end
test "#enqueue returns self when before_enqueue aborts callback chain and return_false_on_aborted_enqueue = false" do
begin
prev = ActiveJob::Base.return_false_on_aborted_enqueue
ActiveJob::Base.return_false_on_aborted_enqueue = false
job = AbortBeforeEnqueueJob.new
assert_deprecated do
assert_equal job, job.enqueue
end
ensure
ActiveJob::Base.return_false_on_aborted_enqueue = prev
end
end
test "#enqueue returns self when the job was enqueued" do
job = CallbackJob.new
assert_equal job, job.enqueue
end
end

View File

@ -0,0 +1,9 @@
# frozen_string_literal: true
class AbortBeforeEnqueueJob < ActiveJob::Base
before_enqueue { throw(:abort) }
def perform
raise "This should never be called"
end
end

View File

@ -15,3 +15,6 @@
# This option is not backwards compatible with earlier Rails versions.
# It's best enabled when your entire app is migrated and stable on 6.0.
# Rails.application.config.action_dispatch.use_cookies_with_metadata = true
# Return false instead of self when #enqueue method was aborted from the callback
Rails.application.config.active_job.return_false_on_aborted_enqueue = true