Skip to content

Commit 5bf425e

Browse files
authoredMay 16, 2020
Merge pull request #30 from stackkit/feature/queue
Queue function and Laravel 7 support
2 parents d38c7e7 + 98aba43 commit 5bf425e

11 files changed

+194
-32
lines changed
 

‎.github/workflows/run-tests.yml

+3-1
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,11 @@ jobs:
1212
strategy:
1313
matrix:
1414
php: [7.4, 7.3, 7.2]
15-
laravel: [6.*, 5.8.*, 5.7.*, 5.6.*]
15+
laravel: [7.*, 6.*, 5.8.*, 5.7.*, 5.6.*]
1616
os: [ubuntu-latest]
1717
include:
18+
- laravel: 7.*
19+
testbench: 5.*
1820
- laravel: 6.*
1921
testbench: 4.*
2022
- laravel: 5.8.*

‎composer.json

+2-2
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,8 @@
3030
},
3131
"require-dev": {
3232
"mockery/mockery": "^1.2",
33-
"orchestra/testbench": "^3.5 || ^3.6 || ^3.7 || ^3.8 || ^4.0",
34-
"symfony/console": "^4.4",
33+
"orchestra/testbench": "^3.5 || ^3.6 || ^3.7 || ^3.8 || ^4.0 || ^5.0",
34+
"symfony/console": "^4.4|^5.0",
3535
"tecnickcom/tcpdf": "^6.3"
3636
}
3737
}

‎src/Email.php

+12-3
Original file line numberDiff line numberDiff line change
@@ -348,7 +348,7 @@ public function hasFrom()
348348
*/
349349
public function hasCc()
350350
{
351-
return strlen($this->getOriginal('cc')) > 0;
351+
return strlen($this->getRawDatabaseValue('cc')) > 0;
352352
}
353353

354354
/**
@@ -358,7 +358,7 @@ public function hasCc()
358358
*/
359359
public function hasBcc()
360360
{
361-
return strlen($this->getOriginal('bcc')) > 0;
361+
return strlen($this->getRawDatabaseValue('bcc')) > 0;
362362
}
363363

364364
/**
@@ -378,7 +378,7 @@ public function isScheduled()
378378
*/
379379
public function isEncrypted()
380380
{
381-
return (bool) $this->getOriginal('encrypted');
381+
return (bool) $this->getRawDatabaseValue('encrypted');
382382
}
383383

