Queues en Laravel

¿Qué son las queues en Laravel?

Laravel nos proporciona una API de queues para crear procesos en nuestra aplicación, que trabajarán en segundo plano, para mejorar la experiencia de nuestros usuarios.

Un ejemplo muy habitual del uso de queues podría ser el envio de un correo desde un formulario. Si no utilizasemos queues, el usuario debería esperar hasta que se envíe el correo, en cambio, con el uso de queues el usuario verá que la acción se ejecuta de forma instantánea, aunque el correo aún no se haya enviado.

En este artículo vamos a aprender a hacer uso de queues con el ejemplo anterior.

Trabajando con queues en Laravel 

Vistas para el email

Lo primero que haremos será crear una vista con el formulario (test.blade.php) y otra que será la que se envíe en el correo (email.blade.php)

<!--test.blade.php-->
<h2>Formulario de contacto</h2>
<form action={{route('contact')}} method="POST">
     {{ csrf_field() }}
    <div class="form-group">
        <label for="name">Nombre</label>
        <input name="name" type="text">
    </div>
    <div class="form-group">
        <label for="name">Mensaje</label>
        <input name="msg" type="text">
    </div>
    <div class="form-group">
        <button type="submit" id='btn-contact' class="btn">Enviar</button>
    </div>
</form>
<!--email.blade.php-->
<h2>Nombre: {{$nameEmail}}</h2>
<h2>Mensaje: {{$messageEmail}}</h2>

Configurando el archivo .env

Nos dirigimos al archivo .env, que será donde vamos a añadir la configuración de nuestra base de datos, el email y las queues (Si nos sabes configurar el .env para trabajar con correos, visita nuestro articulo donde explicamos como configurarlo hasta el apartado «Cofiguración de nuestra aplicación en laravel»).

Una vez añadidos los datos de nuestra base de datos e email, debemos cambiar el valor de la variable queue_connection por database (El nombre de la variable puede cambiar dependiendo de la versión del framework con la que estés trabajando, pero contendrá la palabra QUEUE):

QUEUE_CONNECTION=database

Configurando nuestra base de datos

Para trabajar con queues, necesitaremos crear la tabla jobs en nuestro base de datos, que será la encargada de almacenar nuestras queues hasta se termine el proceso, para ello ejecutaremos:

php artisan queue:table

Esto nos creará un nuevo archivo de migración.

Ahora debemos ejecutar el comando de migrate, para añadir nuestra nueva tabla a la base de datos:

php artisan migrate

Creando la clase email con queues

Vamos a crear la clase EmailMessage, que extenderá de Mailable. Para ello, vamos a utilizar el comando:

php artisan make:mail EmailMessage

A esta clase vamos a implementar ShouldQueue para que trabaje en segundo plano a partir de las queues, para ello añadiremos esto:

class EmailMessage extends Mailable implements ShouldQueue

Luego, vamos a declarar como publicas las variables que enviará nuestro formulario y las añadiremos en el contructor de la clase:

    //Importante declarar las variables
    public $name;
    public $message;

    /**
     * Create a new message instance.
     *
     * @return void
     */
    public function __construct($name, $message)
    {
        $this->name = $name;
        $this->message = $message;
    }

Por último, en la función build, vamos a retornar los datos del correo (a quién va dirigido, la vista que va a utilizar, el asunto y las variables):

public function build()
{
   return $this->from("nigmacode@gmail.com")
          ->view('email')
          ->subject('Asunto del mensaje')
          ->with([
                  'nameEmail' => $this->name,
                  'messageEmail' => $this->message,
                ]);
}

Controlador y ruta

Ahora solo quedaría crear el controlador (EmailController.php por ejemplo), dónde importaremos la clase anterior y haremos uso de ella:

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request; 
//Importante importar la clase EmailMessage y Mail
use App\Mail\EmailMessage; 
use Mail;

class EmailController extends Controller
{

    public function contact(Request $request){
        $name = $request->name;
        $message = $request->message;

        $for = "nigmacode@gmail.com";
        Mail::to($for)->send(new EmailMessage($name, $message));

        return redirect()->back();
    }
}

Y la ruta, que será la que añadimos anteriormente en la vista del formulario:

Route::get('/', function () {
    return view('test');
}); //Esta ruta la ponemos en la raiz para que nada mas ejecutar nuestra aplicación aparezca nuestro formulario

Route::post('/contactar', 'EmailController@contact')->name('contact');
//Ruta que esta señalando nuestro formulario

Probando nuestra queue en Laravel

Una vez hecho esto, ya tendríamos nuestro aplicación lista para trabajar con queues.

Si enviamos el formulario, la petición se haría de forma instantanea y se añadiria en la tabla jobs, de nuestra base de datos, la tarea:

queue_bd

Y ejecutando el comando:

php artisan queue:work

Dándonos éste mensaje, que nos mostrará las queues que se han procesado, en este caso, la única que tenemos:

queue_laravel

De esta forma, se realizarían todas las tareas que tenemos en la queue de nuestra aplicación Laravel.

Importante: No es necesario que estemos ejecutando el comando anterior, ya que si lo dejamos ejecutado, las tareas de las queue se procesarán solas.