Giúp em về Cron job Task Scheduler trong laravel với các anh :(((
Chào anh em trong group ạ.
Em đang build 1 app get api từ website khác về.
Còn bị vướng 1 chức năng nữa là có thể tự động chạy mỗi 1 ngày, 3 ngày, 1 tuần,..... cho mỗi project khác nhau.
Em có tìm hiểu và có keyword là Cron job, Task Scheduler nhưng không áp dụng được.
Anh em giúp em với ạ. Em viết trên laravel 9. Cảm ơn anh em !!!!
1 CÂU TRẢ LỜI
Bạn sử dụng Task Scheduler của Laravel là đúng rồi nhé. Kết hợp dùng Task Scheduler + Artisan Command sẽ là sự lựa chọn tuyệt vời. Cách thức thực hiện thì sẽ làm như sau:
- Tạo một Artisan Command theo hướng dẫn: https://laravel.com/docs/9.x/artisan VD: SendDailyReport
- Viết code logic của bạn vào trong method
handle
trong command - Cấu hình Task Scheduler để Laravel tự động chạy command trên theo hướng dẫn: https://laravel.com/docs/9.x/scheduling#scheduling-artisan-commands
- Cấu hình Crontab trên server để server tự động chạy Task Scheduler của Laravel
Bạn làm theo các hướng dẫn của mình bên trên là được.
Nếu trong quá trình thực hiện bạn gặp lỗi nào khác thì cứ search Google hoặc tạo câu hỏi kèm theo log lỗi để được ae Viblo hỗ trợ nhé.
@huukimit Cảm ơn bạn nhé. Nhưng mình vẫn còn 1 vấn đề. Mình muốn cho người dùng nhập vào cách bao lâu sẽ update dữ liệu (tạo 1 form có nút select). Có cách nào truyền biến số lượng này từ Controller vào method handle không nhỉ?
@datntclickmediaseo Với chức năng dynamic schedule này thì bạn lưu lại lịch vào database. Kiểu schedule_tasks (id, started_at, period, status, và một số thông tin khác).
id = 1, started_at = 2022-12-22 14:35:20, period = "1 hours", status = "pending", subject_id = 1, ...
id = 2, started_at = 2022-12-22 14:36:20, period = "1 hours", status = "pending", subject_id = 2, ...
id = 3, started_at = 2022-12-22 14:37:20, period = "1 hours", status = "pending", subject_id = 3, ...
Bây giờ muốn dynamic schedule task như yêu cầu thì trong Kernel bạn phải đọc từ database ra và có thể init từng task một. Kiểu như này:
<?php
namespace App\Console;
use Illuminate\Console\Scheduling\Schedule;
use Illuminate\Foundation\Console\Kernel as ConsoleKernel;
use Illuminate\Support\Facades\DB;
class Kernel extends ConsoleKernel
{
/**
* Define the application's command schedule.
*
* @param \Illuminate\Console\Scheduling\Schedule $schedule
* @return void
*/
protected function schedule(Schedule $schedule)
{
ScheduleTask::where(...)->where('status', 'pending')->chunk(100, function ($scheduleTasks) use ($schedule) {
$scheduleTasks->each(function ($task) use ($schedule) {
$schedule->job(new AutoUpdateForTask($task))->cron(convertToCron($task->period));
});
});
// .....
}
}
@huukimit cảm ơn bạn đã nhiệt tình hỗ trợ nhé. Chưa hiểu lắm nhưng mình sẽ tìm hiểu.