diff --git a/lib/delayed/job.rb b/lib/delayed/job.rb index c5ceab030..a8472d632 100644 --- a/lib/delayed/job.rb +++ b/lib/delayed/job.rb @@ -70,12 +70,12 @@ def reschedule(message, backtrace = [], time = nil) end end - def self.enqueue(object, priority = 0) + def self.enqueue(object, priority = 0, run_at = nil) unless object.respond_to?(:perform) raise ArgumentError, 'Cannot enqueue items which do not respond to perform' end - Job.create(:payload_object => object, :priority => priority.to_i) + Job.create(:payload_object => object, :priority => priority.to_i, :run_at => run_at) end def self.find_available(limit = 5, max_run_time = MAX_RUN_TIME) diff --git a/spec/job_spec.rb b/spec/job_spec.rb index 990640962..6f8ca6814 100644 --- a/spec/job_spec.rb +++ b/spec/job_spec.rb @@ -22,10 +22,15 @@ def perform; raise 'did not work'; end SimpleJob.runs = 0 end - it "should set run_at automatically" do + it "should set run_at automatically if not set" do Delayed::Job.create(:payload_object => ErrorJob.new ).run_at.should_not == nil end + it "should not set run_at automatically if already set" do + later = 5.minutes.from_now + Delayed::Job.create(:payload_object => ErrorJob.new, :run_at => later).run_at.should == later + end + it "should raise ArgumentError when handler doesn't respond_to :perform" do lambda { Delayed::Job.enqueue(Object.new) }.should raise_error(ArgumentError) end @@ -35,6 +40,19 @@ def perform; raise 'did not work'; end Delayed::Job.count.should == 1 end + it "should be able to set priority when enqueuing items" do + Delayed::Job.enqueue SimpleJob.new, 5 + Delayed::Job.first.priority.should == 5 + end + + it "should be able to set run_at when enqueuing items" do + later = 5.minutes.from_now + Delayed::Job.enqueue SimpleJob.new, 5, later + + # use be close rather than equal to because millisecond values cn be lost in DB round trip + Delayed::Job.first.run_at.should be_close(later, 1) + end + it "should call perform on jobs when running work_off" do SimpleJob.runs.should == 0 @@ -98,7 +116,7 @@ def perform; raise 'did not work'; end job.should_receive(:attempt_to_load).with('Delayed::JobThatDoesNotExist').and_return(true) lambda { job.payload_object.perform }.should raise_error(Delayed::DeserializationError) end - + it "should be failed if it failed more than MAX_ATTEMPTS times and we don't want to destroy jobs" do default = Delayed::Job.destroy_failed_jobs Delayed::Job.destroy_failed_jobs = false @@ -164,7 +182,6 @@ def perform; raise 'did not work'; end Delayed::Job.find_available(1, 4.minutes).length.should == 1 end - it "should be able to get exclusive access again when the worker name is the same" do @job.lock_exclusively! 5.minutes, 'worker1' @job.lock_exclusively! 5.minutes, 'worker1' @@ -241,4 +258,4 @@ def perform; raise 'did not work'; end end -end \ No newline at end of file +end