Skip to content

Commit ad99d8c

Browse files
Merge pull request #5 from SebastianKrupinski/chore/mail-vacation-test
chore: mail vacation tests
2 parents d841730 + 83dc70e commit ad99d8c

4 files changed

Lines changed: 264 additions & 8 deletions

File tree

‎lib/Requests/Mail/MailVacationParameters.php‎

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ public function end(DateTimeInterface $value): static
6262
*
6363
* @return static
6464
*/
65-
public function subject(string $value): static
65+
public function subject(string|null $value): static
6666
{
6767
return $this->parameter('subject', $value);
6868
}
@@ -74,7 +74,7 @@ public function subject(string $value): static
7474
*
7575
* @return static
7676
*/
77-
public function textBody(string $value): static
77+
public function textBody(string|null $value): static
7878
{
7979
return $this->parameter('textBody', $value);
8080
}
@@ -86,7 +86,7 @@ public function textBody(string $value): static
8686
*
8787
* @return static
8888
*/
89-
public function htmlBody(string $value): static
89+
public function htmlBody(string|null $value): static
9090
{
9191
return $this->parameter('htmlBody', $value);
9292
}

‎lib/Responses/ResponseClasses.php‎

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ class ResponseClasses
1616
'Blob' => 'JmapClient\Responses\Blob\BlobParameters',
1717
'Mailbox' => 'JmapClient\Responses\Mail\MailboxParameters',
1818
'Identity' => 'JmapClient\Responses\Mail\MailIdentityParameters',
19+
'VacationResponse' => 'JmapClient\Responses\Mail\MailVacationParameters',
1920
'Email' => 'JmapClient\Responses\Mail\MailParameters',
2021
'EmailSubmission' => 'JmapClient\Responses\Mail\MailSubmissionParameters',
2122
'Calendar' => 'JmapClient\Responses\Calendar\CalendarParameters',
@@ -38,6 +39,9 @@ class ResponseClasses
3839
'Identity/get' => 'JmapClient\Responses\Mail\MailIdentityGet',
3940
'Identity/set' => 'JmapClient\Responses\Mail\MailIdentitySet',
4041
'Identity/changes' => 'JmapClient\Responses\Mail\MailIdentityChanges',
42+
// Mail Vacation
43+
'VacationResponse/get' => 'JmapClient\Responses\Mail\MailVacationGet',
44+
'VacationResponse/set' => 'JmapClient\Responses\Mail\MailVacationSet',
4145
// Mail Collections
4246
'Mailbox/get' => 'JmapClient\Responses\Mail\MailboxGet',
4347
'Mailbox/set' => 'JmapClient\Responses\Mail\MailboxSet',

‎tests/integration/Mail/MailIdentityTest.php‎

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -65,13 +65,9 @@ public function tearDown(): void
6565
str_starts_with($identity->name(), 'To Delete Identity '))) {
6666
$rq = new MailIdentitySetRequest($this->account->id());
6767
$rq->delete($identity->id());
68-
$commands[] = $rq;
68+
$this->client->perform([$rq]);
6969
}
7070
}
71-
// transceive
72-
if (!empty($commands)) {
73-
//$this->client->perform($commands);
74-
}
7571
}
7672

