Laravel: How to Queue mails to send later
Asked Answered
P

2

9

Im trying to use the Mail::queue to send and email, but when I call this function it simple sends the mail, and the response is delayed ... I thought that the point of using Mail::queue was to queue ....

I want the response to came instantly, not having to wait for the email to be sent

for eg

Mail::queue('emails.template', $data, function($message) {
    $message->to('[email protected]');
    $message->subject('Notificacion');
});

return Response::json(array('error' => 0, 'message' => 'Ok'));

I want to receive the response without waiting for the mail to be sent. How can I do that???

Piezochemistry answered 7/5, 2014 at 4:48 Comment(3)
The method Mail::later does the same thing, it just waits whatever time I tell it to wait and the response is delayedPiezochemistry
It's practically impossible. You will get response from server your operation executed.Allowed
@GabrielMatusevich may I know whether you get any solutions about this? I also meet the same problems when using laravel5Chamois
W
5

What queue driver (app/config/queue.php - 'default' param) are you using? If you're using sync, and haven't set up one of the others, then you're using the synchronous driver, which does exactly what the name says: Runs your queued task as soon as the task is created.

You need to configure an MQ server for Laravel to talk to. You can get a free iron.io account for this, and then you need to configure it, for instance:

'iron' => array(
    'driver'  => 'iron',
    'project' => 'iron-io-project-id',
    'token'   => 'iron-io-queue-token',
    'queue'   => 'queue-name',
),

Then when you use Mail::queue() it will push the instruction to iron.io. You'll then have to have another thread listening on the queue - just run php artisan queue:listen and leave it running while messages are pushed to the queue.

Wei answered 13/5, 2014 at 16:59 Comment(3)
This is really helpful but I'm actually looking for some way to do this locally without depending on another service :PPiezochemistry
what about beanstalkd?? do you have an example config for it?Piezochemistry
Using iron.io really will be the fastest way to get it set up. For beanstalkd, once you install it, you should just be able to use the configured defaults - just change default on line 18 to beanstalkd.Wei
R
-1
 /**
 * Get all email recipients and include their user details for Mailgun's
 * template tags - %recipient.userToken%
 */
private function getRecipients()
{
    foreach (User::get() as $user)
    {
        $this->recipients[$user->email] = [
            'id' => $user->id,
            'userToken' => $user->user_token,
            'first_name' => $user->first_name,
            'last_name' => $user->last_name,
            'email' => $user->email
        ];
    }
}

private function sendEmail()
{
    $subject = 'Demo Subject';
    /**
     * Data for the Blade template
     */
    $data = [
        'foo' => 'bar'
    ];
    // Inline the CSS for the email
    $inliner = new InlineEmail('emails.some-email', $data);
    $content = $inliner->convert();

    // Create Emails table entry for this email. Used for Mailgun webhooks
    $email = Email::create(['user_id' => $this->userId, 'subject' => $subject, 'email_id' => str_random()]);

    // Prepare the email addresses
    $emailAddresses = array_column($this->recipients, 'email');

    $this->mailgun->sendMessage('demo.org', [
        "from" => '[email protected]',
        "to" => implode(',', $emailAddresses), // Comma separated list of email addresses
        "subject" => $subject,
        "html" => $content, // Inlined CSS HTML from Blade
        "text" => "Plain text message here",
        "recipient-variables" => json_encode($this->recipients), // Required for batch sending, matches to recipient details
        "v:messageId" => $email->id, // Custom variable used for webhooks
    ]);
}
Revels answered 6/2, 2017 at 7:20 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.