How to assert a Laravel job is delayed

I've seen a lot of convoluted approaches to this, here's a drop-dead simple way to do it.

Joel Clermont
Joel Clermont
2023-11-01

Tests should give us confidence that our code works as expected. So when we dispatch a job with a delay, it's important to cover that in our tests.

Laravel provides some ways of manipulating time in our tests, but none of those techniques are actually necessary in this case. Instead, we can assert the Job class has the delay property set as expected:

Bus::fake();

ConversationEvent::factory()->create(); // when created, this model dispatches a job with a delay

Bus::assertDispatchedTimes(AddMessageToConversation::class, 1);

Bus::assertDispatched(AddMessageToConversation::class, function (AddMessageToConversation $job) {
    self::assertEquals('some-value-here', $job->someProperty);
    // other property assertions here...
    self::assertEquals(60, $job->delay); // This asserts the job will be delayed 60 seconds
});

Laravel already has its own tests to make sure it processes the delays properly. There's no need to cover that in your feature tests as well.

Here to help,

Joel

P.S. Do you wish you had more tests in your app? We can help you become more confident with a solid testing strategy.

Toss a coin in the jar if you found this helpful.
Want a tip like this in your inbox every weekday? Sign up below 👇🏼

Level up your Laravel skills!

Each 2-minute email has real-world advice you can use.