7773
public function testMailIdentityGetAll(): void
Lines changed: 256 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,256 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
/**
5+
* SPDX-FileCopyrightText: Sebastian Krupinski <krupinski01@gmail.com>
6+
* SPDX-License-Identifier: AGPL-3.0-or-later
7+
*/
8+
9+
namespace JmapClient\Tests\Integration\Mail;
10+
11+
use JmapClient\Client;
12+
use JmapClient\Requests\Mail\MailVacationGet as MailVacationGetRequest;
13+
use JmapClient\Requests\Mail\MailVacationSet as MailVacationSetRequest;
14+
use JmapClient\Responses\Mail\MailVacationGet as MailVacationGetResponse;
15+
use JmapClient\Responses\Mail\MailVacationParameters;
16+
use JmapClient\Responses\Mail\MailVacationSet as MailVacationSetResponse;
17+
use JmapClient\Session\Account;
18+
use JmapClient\Tests\Integration\ClientFactory;
19+
use PHPUnit\Framework\TestCase;
20+
21+
class MailVacationTest extends TestCase
22+
{
23+
private Client $client;
24+
private Account $account;
25+
26+
public function setUp(): void
27+
{
28+
parent::setUp();
29+
$this->client = ClientFactory::instance('service1');
30+
$this->client->connect();
31+
$this->account = $this->client->sessionAccountDefault('mail');
32+
33+
// seed the singleton so that get tests always find at least one vacation response
34+
$rSeed = new MailVacationSetRequest($this->account->id());
35+
$pSeed = $rSeed->update('singleton');
36+
$pSeed->enabled(false);
37+
$pSeed->subject('Seed vacation subject');
38+
$pSeed->textBody('Seed vacation text body');
39+
$pSeed->htmlBody('<p>Seed vacation html body</p>');
40+
$seedBundle = $this->client->perform([$rSeed]);
41+
$this->assertNotNull($seedBundle->first()->updateSuccess('singleton'), 'Failed to seed vacation singleton');
42+
}
43+
44+
public function tearDown(): void
45+
{
46+
parent::tearDown();
47+
// per RFC 8621 §8.1 there is always exactly one VacationResponse with id "singleton"
48+
// reset it to a clean disabled state after each test
49+
$r0 = new MailVacationSetRequest($this->account->id());
50+
$p0 = $r0->update('singleton');
51+
$p0->enabled(false);
52+
$p0->subject(null);
53+
$p0->textBody(null);
54+
$p0->htmlBody(null);
55+
$this->client->perform([$r0]);
56+
}
57+
58+
public function testMailVacationGetAll(): void
59+
{
60+
// construct fetch request (no ids = retrieve all / the singleton)
61+
$r0 = new MailVacationGetRequest($this->account->id());
62+
63+
// transceive
64+
$bundle = $this->client->perform([$r0]);
65+
66+
// verify fetch response — servers MUST always return the singleton
67+
$this->assertEquals(1, $bundle->tally());
68+
$this->assertInstanceOf(MailVacationGetResponse::class, $bundle->first());
69+
$results = $bundle->first()->objects();
70+
$this->assertIsArray($results);
71+
$this->assertNotEmpty($results);
72+
foreach ($results as $result) {
73+
$this->assertInstanceOf(MailVacationParameters::class, $result);
74+
}
75+
}
76+
77+
public function testMailVacationGetSpecific(): void
78+
{
79+
// construct fetch request targeting the well-known singleton id
80+
$r0 = new MailVacationGetRequest($this->account->id());
81+
$r0->target('singleton');
82+
83+
// transceive
84+
$bundle = $this->client->perform([$r0]);
85+
86+
// verify fetch response
87+
$this->assertEquals(1, $bundle->tally());
88+
$this->assertInstanceOf(MailVacationGetResponse::class, $bundle->first());
89+
$result = $bundle->first()->object(0);
90+
$this->assertInstanceOf(MailVacationParameters::class, $result);
91+
$this->assertEquals('singleton', $result->id());
92+
}
93+
94+
public function testMailVacationGetWithProperties(): void
95+
{
96+
// construct fetch request with limited property set
97+
$r0 = new MailVacationGetRequest($this->account->id());
98+
$r0->property('id', 'isEnabled');
99+
100+
// transceive
101+
$bundle = $this->client->perform([$r0]);
102+
103+
// verify fetch response — unrequested properties should be absent/null
104+
$this->assertEquals(1, $bundle->tally());
105+
$this->assertInstanceOf(MailVacationGetResponse::class, $bundle->first());
106+
$result = $bundle->first()->object(0);
107+
$this->assertInstanceOf(MailVacationParameters::class, $result);
108+
$this->assertNotEmpty($result->id());
109+
$this->assertNull($result->subject());
110+
$this->assertNull($result->bodyText());
111+
$this->assertNull($result->bodyHtml());
112+
}
113+
114+
public function testMailVacationSetEnable(): void
115+
{
116+
// construct update request to enable the vacation response
117+
$r0 = new MailVacationSetRequest($this->account->id());
118+
$p0 = $r0->update('singleton');
119+
$p0->enabled(true);
120+
$p0->subject('Out of office');
121+
$p0->textBody('I am currently out of the office.');
122+
123+
// transceive
124+
$bundle = $this->client->perform([$r0]);
125+
126+
// verify set response
127+
$this->assertEquals(1, $bundle->tally());
128+
$this->assertInstanceOf(MailVacationSetResponse::class, $bundle->first());
129+
$result = $bundle->first()->updateSuccess('singleton');
130+
$this->assertNotNull($result);
131+
132+
// fetch and confirm persisted state
133+
$r1 = new MailVacationGetRequest($this->account->id());
134+
$r1->target('singleton');
135+
$bundle = $this->client->perform([$r1]);
136+
$vacation = $bundle->first()->object(0);
137+
$this->assertInstanceOf(MailVacationParameters::class, $vacation);
138+
$this->assertTrue($vacation->enabled());
139+
$this->assertEquals('Out of office', $vacation->subject());
140+
$this->assertEquals('I am currently out of the office.', $vacation->bodyText());
141+
}
142+
143+
public function testMailVacationSetDisable(): void
144+
{
145+
// first enable so we have a known starting state
146+
$r0 = new MailVacationSetRequest($this->account->id());
147+
$p0 = $r0->update('singleton');
148+
$p0->enabled(true);
149+
$p0->subject('Out of office');
150+
$p0->textBody('Away.');
151+
$this->client->perform([$r0]);
152+
153+
// now disable
154+
$r1 = new MailVacationSetRequest($this->account->id());
155+
$p1 = $r1->update('singleton');
156+
$p1->enabled(false);
157+
158+
// transceive
159+
$bundle = $this->client->perform([$r1]);
160+
161+
// verify set response
162+
$this->assertEquals(1, $bundle->tally());
163+
$this->assertInstanceOf(MailVacationSetResponse::class, $bundle->first());
164+
$result = $bundle->first()->updateSuccess('singleton');
165+
$this->assertNotNull($result);
166+
167+
// fetch and confirm disabled state
168+
$r2 = new MailVacationGetRequest($this->account->id());
169+
$r2->target('singleton');
170+
$bundle = $this->client->perform([$r2]);
171+
$vacation = $bundle->first()->object(0);
172+
$this->assertInstanceOf(MailVacationParameters::class, $vacation);
173+
$this->assertFalse($vacation->enabled());
174+
}
175+
176+
public function testMailVacationSetUpdateSubject(): void
177+
{
178+
$newSubject = 'Updated OOO ' . time();
179+
180+
// construct update request changing only the subject
181+
$r0 = new MailVacationSetRequest($this->account->id());
182+
$p0 = $r0->update('singleton');
183+
$p0->subject($newSubject);
184+
185+
// transceive
186+
$bundle = $this->client->perform([$r0]);
187+
188+
// verify set response
189+
$this->assertEquals(1, $bundle->tally());
190+
$this->assertInstanceOf(MailVacationSetResponse::class, $bundle->first());
191+
$result = $bundle->first()->updateSuccess('singleton');
192+
$this->assertNotNull($result);
193+
194+
// fetch and verify subject was persisted
195+
$r1 = new MailVacationGetRequest($this->account->id());
196+
$r1->target('singleton');
197+
$bundle = $this->client->perform([$r1]);
198+
$vacation = $bundle->first()->object(0);
199+
$this->assertInstanceOf(MailVacationParameters::class, $vacation);
200+
$this->assertEquals($newSubject, $vacation->subject());
201+
}
202+
203+
public function testMailVacationSetUpdateTextBody(): void
204+
{
205+
$newBody = 'Plain text body updated at ' . time();
206+
207+
// construct update request changing only the text body
208+
$r0 = new MailVacationSetRequest($this->account->id());
209+
$p0 = $r0->update('singleton');
210+
$p0->textBody($newBody);
211+
212+
// transceive
213+
$bundle = $this->client->perform([$r0]);
214+
215+
// verify set response
216+
$this->assertEquals(1, $bundle->tally());
217+
$this->assertInstanceOf(MailVacationSetResponse::class, $bundle->first());
218+
$result = $bundle->first()->updateSuccess('singleton');
219+
$this->assertNotNull($result);
220+
221+
// fetch and verify text body was persisted
222+
$r1 = new MailVacationGetRequest($this->account->id());
223+
$r1->target('singleton');
224+
$bundle = $this->client->perform([$r1]);
225+
$vacation = $bundle->first()->object(0);
226+
$this->assertInstanceOf(MailVacationParameters::class, $vacation);
227+
$this->assertEquals($newBody, $vacation->bodyText());
228+
}
229+
230+
public function testMailVacationSetUpdateHtmlBody(): void
231+
{
232+
$newHtml = '<p>HTML body updated at ' . time() . '</p>';
233+
234+
// construct update request changing only the HTML body
235+
$r0 = new MailVacationSetRequest($this->account->id());
236+
$p0 = $r0->update('singleton');
237+
$p0->htmlBody($newHtml);
238+
239+
// transceive
240+
$bundle = $this->client->perform([$r0]);
241+
242+
// verify set response
243+
$this->assertEquals(1, $bundle->tally());
244+
$this->assertInstanceOf(MailVacationSetResponse::class, $bundle->first());
245+
$result = $bundle->first()->updateSuccess('singleton');
246+
$this->assertNotNull($result);
247+
248+
// fetch and verify HTML body was persisted
249+
$r1 = new MailVacationGetRequest($this->account->id());
250+
$r1->target('singleton');
251+
$bundle = $this->client->perform([$r1]);
252+
$vacation = $bundle->first()->object(0);
253+
$this->assertInstanceOf(MailVacationParameters::class, $vacation);
254+
$this->assertEquals($newHtml, $vacation->bodyHtml());
255+
}
256+
}

0 commit comments

Comments
 (0)