384384
/**
@@ -479,4 +479,13 @@ public function retry()
479479

480480
$retry->save();
481481
}
482+
483+
public function getRawDatabaseValue($key = null, $default = null)
484+
{
485+
if (method_exists($this, 'getRawOriginal')) {
486+
return $this->getRawOriginal($key, $default);
487+
}
488+
489+
return $this->getOriginal($key, $default);
490+
}
482491
}

‎src/EmailComposer.php

+30
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,27 @@ public function later($scheduledAt)
194194
return $this->send();
195195
}
196196

197+
/**
198+
* Queue the e-mail.
199+
*
200+
* @param string|null $connection
201+
* @param string|null $queue
202+
* @param \DateTimeInterface|\DateInterval|int|null $delay
203+
* @return Email
204+
*/
205+
public function queue($connection = null, $queue = null, $delay = null)
206+
{
207+
$connection = $connection ?: config('queue.default');
208+
$queue = $queue ?: 'default';
209+
210+
$this->setData('queued', true);
211+
$this->setData('connection', $connection);
212+
$this->setData('queue', $queue);
213+
$this->setData('delay', $delay);
214+
215+
return $this->send();
216+
}
217+
197218
/**
198219
* Set the Mailable.
199220
*
@@ -273,6 +294,15 @@ public function send()
273294

274295
$this->email->refresh();
275296

297+
if ($this->getData('queued', false) === true) {
298+
dispatch(new SendEmailJob($this->email))
299+
->onConnection($this->getData('connection'))
300+
->onQueue($this->getData('queue'))
301+
->delay($this->getData('delay'));
302+
303+
return $this->email;
304+
}
305+
276306
if (Config::sendImmediately()) {
277307
$this->email->send();
278308
}

‎src/SendEmailJob.php

+27
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
<?php
2+
3+
4+
namespace Stackkit\LaravelDatabaseEmails;
5+
6+
use Illuminate\Bus\Queueable;
7+
use Illuminate\Contracts\Queue\ShouldQueue;
8+
use Illuminate\Foundation\Bus\Dispatchable;
9+
use Illuminate\Queue\InteractsWithQueue;
10+
use Illuminate\Queue\SerializesModels;
11+
12+
class SendEmailJob implements ShouldQueue
13+
{
14+
use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
15+
16+
public $email;
17+
18+
public function __construct(Email $email)
19+
{
20+
$this->email = $email;
21+
}
22+
23+
public function handle()
24+
{
25+
(new Sender())->send($this->email);
26+
}
27+
}

‎src/Sender.php

+2-12
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,8 @@
22

33
namespace Stackkit\LaravelDatabaseEmails;
44

5-
use Illuminate\Mail\Mailer;
65
use Illuminate\Mail\Message;
6+
use Illuminate\Support\Facades\Mail;
77

88
class Sender
99
{
@@ -20,23 +20,13 @@ public function send(Email $email)
2020

2121
$email->markAsSending();
2222

23-
$this->getMailerInstance()->send([], [], function (Message $message) use ($email) {
23+
Mail::send([], [], function (Message $message) use ($email) {
2424
$this->buildMessage($message, $email);
2525
});
2626

2727
$email->markAsSent();
2828
}
2929

30-
/**
31-
* Get the instance of the Laravel mailer.
32-
*
33-
* @return Mailer
34-
*/
35-
private function getMailerInstance()
36-
{
37-
return app('mailer');
38-
}
39-
4030
/**
4131
* Build the e-mail message.
4232
*

‎tests/EncryptionTest.php

+7-7
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ public function the_recipient_should_be_encrypted_and_decrypted()
2626
{
2727
$email = $this->sendEmail(['recipient' => 'john@doe.com']);
2828

29-
$this->assertEquals('john@doe.com', decrypt($email->getOriginal('recipient')));
29+
$this->assertEquals('john@doe.com', decrypt($email->getRawDatabaseValue('recipient')));
3030

3131
$this->assertEquals('john@doe.com', $email->getRecipient());
3232
}
@@ -39,8 +39,8 @@ public function cc_and_bb_should_be_encrypted_and_decrypted()
3939
'bcc' => $bcc = ['jane+1@doe.com', 'jane+2@doe.com'],
4040
]);
4141

42-
$this->assertEquals($cc, decrypt($email->getOriginal('cc')));
43-
$this->assertEquals($bcc, decrypt($email->getOriginal('bcc')));
42+
$this->assertEquals($cc, decrypt($email->getRawDatabaseValue('cc')));
43+
$this->assertEquals($bcc, decrypt($email->getRawDatabaseValue('bcc')));
4444

4545
$this->assertEquals($cc, $email->getCc());
4646
$this->assertEquals($bcc, $email->getBcc());
@@ -51,7 +51,7 @@ public function the_subject_should_be_encrypted_and_decrypted()
5151
{
5252
$email = $this->sendEmail(['subject' => 'test subject']);
5353

54-
$this->assertEquals('test subject', decrypt($email->getOriginal('subject')));
54+
$this->assertEquals('test subject', decrypt($email->getRawDatabaseValue('subject')));
5555

5656
$this->assertEquals('test subject', $email->getSubject());
5757
}
@@ -63,7 +63,7 @@ public function the_variables_should_be_encrypted_and_decrypted()
6363

6464
$this->assertEquals(
6565
['name' => 'Jane Doe'],
66-
decrypt($email->getOriginal('variables'))
66+
decrypt($email->getRawDatabaseValue('variables'))
6767
);
6868

6969
$this->assertEquals(
@@ -79,7 +79,7 @@ public function the_body_should_be_encrypted_and_decrypted()
7979

8080
$expectedBody = "Name: Jane Doe\n";
8181

82-
$this->assertEquals($expectedBody, decrypt($email->getOriginal('body')));
82+
$this->assertEquals($expectedBody, decrypt($email->getRawDatabaseValue('body')));
8383

8484
$this->assertEquals($expectedBody, $email->getBody());
8585
}
@@ -94,7 +94,7 @@ public function from_should_be_encrypted_and_decrypted()
9494
'name' => 'Marick',
9595
];
9696

97-
$this->assertEquals($expect, decrypt($email->getOriginal('from')));
97+
$this->assertEquals($expect, decrypt($email->getRawDatabaseValue('from')));
9898
$this->assertEquals($expect, $email->getFrom());
9999
}
100100
}

‎tests/QueuedEmailsTest.php

+100
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,100 @@
1+
<?php
2+
3+
namespace Tests;
4+
5+
use Illuminate\Support\Facades\Queue;
6+
use Stackkit\LaravelDatabaseEmails\SendEmailJob;
7+
use Illuminate\Support\Facades\Mail;
8+
9+
class QueuedEmailsTest extends TestCase
10+
{
11+
public function setUp(): void
12+
{
13+
parent::setUp();
14+
}
15+
16+
/** @test */
17+
public function queueing_an_email_will_leave_sending_on_false()
18+
{
19+
$email = $this->queueEmail();
20+
21+
$this->assertEquals(0, $email->sending);
22+
}
23+
24+
/** @test */
25+
public function queueing_an_email_will_dispatch_a_job()
26+
{
27+
Queue::fake();
28+
29+
$email = $this->queueEmail();
30+
31+
Queue::assertPushed(SendEmailJob::class, function (SendEmailJob $job) use ($email) {
32+
return $job->email->id === $email->id;
33+
});
34+
}
35+
36+
/** @test */
37+
public function emails_can_be_queued_on_a_specific_connection()
38+
{
39+
Queue::fake();
40+
41+
$this->queueEmail('some-connection');
42+
43+
Queue::assertPushed(SendEmailJob::class, function (SendEmailJob $job) {
44+
return $job->connection === 'some-connection';
45+
});
46+
}
47+
48+
/** @test */
49+
public function emails_can_be_queued_on_a_specific_queue()
50+
{
51+
Queue::fake();
52+
53+
$this->queueEmail('default', 'some-queue');
54+
55+
Queue::assertPushed(SendEmailJob::class, function (SendEmailJob $job) {
56+
return $job->queue === 'some-queue';
57+
});
58+
}
59+
60+
/** @test */
61+
public function emails_can_be_queued_with_a_delay()
62+
{
63+
Queue::fake();
64+
65+
$delay = now()->addMinutes(6);
66+
67+
$this->queueEmail(null, null, $delay);
68+
69+
Queue::assertPushed(SendEmailJob::class, function (SendEmailJob $job) use ($delay) {
70+
return $job->delay->getTimestamp() === $delay->timestamp;
71+
});
72+
}
73+
74+
/** @test */
75+
public function the_send_email_job_will_call_send_on_the_email_instance()
76+
{
77+
Queue::fake();
78+
79+
$email = $this->queueEmail('default', 'some-queue');
80+
81+
$job = new SendEmailJob($email);
82+
83+
Mail::shouldReceive('send')->once();
84+
85+
$job->handle();
86+
}
87+
88+
/** @test */
89+
public function the_mail_will_be_marked_as_sent_when_job_is_finished()
90+
{
91+
Queue::fake();
92+
93+
$email = $this->queueEmail('default', 'some-queue');
94+
95+
$job = new SendEmailJob($email);
96+
$job->handle();
97+
98+
$this->assertTrue($email->isSent());
99+
}
100+
}

