Get an array of scheduled tasks

19.1k Views Asked by At

Using the Laravel task scheduler I have created a number of tasks in app/Console/Kernel.php

e.g:

$schedule->command('some:command')
    ->daily();

$schedule->command('another:command')
    ->daily();

I would like to display the list of scheduled commands, their frequency, and last/next run time on a dashboard but I'm not sure how I can get the list of scheduled events. Is there a way to do this?

4

There are 4 best solutions below

3
On BEST ANSWER

There's actually no support out of the box for this, unfortunately. What you'll have to do is extend the artisan schedule command and add a list feature. Thankfully there's a simple class you can run:

<?php

namespace App\Console\Commands;

use Illuminate\Console\Command;
use Illuminate\Console\Scheduling\Schedule;

class ScheduleList extends Command
{
    protected $signature = 'schedule:list';
    protected $description = 'List when scheduled commands are executed.';

    /**
     * @var Schedule
     */
    protected $schedule;

    /**
     * ScheduleList constructor.
     *
     * @param Schedule $schedule
     */
    public function __construct(Schedule $schedule)
    {
        parent::__construct();

        $this->schedule = $schedule;
    }

    /**
     * Execute the console command.
     *
     * @return mixed
     */
    public function handle()
    {
        $events = array_map(function ($event) {
            return [
                'cron' => $event->expression,
                'command' => static::fixupCommand($event->command),
            ];
        }, $this->schedule->events());

        $this->table(
            ['Cron', 'Command'],
            $events
        );
    }

    /**
     * If it's an artisan command, strip off the PHP
     *
     * @param $command
     * @return string
     */
    protected static function fixupCommand($command)
    {
        $parts = explode(' ', $command);
        if (count($parts) > 2 && $parts[1] === "'artisan'") {
            array_shift($parts);
        }

        return implode(' ', $parts);
    }
}

This will provide you with a php artisan schedule:list. Now that's not exactly what you need, but then you can easily get this list from within your Laravel stack by executing:

Artisan::call('schedule:list');

And that will provide you with a list of the schedule commands.

Of course, don't forget to inject the Facade: use Illuminate\Support\Facades\Artisan;

7
On

You can use dependency injection in your controller method to get access to the needed objects.

<?php
namespace App\Http\Controllers;

use Illuminate\Console\Scheduling\Schedule;
use Illuminate\Contracts\Console\Kernel;

class MyController extends Controller {
    public function index(Kernel $kernel, Schedule $schedule)
    {
        dd($schedule->events());
    }
}

Note the Kernel instance is not used, but is required to be passed.

1
On

In Laravel Framework 8.22.1 I got to work by making app/Console/Kernel->schedule method public and then in a Controller:

use Illuminate\Console\Scheduling\Schedule;
use Illuminate\Events\Dispatcher;

    private function getScheduledJobs()
    {
        new \App\Console\Kernel(app(), new Dispatcher());
        $schedule = app(Schedule::class);
        $scheduledCommands = collect($schedule->events());

        return $scheduledCommands;
    }
0
On

I was having the task to stop/enable and edit the frequency of the scheduled tasks from the admin dashboard. So I foreach them in Kernel.php and capture the output in function.

$enabled_commands = ConsoleCommand::where('is_enabled', 1)
        ->get();

    foreach ($enabled_commands as $command)
    {
        $schedule->command($command->command_name)
            ->{$command->frequency}($command->time)
            ->after(function () use ($command) {
                $this->log($command->command_name);
            });
    }

Hope this help you.