- Inledning
- Definiering av scheman
- Schemaläggning av Artisan-kommandon
- Schemaläggning av köade jobb
- Schemaläggning av Shell-kommandon
- Optioner för schemaläggning av frekvenser
- Tidzoner
- Förhindra att uppgifter överlappar varandra
- Körning av uppgifter på en server
- Bakgrundsuppgifter
- Underhållsläge
- Körning av schemaläggaren
- Körning av schemaläggaren lokalt
- Utmatning av uppgifter
- Task Hooks
- Inledning
- Definiera schemaläggning
- Schemaläggning av Artisan-kommandon
- Skemaläggning av köade jobb
- Scheduling Shell Commands
- Schedule Frequency Options
- Day Constraints
- Between Time Constraints
- Truth Test Constraints
- Miljöbegränsningar
- Timezones
- Förhindra överlappning av uppgifter
- Körning av uppgifter på en server
- Bakgrundsuppgifter
- Underhållsläge
- Körning av schemaläggaren
- Körning av schemaläggaren lokalt
- Task Output
- Task Hooks
- Ping URL:er
Inledning
Förut, kan du ha skrivit en cron-konfigurationspost för varje uppgift som du behövde schemalägga på din server. Detta kan dock snabbt bli besvärligt eftersom ditt uppgiftsschema inte längre finns i källkontrollen och du måste SSH:a in på din server för att visa dina befintliga cronposter eller lägga till ytterligare poster.
Laravels kommandoschemaläggare erbjuder ett nytt tillvägagångssätt för att hantera schemalagda uppgifter på din server. Schemaläggaren gör det möjligt för dig att flytande och uttrycksfullt definiera ditt kommandoschema i din Laravel-applikation själv. När du använder schemaläggaren behövs endast en enda cron-post på din server. Ditt uppgiftsschema definieras i app/Console/Kernel.php
-filens schedule
-metod. För att hjälpa dig komma igång definieras ett enkelt exempel i metoden.
Definiera schemaläggning
Du kan definiera alla dina schemalagda uppgifter i schedule
-metoden i din applikations App\Console\Kernel
-klass App\Console\Kernel
. För att komma igång tar vi en titt på ett exempel. I det här exemplet schemalägger vi en stängning som ska anropas varje dag vid midnatt. Inom stängningen kommer vi att utföra en databasfråga för att rensa en tabell:
<?phpnamespace App\Console;use Illuminate\Console\Scheduling\Schedule;use Illuminate\Foundation\Console\Kernel as ConsoleKernel;use Illuminate\Support\Facades\DB;class Kernel extends ConsoleKernel{ /** * The Artisan commands provided by your application. * * @var array */ protected $commands = ; /** * Define the application's command schedule. * * @param \Illuminate\Console\Scheduling\Schedule $schedule * @return void */ protected function schedule(Schedule $schedule) { $schedule->call(function () { DB::table('recent_users')->delete(); })->daily(); }}
Inom schemaläggning med hjälp av stängningar kan du också schemalägga anropsbara objekt. Invokabla objekt är enkla PHP-klasser som innehåller en __invoke
metod:
$schedule->call(new DeleteRecentUsers)->daily();
Om du vill visa en översikt över dina schemalagda uppgifter och när de ska köras nästa gång kan du använda kommandot schedule:list
Artisan:
php artisan schedule:list
Schemaläggning av Artisan-kommandon
Förutom schemaläggning av closures kan du också schemalägga Artisan-kommandon och systemkommandon. Du kan till exempel använda metoden command
för att schemalägga ett Artisan-kommando med hjälp av antingen kommandots namn eller klass.
När du schemalägger Artisan-kommandon med hjälp av kommandots klassnamn kan du skicka en matris med ytterligare kommandoradsargument som ska tillhandahållas till kommandot när det anropas:
use App\Console\Commands\SendEmailsCommand;$schedule->command('emails:send Taylor --force')->daily();$schedule->command(SendEmailsCommand::class, )->daily();
Skemaläggning av köade jobb
Metoden job
kan användas för att schemalägga ett köat jobb. Denna metod ger ett bekvämt sätt att schemalägga köade jobb utan att använda call
-metoden för att definiera stängningar för att ställa jobbet i kö:
use App\Jobs\Heartbeat;$schedule->job(new Heartbeat)->everyFiveMinutes();
Optionella andra och tredje argument kan tillhandahållas till job
-metoden som anger det könamn och den köanslutning som ska användas för att ställa jobbet i kö:
use App\Jobs\Heartbeat;// Dispatch the job to the "heartbeats" queue on the "sqs" connection...$schedule->job(new Heartbeat, 'heartbeats', 'sqs')->everyFiveMinutes();
Scheduling Shell Commands
Metoden exec
kan användas för att utfärda ett kommando till operativsystemet:
$schedule->exec('node /home/forge/script.js')->daily();
Schedule Frequency Options
Vi har redan sett några exempel på hur du kan konfigurera en uppgift så att den ska köras med bestämda intervaller. Det finns dock många fler uppgiftsschemafrekvenser som du kan tilldela en uppgift:
Metod | Beskrivning |
---|---|
->cron('* * * * *'); |
Kör uppgiften på ett anpassat cronschema |
->everyMinute(); |
Kör uppgiften varje minut |
->everyTwoMinutes(); |
Kör uppgiften varannan minut |
->everyThreeMinutes(); |
Kör uppgiften var tredje minut |
->everyFourMinutes(); |
Kör uppgiften var fjärde minut |
->everyFiveMinutes(); |
Kör uppgiften. var femte minut |
->everyTenMinutes(); |
Kör uppgiften var tionde minut |
->everyFifteenMinutes(); |
Kör uppgiften var femtonde minut |
->everyThirtyMinutes(); |
Kör uppgiften var trettionde minut |
->hourly(); |
Kör uppgiften varje timme |
->hourlyAt(17); |
Kör uppgiften varje timme klockan 17 minuter över timmen |
->everyTwoHours(); |
Kör uppgiften varannan timme |
->everyThreeHours(); |
Kör uppgiften var tredje timme |
->everyFourHours(); |
Kör uppgiften var fjärde timme |
->everySixHours(); |
Kör uppgiften. var sjätte timme |
->daily(); |
Kör uppgiften varje dag vid midnatt |
->dailyAt('13:00'); |
Kör uppgiften varje dag klockan 13:00 |
->twiceDaily(1, 13); |
Kör uppgiften varje dag klockan 1:00 & 13:00 |
->weekly(); |
Kör uppgiften varje söndag klockan 00:00 |
->weeklyOn(1, '8:00'); |
Kör uppgiften varje vecka på måndag klockan 8:00 |
->monthly(); |
Kör uppgiften den första dagen i varje månad klockan 00:00 |
->monthlyOn(4, '15:00'); |
Kör uppgiften varje månad den 4:e klockan 15:00 |
->twiceMonthly(1, 16, '13:00'); |
Kör uppgiften månadsvis den 1:a och 16:e klockan 13:00 |
->lastDayOfMonth('15:00'); |
Kör uppgiften den sista dagen i månaden klockan 15:00 |
->quarterly(); |
Kör uppgiften den första dagen i varje kvartal klockan 00:00 |
->yearly(); |
Kör uppgiften den första dagen i varje år klockan 00:00 |
->yearlyOn(6, 1, '17:00'); |
Kör uppgiften varje år den 1 juni klockan 17:00 |
->timezone('America/New_York'); |
Inställ tidszon för uppgiften |
Dessa metoder kan kombineras med ytterligare begränsningar för att skapa ännu mer finjusterade scheman som endast körs vissa dagar i veckan. Du kan till exempel schemalägga ett kommando så att det körs varje vecka på måndag:
// Run once per week on Monday at 1 PM...$schedule->call(function () { //})->weekly()->mondays()->at('13:00');// Run hourly from 8 AM to 5 PM on weekdays...$schedule->command('foo') ->weekdays() ->hourly() ->timezone('America/Chicago') ->between('8:00', '17:00');
En lista över ytterligare schemabegränsningar finns nedan:
Metod | Beskrivning |
---|---|
->weekdays(); |
Begränsar uppgiften till vardagar |
->weekends(); |
Begränsar uppgiften till helger |
->sundays(); |
Begränsar uppgiften till söndagar |
->mondays(); |
Begränsar uppgiften till måndag |
->tuesdays(); |
Begränsar uppgiften till tisdag |
->wednesdays(); |
Begränsar uppgiften. till onsdag |
->thursdays(); |
Begränsar uppgiften till torsdag |
->fridays(); |
Begränsar uppgiften till fredag |
->saturdays(); |
Begränsar uppgiften till lördag |
->days(array|mixed); |
Begränsar uppgiften till vissa dagar |
->between($startTime, $endTime); |
Begränsar att aktiviteten ska köras mellan start- och sluttider |
->unlessBetween($startTime, $endTime); |
Begränsar att aktiviteten inte ska köras mellan start- och sluttider |
->unlessBetween($startTime, $endTime); |
Begränsar att aktiviteten inte ska köras mellan start- och sluttider. sluttider |
->when(Closure); |
Begränsar uppgiften baserat på ett sanningstest |
->environments($env); |
Begränsar uppgiften till specifika miljöer |
Day Constraints
Metoden days
kan användas för att begränsa utförandet av en uppgift till vissa dagar i veckan. Du kan till exempel schemalägga ett kommando så att det körs varje timme på söndagar och onsdagar:
$schedule->command('emails:send') ->hourly() ->days();
Alternativt kan du använda de konstanter som finns tillgängliga i klassen Illuminate\Console\Scheduling\Schedule
när du definierar vilka dagar en uppgift ska köras:
use Illuminate\Console\Scheduling\Schedule;$schedule->command('emails:send') ->hourly() ->days();
Between Time Constraints
Metoden between
kan användas för att begränsa utförandet av en uppgift baserat på tid på dagen:
På samma sätt kan unlessBetween
-metoden användas för att utesluta utförandet av en uppgift under en viss tidsperiod:
$schedule->command('emails:send') ->hourly() ->unlessBetween('23:00', '4:00');
Truth Test Constraints
Med when
-metoden kan when
användas för att begränsa utförandet av en uppgift baserat på resultatet av ett visst truth test. Med andra ord, om den givna stängningen ger true
kommer uppgiften att utföras så länge inga andra begränsande villkor hindrar uppgiften från att köras:
$schedule->command('emails:send')->daily()->when(function () { return true;});
Metoden skip
kan ses som en motsats till when
. Om skip
-metoden returnerar true
kommer den schemalagda uppgiften inte att exekveras:
$schedule->command('emails:send')->daily()->skip(function () { return true;});
När man använder kedjade when
-metoder kommer det schemalagda kommandot endast att exekveras om alla when
-villkor returnerar true
.
Miljöbegränsningar
Metoden environments
kan användas för att exekvera uppgifter endast i de givna miljöerna (enligt definitionen i miljövariabeln APP_ENV
):
$schedule->command('emails:send') ->daily() ->environments();
Timezones
Med hjälp av timezone
-metoden kan du ange att en schemalagd uppgifts tid ska tolkas inom en viss tidszon:
$schedule->command('report:generate') ->timezone('America/New_York') ->at('2:00')
Om du upprepade gånger tilldelar samma tidszon till alla dina schemalagda uppgifter kan du definiera en scheduleTimezone
-metod i din App\Console\Kernel
-klass. Denna metod bör återge den standardtidszon som ska tilldelas alla schemalagda uppgifter:
/** * Get the timezone that should be used by default for scheduled events. * * @return \DateTimeZone|string|null */protected function scheduleTimezone(){ return 'America/Chicago';}
{note} Kom ihåg att vissa tidszoner använder sig av sommartid. När sommartid ändras kan det hända att din schemalagda aktivitet körs två gånger eller inte alls. Därför rekommenderar vi att du undviker schemaläggning i tidszoner när det är möjligt.
Förhindra överlappning av uppgifter
Som standard körs schemalagda uppgifter även om den tidigare instansen av uppgiften fortfarande körs. För att förhindra detta kan du använda metoden withoutOverlapping
:
$schedule->command('emails:send')->withoutOverlapping();
I det här exemplet körs kommandot emails:send
Artisan varje minut om det inte redan är igång. Metoden withoutOverlapping
är särskilt användbar om du har uppgifter som varierar drastiskt i exekveringstid, vilket gör att du inte kan förutsäga exakt hur lång tid en viss uppgift kommer att ta.
Om det behövs kan du ange hur många minuter som måste gå innan spärren ”utan överlappning” löper ut. Som standard upphör låsningen att gälla efter 24 timmar:
$schedule->command('emails:send')->withoutOverlapping(10);
Körning av uppgifter på en server
{note} För att kunna använda den här funktionen måste ditt program använda
database
,memcached
,dynamodb
ellerredis
som standardcachedrivrutin för ditt program. Dessutom måste alla servrar kommunicera med samma centrala cacheserver.
Om schemaläggaren i ditt program körs på flera servrar kan du begränsa ett schemalagt jobb så att det endast utförs på en enda server. Anta till exempel att du har en schemalagd aktivitet som genererar en ny rapport varje fredagskväll. Om schemaläggaren körs på tre arbetsservrar kommer den schemalagda aktiviteten att köras på alla tre servrar och generera rapporten tre gånger. Inte bra!
Om du vill ange att uppgiften bara ska köras på en server använder du metoden onOneServer
när du definierar den schemalagda uppgiften. Den första servern som får uppgiften kommer att säkra ett atomärt lås på uppgiften för att förhindra att andra servrar kör samma uppgift samtidigt:
Bakgrundsuppgifter
Som standard kommer flera uppgifter som schemaläggs samtidigt att exekveras sekventiellt baserat på den ordning de definieras i din schedule
-metod. Om du har uppgifter som pågår länge kan detta leda till att efterföljande uppgifter startar mycket senare än beräknat. Om du vill köra uppgifter i bakgrunden så att alla kan köras samtidigt kan du använda runInBackground
-metoden:
$schedule->command('analytics:report') ->daily() ->runInBackground();
{note} Metoden
runInBackground
får endast användas när du schemalägger uppgifter via metodernacommand
ochexec
.
Underhållsläge
De schemalagda uppgifterna i ditt program kommer inte att köras när programmet befinner sig i underhållsläge, eftersom vi inte vill att dina uppgifter ska störa oavslutade underhållsarbeten som du eventuellt utför på din server. Men om du vill tvinga en uppgift att köras även i underhållsläge kan du anropa metoden evenInMaintenanceMode
när du definierar uppgiften:
$schedule->command('emails:send')->evenInMaintenanceMode();
Körning av schemaläggaren
Nu när vi har lärt oss hur man definierar schemalagda uppgifter ska vi diskutera hur man faktiskt kör dem på vår server. Kommandot schedule:run
Artisan utvärderar alla dina schemalagda uppgifter och bestämmer om de behöver köras baserat på serverns aktuella tid.
Så när vi använder Larvels schemaläggare behöver vi bara lägga till en enda cron-konfigurationspost på vår server som kör kommandot schedule:run
varje minut. Om du inte vet hur du lägger till cronposter på din server kan du överväga att använda en tjänst som Laravel Forge som kan hantera cronposterna åt dig:
* * * * * cd /path-to-your-project && php artisan schedule:run >> /dev/null 2>&1
Körning av schemaläggaren lokalt
Typiskt sett skulle du inte lägga till en schemaläggar-cronpost på din lokala utvecklingsmaskin. Istället kan du använda kommandot schedule:work
Artisan. Det här kommandot körs i förgrunden och anropar schemaläggaren varje minut tills du avslutar kommandot:
php artisan schedule:work
Task Output
Laravel-schemaläggaren tillhandahåller flera bekväma metoder för att arbeta med den utdata som genereras av schemalagda uppgifter. För det första kan du med hjälp av metoden sendOutputTo
skicka utdata till en fil för senare granskning:
$schedule->command('emails:send') ->daily() ->sendOutputTo($filePath);
Om du vill bifoga utdata till en viss fil kan du använda metoden appendOutputTo
:
$schedule->command('emails:send') ->daily() ->appendOutputTo($filePath);
Med hjälp av metoden emailOutputTo
kan du maila utdata till en valfri e-postadress. Innan du skickar utdata från en uppgift via e-post bör du konfigurera Laravels e-posttjänster:
$schedule->command('report:generate') ->daily() ->sendOutputTo($filePath) ->emailOutputTo('');
Om du bara vill skicka utdata via e-post om det schemalagda Artisan- eller systemkommandot avslutas med en utgångskod som inte är noll, använder du emailOutputOnFailure
-metoden:
$schedule->command('report:generate') ->daily() ->emailOutputOnFailure('');
{not} Metoderna
emailOutputTo
,emailOutputOnFailure
,sendOutputTo
ochappendOutputTo
är exklusiva för metodernacommand
ochexec
.
Task Hooks
Med hjälp av metoderna before
och after
kan du ange kod som ska exekveras före och efter att den schemalagda uppgiften exekveras:
$schedule->command('emails:send') ->daily() ->before(function () { // The task is about to execute... }) ->after(function () { // The task has executed... });
Med hjälp av metoderna onSuccess
och onFailure
kan du ange kod som ska exekveras om den schemalagda uppgiften lyckas eller misslyckas. Ett misslyckande indikerar att det schemalagda Artisan- eller systemkommandot avslutades med en utgångskod som inte är noll:
$schedule->command('emails:send') ->daily() ->onSuccess(function () { // The task succeeded... }) ->onFailure(function () { // The task failed... });
Om utdata finns tillgängligt från ditt kommando kan du få tillgång till det i dina after
-, onSuccess
– eller onFailure
-krokar genom att typhita en Illuminate\Support\Stringable
-instans som $output
-argument i definitionen av din kroks stängning:
use Illuminate\Support\Stringable;$schedule->command('emails:send') ->daily() ->onSuccess(function (Stringable $output) { // The task succeeded... }) ->onFailure(function (Stringable $output) { // The task failed... });
Ping URL:er
Med hjälp av metoderna pingBefore
och thenPing
kan schemaläggaren automatiskt pinga en viss URL före eller efter att en uppgift har utförts. Den här metoden är användbar för att meddela en extern tjänst, t.ex. Envoyer, att den schemalagda uppgiften börjar eller har avslutats:
$schedule->command('emails:send') ->daily() ->pingBefore($url) ->thenPing($url);
Metoderna pingBeforeIf
och thenPingIf
kan användas för att pinga en viss URL endast om ett visst villkor är true
:
$schedule->command('emails:send') ->daily() ->pingBeforeIf($condition, $url) ->thenPingIf($condition, $url);
Metoderna pingOnSuccess
och pingOnFailure
kan användas för att pinga en viss URL endast om uppgiften lyckas eller misslyckas. Ett misslyckande indikerar att det schemalagda Artisan- eller systemkommandot avslutades med en utgångskod som inte är noll:
$schedule->command('emails:send') ->daily() ->pingOnSuccess($successUrl) ->pingOnFailure($failureUrl);
Alla ping-metoderna kräver Guzzle HTTP-biblioteket. Guzzle installeras vanligtvis som standard i alla nya Laravel-projekt, men du kan manuellt installera Guzzle i ditt projekt med hjälp av Composer-pakethanteraren om det har tagits bort av misstag:
composer require guzzlehttp/guzzle
Lämna ett svar