‎tests/SendEmailsCommandTest.php

+3-5
Original file line numberDiff line numberDiff line change
@@ -39,8 +39,6 @@ public function an_email_should_not_be_sent_once_it_is_marked_as_sent()
3939

4040
$this->assertNotNull($firstSend = $email->fresh()->getSendDate());
4141

42-
sleep(1);
43-
4442
$this->artisan('email:send');
4543

4644
$this->assertEquals(1, $email->fresh()->getAttempts());
@@ -50,14 +48,14 @@ public function an_email_should_not_be_sent_once_it_is_marked_as_sent()
5048
/** @test */
5149
public function if_an_email_fails_to_be_sent_it_should_be_logged_in_the_database()
5250
{
53-
$this->app['config']['mail.driver'] = 'does-not-exist';
54-
5551
$email = $this->sendEmail();
5652

53+
$email->update(['recipient' => 'asdf']);
54+
5755
$this->artisan('email:send');
5856

5957
$this->assertTrue($email->fresh()->hasFailed());
60-
$this->assertStringContains('Driver [does-not-exist] not supported.', $email->fresh()->getError());
58+
$this->assertStringContains('Swift_RfcComplianceException', $email->fresh()->getError());
6159
}
6260

6361
/** @test */

‎tests/SenderTest.php

+1-2
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,7 @@ public function it_sends_an_email()
2424
{
2525
$this->sendEmail();
2626

27-
Mail::shouldReceive('send')
28-
->once();
27+
Mail::shouldReceive('send')->once();
2928

3029
$this->artisan('email:send');
3130
}

‎tests/TestCase.php

+7
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,8 @@ protected function getEnvironmentSetUp($app)
9292
'prefix' => '',
9393
'strict' => true,
9494
]);
95+
96+
$app['config']->set('mail.driver', 'log');
9597
}
9698

9799
public function createEmail($overwrite = [])
@@ -131,6 +133,11 @@ public function scheduleEmail($scheduledFor, $overwrite = [])
131133
return $this->createEmail($overwrite)->schedule($scheduledFor);
132134
}
133135

136+
public function queueEmail($connection = null, $queue = null, $delay = null, $overwrite = [])
137+
{
138+
return $this->createEmail($overwrite)->queue($connection, $queue, $delay);
139+
}
140+
134141
public function assertStringContains($needle, $haystack)
135142
{
136143
if (method_exists($this, 'assertStringContainsString')) {

0 commit comments

Comments
 (0)
Please sign in to comment.