Skip to content

Commit cf0bf34

Browse files
author
epriestley
committedAug 30, 2013
Allow MetaMTA adapters to indicate that a mail is permanently undeliverable
Summary: Currently, adapters can only fail mail temporarily. Allow them to indicate a permanent failure by throwing a special exception. Test Plan: Added and ran unit tests. Reviewers: wez, btrahan Reviewed By: btrahan CC: aran Differential Revision: https://secure.phabricator.com/D6847
1 parent 11f1268 commit cf0bf34

6 files changed

+84
-0
lines changed
 

‎src/__phutil_library_map__.php

+2
Original file line numberDiff line numberDiff line change
@@ -1302,6 +1302,7 @@
13021302
'PhabricatorMetaMTAMailBodyTestCase' => 'applications/metamta/view/__tests__/PhabricatorMetaMTAMailBodyTestCase.php',
13031303
'PhabricatorMetaMTAMailTestCase' => 'applications/metamta/storage/__tests__/PhabricatorMetaMTAMailTestCase.php',
13041304
'PhabricatorMetaMTAMailingList' => 'applications/mailinglists/storage/PhabricatorMetaMTAMailingList.php',
1305+
'PhabricatorMetaMTAPermanentFailureException' => 'applications/metamta/exception/PhabricatorMetaMTAPermanentFailureException.php',
13051306
'PhabricatorMetaMTAReceivedMail' => 'applications/metamta/storage/PhabricatorMetaMTAReceivedMail.php',
13061307
'PhabricatorMetaMTAReceivedMailProcessingException' => 'applications/metamta/exception/PhabricatorMetaMTAReceivedMailProcessingException.php',
13071308
'PhabricatorMetaMTAReceivedMailTestCase' => 'applications/metamta/storage/__tests__/PhabricatorMetaMTAReceivedMailTestCase.php',
@@ -3387,6 +3388,7 @@
33873388
0 => 'PhabricatorMetaMTADAO',
33883389
1 => 'PhabricatorPolicyInterface',
33893390
),
3391+
'PhabricatorMetaMTAPermanentFailureException' => 'Exception',
33903392
'PhabricatorMetaMTAReceivedMail' => 'PhabricatorMetaMTADAO',
33913393
'PhabricatorMetaMTAReceivedMailProcessingException' => 'Exception',
33923394
'PhabricatorMetaMTAReceivedMailTestCase' => 'PhabricatorTestCase',

‎src/applications/metamta/adapter/PhabricatorMailImplementationAdapter.php

+12
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,18 @@ abstract public function setIsHTML($is_html);
1818
*/
1919
abstract public function supportsMessageIDHeader();
2020

21+
22+
/**
23+
* Send the message. Generally, this means connecting to some service and
24+
* handing data to it.
25+
*
26+
* If the adapter determines that the mail will never be deliverable, it
27+
* should throw a @{class:PhabricatorMetaMTAPermanentFailureException}.
28+
*
29+
* For temporary failures, throw some other exception or return `false`.
30+
*
31+
* @return bool True on success.
32+
*/
2133
abstract public function send();
2234

2335
}

‎src/applications/metamta/adapter/PhabricatorMailImplementationTestAdapter.php

+20
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,16 @@ public function supportsMessageIDHeader() {
7979
}
8080

8181
public function send() {
82+
if (!empty($this->guts['fail-permanently'])) {
83+
throw new PhabricatorMetaMTAPermanentFailureException(
84+
'Unit Test (Permanent)');
85+
}
86+
87+
if (!empty($this->guts['fail-temporarily'])) {
88+
throw new Exception(
89+
'Unit Test (Temporary)');
90+
}
91+
8292
$this->guts['did-send'] = true;
8393
return true;
8494
}
@@ -87,4 +97,14 @@ public function getGuts() {
8797
return $this->guts;
8898
}
8999

100+
public function setFailPermanently($fail) {
101+
$this->guts['fail-permanently'] = $fail;
102+
return $this;
103+
}
104+
105+
public function setFailTemporarily($fail) {
106+
$this->guts['fail-temporarily'] = $fail;
107+
return $this;
108+
}
109+
90110
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
<?php
2+
3+
final class PhabricatorMetaMTAPermanentFailureException
4+
extends Exception {
5+
6+
}

‎src/applications/metamta/storage/PhabricatorMetaMTAMail.php

+4
Original file line numberDiff line numberDiff line change
@@ -627,6 +627,10 @@ public function sendNow(
627627
try {
628628
$ok = $mailer->send();
629629
$error = null;
630+
} catch (PhabricatorMetaMTAPermanentFailureException $ex) {
631+
$this->setStatus(self::STATUS_FAIL);
632+
$this->setMessage($ex->getMessage());
633+
return $this->save();
630634
} catch (Exception $ex) {
631635
$ok = false;
632636
$error = $ex->getMessage()."\n".$ex->getTraceAsString();

‎src/applications/metamta/storage/__tests__/PhabricatorMetaMTAMailTestCase.php

+40
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,46 @@ protected function getPhabricatorTestCaseConfiguration() {
88
);
99
}
1010

11+
public function testMailSendFailures() {
12+
$user = $this->generateNewTestUser();
13+
$phid = $user->getPHID();
14+
15+
16+
// Normally, the send should succeed.
17+
$mail = new PhabricatorMetaMTAMail();
18+
$mail->addTos(array($phid));
19+
20+
$mailer = new PhabricatorMailImplementationTestAdapter();
21+
$mail->sendNow($force = true, $mailer);
22+
$this->assertEqual(
23+
PhabricatorMetaMTAMail::STATUS_SENT,
24+
$mail->getStatus());
25+
26+
27+
// When the mailer fails temporarily, the mail should remain queued.
28+
$mail = new PhabricatorMetaMTAMail();
29+
$mail->addTos(array($phid));
30+
31+
$mailer = new PhabricatorMailImplementationTestAdapter();
32+
$mailer->setFailTemporarily(true);
33+
$mail->sendNow($force = true, $mailer);
34+
$this->assertEqual(
35+
PhabricatorMetaMTAMail::STATUS_QUEUE,
36+
$mail->getStatus());
37+
38+
39+
// When the mailer fails permanently, the mail should be failed.
40+
$mail = new PhabricatorMetaMTAMail();
41+
$mail->addTos(array($phid));
42+
43+
$mailer = new PhabricatorMailImplementationTestAdapter();
44+
$mailer->setFailPermanently(true);
45+
$mail->sendNow($force = true, $mailer);
46+
$this->assertEqual(
47+
PhabricatorMetaMTAMail::STATUS_FAIL,
48+
$mail->getStatus());
49+
}
50+
1151
public function testRecipients() {
1252
$user = $this->generateNewTestUser();
1353
$phid = $user->getPHID();

0 commit comments

Comments
 (0)
Failed to load comments.