Gestire una newsletter con i jobs di Laravel
La gestione di una newsletter è una delle possibili funzionalità richieste dalle applicazioni moderne. Se la incontriamo nelle specifiche di un progetto, dobbiamo tenere a mente che l'invio sincrono delle email può rallentare la risposta del server e l'esperienza utente.
In questo articolo, vedremo come gestire efficacemente l'invio delle email utilizzando i jobs di Laravel.
In Laravel, i jobs sono delle classi che rappresentano dei processi asincroni eseguiti in background nel sistema. Un job è una singola unità di lavoro che viene messa in coda e poi processata in un secondo momento da un "worker".
Vengono utilizzati per eseguire attività che richiedono del tempo, come l'invio di email, la generazione di report o l'elaborazione di grandi quantità di dati. Invece di eseguire queste attività immediatamente durante la richiesta HTTP, i jobs vengono processati in un second momento, evitando di bloccare il flusso principale dell'applicazione.
Configurazione dell'applicazione per gestire i jobs
Prima di tutto, assicuriamoci di aver correttamente configurato il nostro database nel file .env del nostro progetto Laravel. Verifichiamo che le credenziali di accesso al database siano corrette e che il driver sia impostato sul database che intendiamo utilizzare, ad esempio MySQL o PostgreSQL.
Il sistema di gestione delle job queues di Laravel richiede la creazione di due tabelle nel database: jobs e failed_jobs.
Per creare queste tabelle, apriamo il nostro terminale e navighiamo nella cartella del nostro progetto Laravel. Quindi, eseguiamo il comando Artisan seguente:
Questo comando genererà una migration per la tabella jobs. Questa tabella conterrà le informazioni sui job in coda, come il tipo di job, i dati del job e lo stato del job.
Successivamente, creiamo la tabella failed_jobs, che sarà utilizzata per registrare i job che non sono riusciti ad essere processati correttamente. Sempre nel nostro terminale, eseguiamo il comando Artisan seguente:
Questo genererà una migration per la tabella failed_jobs. Per creare la tabella nel database, eseguiamo il comando di migrazione:
Ora, dovremmo avere le tabelle jobs e failed_jobs nel nostro database.
Successivamente, apriamo il file .env del nostro progetto Laravel. Troviamo la riga che inizia con QUEUE_CONNECTION= e assicuriamoci che sia impostata su database.
Diamo il comando per ripulire la cache del software
Questa è la procedura per configurare il sistema di gestione delle code di lavoro nel database in Laravel. Assicuriamoci di aver correttamente configurato il nostro database, creato le tabelle jobs e failed_jobs e impostato il driver della coda nel file .env.
Creazione della classe personalizzata per gestire l'email
Per creare una classe email personalizzata, possiamo sfruttare il comando make:mail di Artisan. Utilizzando il terminale, eseguiamo il seguente comando:
Una volta creata la classe di email, possiamo personalizzare la vista associata al template dell'email. Laravel consente di utilizzare il motore di rendering Blade per creare viste eleganti e flessibili. All'interno della classe SendEmail, troveremo un metodo chiamato build().
Questo metodo ci consente di impostare i dettagli dell'email, tra cui il mittente, il destinatario, l'oggetto e il contenuto dell'email. Possiamo anche definire il template da utilizzare per l'aspetto visivo dell'email. Utilizzando il motore di rendering Blade, possiamo creare una vista con HTML e variabili dinamiche per personalizzare il contenuto dell'email in base alle esigenze specifiche.
Ecco un esempio di come potrebbe essere il metodo build() all'interno della classe SendEmail:
A questo punto possiamo passare alla configurazione del server SMPT
Configurazione del server SMPT
Per inviare effettivamente le email, dobbiamo configurare le credenziali SMTP nel file .env del nostro progetto Laravel. Raccomandiamo di utilizzare Google come provider di servizi SMTP per la sua affidabilità e semplicità di configurazione. Possiamo accedere al pannello di controllo del nostro account Google e generare le credenziali SMTP necessarie. Successivamente, nel file .env, dobbiamo configurare le seguenti variabili di ambiente:
Creazione del job per inviare le emails
Per iniziare, utilizzeremo il comando Artisan di Laravel per generare una nuova classe di job chiamata SendEmailJob. Esegui il seguente comando nella riga di comando:
Questo comando creerà un nuovo file SendEmailJob.php all'interno della cartella app/Jobs del nostro progetto Laravel.
All'interno del file del job generato, dovremo includere la classe SendEmail che abbiamo creato in precedenza per gestire l'invio delle email. Per farlo, importiamo la classe all'inizio del file:
Il metodo handle è il cuore del job e dovrà contenere la logica per l'invio effettivo dell'email. All'interno di questo metodo, definiamo il codice che prenderà l'utente destinatario e il messaggio dell'email, e invierà l'email utilizzando la classe SendEmail.
Durante l'invio delle email, potrebbero verificarsi delle eccezioni, ad esempio se il server SMTP non è disponibile. Per gestire queste eccezioni, dobbiamo utilizzare i blocchi try-catch per catturare gli errori e prendere le appropriate misure correttive. Ad esempio:
Inserimento del job nella coda di lavorazione
Per mettere il job nella coda di lavorazione, puoi utilizzare il metodo dispatch fornito dalla classe Dispatchable di Laravel. Questo metodo prende un'istanza del job e lo inserisce nella coda di lavoro corrispondente.
Nel controller o in qualsiasi altro punto in cui si desidera inviare l'email, richiamiamo il metodo dispatch sul job che abbiamo creato. Possiamo passare eventuali argomenti o parametri necessari al costruttore del job tramite il metodo dispatch. Nel nostro caso, dovremmo passare l'oggetto $user al job, in modo che poi quest'ultimo lo passi a sua volta alla classe SendMail.
Per gestire il ritardo nell'esecuzione di un job, Laravel offre il concetto di "job in coda". Puoi specificare un ritardo prima che un job venga effettivamente eseguito, consentendo di programmare l'esecuzione del job in un momento successivo.
Per aggiungere un ritardo all'esecuzione di un job, puoi utilizzare il metodo delay nel momento in cui lo dispatchi nella coda di lavorazione. Il metodo delay accetta un parametro di tipo DateTime o un intervallo di tempo rappresentato in secondi. Ecco un esempio:
Nell'esempio sopra, il job SendEmailJob verrà eseguito 10 minuti dopo essere stato inserito nella coda di lavorazione. Puoi personalizzare il ritardo in base alle tue esigenze specifiche.
Ma supponiamo che vogliamo dare la possibilità all'utente di annullare un job che ormai è stato schedulato, come possiamo fare? In teoria basta salvare l'identificativo del job da qualche parte, in modo da gestirlo a seconda delle esigenze. Per ottenere l'id di un job una volta salvato nel database, dobbiamo usare usare una sintassi differente.
In questo ultimo esempio, abbiamo creato un'istanza del job SendEmailJob passando il destinatario al suo costruttore. Utilizziamo quindi il metodo delay per specificare un ritardo di 10 minuti prima dell'esecuzione effettiva del job.
Successivamente, creiamo un'istanza del Dispatcher utilizzando il servizio app() di Laravel. Il Dispatcher è responsabile per la gestione dell'inserimento del job nella coda di lavorazione.
Infine, utilizziamo il metodo dispatch del Dispatcher per eseguire il dispatch del job nella coda di lavorazione. Questo metodo restituisce un identificatore univoco ($job_id) che rappresenta il job appena creato e inserito nella coda. Puoi utilizzare questo ID per monitorare lo stato o gestire il job in seguito, se necessario.
Avvio della coda di lavorazione
Ora possiamo avviare il worker per iniziare ad elaborare i job in coda. Nel nostro terminale, eseguiamo il comando Artisan seguente:
Il worker si metterà in ascolto delle code di lavoro e inizierà ad elaborare i job in coda. Possiamo anche specificare opzioni aggiuntive come --queue per specificare la coda da elaborare, ad esempio --queue=emails se desideriamo elaborare solo i job della coda "emails".