phpmailer-bmh_rules.php ➔ bmhDSNRules()   F
last analyzed

Complexity

Conditions 143
Paths > 20000

Size

Total Lines 1069

Duplication

Lines 33
Ratio 3.09 %

Importance

Changes 0
Metric Value
cc 143
nc 40960
nop 3
dl 33
loc 1069
rs 0
c 0
b 0
f 0

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
/*~ phpmailer-bmh_rules.php
4
.---------------------------------------------------------------------------.
5
|  Software: PHPMailer-BMH (Bounce Mail Handler)                            |
6
|   Version: 6.0-dev                                                        |
7
|   Contact: [email protected]                             |
8
|      Info: http://phpmailer.codeworxtech.com                              |
9
| ------------------------------------------------------------------------- |
10
|    Author: Andy Prevost [email protected] (admin)                 |
11
| Copyright (c) 2002-2009, Andy Prevost. All Rights Reserved.               |
12
| ------------------------------------------------------------------------- |
13
|   License: Distributed under the General Public License (GPL)             |
14
|            (http://www.gnu.org/licenses/gpl.html)                         |
15
| This program is distributed in the hope that it will be useful - WITHOUT  |
16
| ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or     |
17
| FITNESS FOR A PARTICULAR PURPOSE.                                         |
18
| ------------------------------------------------------------------------- |
19
| This is a update of the original Bounce Mail Handler script               |
20
| http://sourceforge.net/projects/bmh/                                      |
21
| The script has been renamed from Bounce Mail Handler to PHPMailer-BMH     |
22
| ------------------------------------------------------------------------- |
23
| We offer a number of paid services:                                       |
24
| - Web Hosting on highly optimized fast and secure servers                 |
25
| - Technology Consulting                                                   |
26
| - Oursourcing (highly qualified programmers and graphic designers)        |
27
'---------------------------------------------------------------------------'
28
29
/**
30
 * next rule number (BODY): 0257 <br />
31
 * default category:        unrecognized: <br />
32
 * default rule no.:        0000 <br />
33
 */
34
35
global $rule_categories;
36
37
$rule_categories = [
38
    'antispam'       => ['remove' => 0, 'bounce_type' => 'blocked'],
39
    'autoreply'      => ['remove' => 0, 'bounce_type' => 'autoreply'],
40
    'concurrent'     => ['remove' => 0, 'bounce_type' => 'soft'],
41
    'content_reject' => ['remove' => 0, 'bounce_type' => 'soft'],
42
    'command_reject' => ['remove' => 1, 'bounce_type' => 'hard'],
43
    'internal_error' => ['remove' => 0, 'bounce_type' => 'temporary'],
44
    'defer'          => ['remove' => 0, 'bounce_type' => 'soft'],
45
    'delayed'        => ['remove' => 0, 'bounce_type' => 'temporary'],
46
    'dns_loop'       => ['remove' => 1, 'bounce_type' => 'hard'],
47
    'dns_unknown'    => ['remove' => 1, 'bounce_type' => 'hard'],
48
    'full'           => ['remove' => 0, 'bounce_type' => 'soft'],
49
    'inactive'       => ['remove' => 1, 'bounce_type' => 'hard'],
50
    'latin_only'     => ['remove' => 0, 'bounce_type' => 'soft'],
51
    'other'          => ['remove' => 1, 'bounce_type' => 'generic'],
52
    'oversize'       => ['remove' => 0, 'bounce_type' => 'soft'],
53
    'outofoffice'    => ['remove' => 0, 'bounce_type' => 'soft'],
54
    'unknown'        => ['remove' => 1, 'bounce_type' => 'hard'],
55
    'unrecognized'   => ['remove' => 0, 'bounce_type' => false],
56
    'user_reject'    => ['remove' => 1, 'bounce_type' => 'hard'],
57
    'warning'        => ['remove' => 0, 'bounce_type' => 'soft'],
58
];
59
60
/*
61
 * var for new line ending
62
 */
63
$bmh_newline = "<br />\n";
64
65
/**
66
 * Defined bounce parsing rules for non-standard DSN
67
 *
68
 * @param string $body       body of the email
69
 * @param string $structure  message structure
70
 * @param bool   $debug_mode show debug info. or not
71
 *
72
 * @return array $result an array include the following fields: 'email', 'bounce_type','remove','rule_no','rule_cat'
73
 *               if we could NOT detect the type of bounce, return rule_no = '0000'
74
 */
75
function bmhBodyRules($body, /** @noinspection PhpUnusedParameterInspection */ $structure, $debug_mode = false): array
0 ignored issues
show
Unused Code introduced by
The parameter $structure is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
76
{
77
    global $rule_categories;
78
    global $bmh_newline;
79
80
    // initialize the result array
81
    $result = [
82
        'email'           => '',
83
        'bounce_type'     => false,
84
        'remove'          => 0,
85
        'rule_cat'        => 'unrecognized',
86
        'rule_no'         => '0000',
87
        'status_code'     => '',
88
        'action'          => '',
89
        'diagnostic_code' => '',
90
    ];
91
92
    // ======== rules =========
93
94
    /* rule: dns_unknown
95
     * sample:
96
     *   Technical details of permanent failure:
97
     *   DNS Error: Domain name not found
98
     */
99
    if (\preg_match("/domain\s+name\s+not\s+found/i", $body, $match)) {
100
        $result['rule_cat'] = 'dns_unknown';
101
        $result['rule_no'] = '0999';
102
    } /* rule: unknown
103
   * sample:
104
   *   [email protected]
105
   *   no such address here
106
   */
107 View Code Duplication
    elseif (\preg_match("/no\s+such\s+address\s+here/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
108
        $result['rule_cat'] = 'unknown';
109
        $result['rule_no'] = '0237';
110
    } /* Gmail Bounce Error
111
   * rule: unknown
112
   * sample:
113
   *   Delivery to the following recipient failed permanently:
114
   *   [email protected]
115
   */
116
    elseif (
117
      \strpos($body, 'Technical details of permanent failure') === false // if there are technical details, try another test-case
118
      &&
119
      \preg_match("/Delivery to the following (?:recipient|recipients) failed permanently\X*?(\S+@\S+\w)/ui", $body, $match)
120
  ) {
121
        $result['rule_cat'] = 'unknown';
122
        $result['rule_no'] = '0998';
123
        $result['email'] = $match[1];
124
    } /*
125
   * rule: unknown
126
   * sample:
127
   * <[email protected]>: host mail-host[111.111.111.111]
128
    said: 550 5.1.1 This user does not exist
129
   */
130
    elseif (\preg_match("/user.+?not\s+exist/i", $body, $match)) {
131
        $result['rule_cat'] = 'unknown';
132
        $result['rule_no'] = '02361';
133
    } /* rule: unknown
134
   * sample:
135
   *   <[email protected]>:
136
   *   111.111.111.111 does not like recipient.
137
   *   Remote host said: 550 User unknown
138
   */
139 View Code Duplication
    elseif (\preg_match("/user\s+unknown/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
140
        $result['rule_cat'] = 'unknown';
141
        $result['rule_no'] = '0236';
142
    } /* rule: unknown
143
   * sample:
144
   *
145
   */
146 View Code Duplication
    elseif (\preg_match("/unknown\s+user/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
147
        $result['rule_cat'] = 'unknown';
148
        $result['rule_no'] = '0249';
149
    } /* rule: unknown
150
   * sample:
151
   *   <[email protected]>:
152
   *   Sorry, no mailbox here by that name. vpopmail (#5.1.1)
153
   */
154 View Code Duplication
    elseif (\preg_match("/no\s+mailbox/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
155
        $result['rule_cat'] = 'unknown';
156
        $result['rule_no'] = '0157';
157
    } /* rule: unknown
158
   * sample:
159
   *   [email protected]<br>
160
   *   local: Sorry, can't find user's mailbox. (#5.1.1)<br>
161
   */
162 View Code Duplication
    elseif (\preg_match("/can't\s+find.*mailbox/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
163
        $result['rule_cat'] = 'unknown';
164
        $result['rule_no'] = '0164';
165
    } /* rule: unknown
166
   * sample:
167
   *   ##########################################################
168
   *   #  This is an automated response from a mail delivery    #
169
   *   #  program.  Your message could not be delivered to      #
170
   *   #  the following address:                                #
171
   *   #                                                        #
172
   *   #      "|/usr/local/bin/mailfilt -u #dkms"               #
173
   *   #        (reason: Can't create output)                   #
174
   *   #        (expanded from: <[email protected]>)         #
175
   *   #                                                        #
176
   */
177 View Code Duplication
    elseif (\preg_match("/Can't\s+create\s+output.*<(\S+@\S+\w)>/is", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
178
        $result['rule_cat'] = 'unknown';
179
        $result['rule_no'] = '0169';
180
        $result['email'] = $match[1];
181
    } /* rule: unknown
182
   * sample:
183
   *   ????????????????:
184
   *   [email protected] : ????, ?????.
185
   */
186 View Code Duplication
    elseif (\preg_match('/=D5=CA=BA=C5=B2=BB=B4=E6=D4=DA/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
187
        $result['rule_cat'] = 'unknown';
188
        $result['rule_no'] = '0174';
189
    } /* rule: unknown
190
   * sample:
191
   *   [email protected]
192
   *   Unrouteable address
193
   */
194 View Code Duplication
    elseif (\preg_match("/Unrouteable\s+address/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
195
        $result['rule_cat'] = 'unknown';
196
        $result['rule_no'] = '0179';
197
    } /* rule: unknown
198
   * sample:
199
   *   Delivery to the following recipients failed.
200
   *   [email protected]
201
   */
202 View Code Duplication
    elseif (\preg_match("/delivery[^\n\r]+failed\S*\s+(\S+@\S+\w)\s/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
203
        $result['rule_cat'] = 'unknown';
204
        $result['rule_no'] = '0013';
205
        $result['email'] = $match[1];
206
    } /* rule: unknown
207
   * sample:
208
   *   A message that you sent could not be delivered to one or more of its
209
   *   recipients. This is a permanent error. The following address(es) failed:
210
   *
211
   *   [email protected]
212
   *   unknown local-part "xxxxx" in domain "yourdomain.com"
213
   */
214 View Code Duplication
    elseif (\preg_match("/unknown\s+local-part/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
215
        $result['rule_cat'] = 'unknown';
216
        $result['rule_no'] = '0232';
217
    } /* rule: unknown
218
   * sample:
219
   *   <[email protected]>:
220
   *   111.111.111.11 does not like recipient.
221
   *   Remote host said: 550 Invalid recipient: <[email protected]>
222
   */
223 View Code Duplication
    elseif (\preg_match("/Invalid.*(?:alias|account|recipient|address|email|mailbox|user).*<(\S+@\S+\w)>/is", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
224
        $result['rule_cat'] = 'unknown';
225
        $result['rule_no'] = '0233';
226
        $result['email'] = $match[1];
227
    } /* rule: unknown
228
   * sample:
229
   *   Sent >>> RCPT TO: <[email protected]>
230
   *   Received <<< 550 [email protected]... No such user
231
   *
232
   *   Could not deliver mail to this user.
233
   *   [email protected]
234
   *   *****************     End of message     ***************
235
   */
236 View Code Duplication
    elseif (\preg_match("/No\s+such.*(?:alias|account|recipient|address|email|mailbox|user).*<(\S+@\S+\w)>/is", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
237
        $result['rule_cat'] = 'unknown';
238
        $result['rule_no'] = '0234';
239
        $result['email'] = $match[1];
240
    } /* rule: unknown
241
   * sample:
242
   *   Diagnostic-Code: X-Notes; Recipient user name info ([email protected]) not unique.  Several matches found in Domino Directory.
243
   */
244 View Code Duplication
    elseif (\preg_match('/not unique.\s+Several matches found/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
245
        $result['rule_cat'] = 'unknown';
246
        $result['rule_no'] = '0254';
247
    } /* rule: full
248
   * sample 1:
249
   *   <[email protected]>:
250
   *   This account is over quota and unable to receive mail.
251
   *   sample 2:
252
   *   <[email protected]>:
253
   *   Warning: undefined mail delivery mode: normal (ignored).
254
   *   The users mailfolder is over the allowed quota (size). (#5.2.2)
255
   */
256 View Code Duplication
    elseif (\preg_match('/over.*quota/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
257
        $result['rule_cat'] = 'full';
258
        $result['rule_no'] = '0182';
259
    } /* rule: full
260
   * sample:
261
   *   ----- Transcript of session follows -----
262
   *   mail.local: /var/mail/2b/10/kellen.lee: Disc quota exceeded
263
   *   554 <[email protected]>... Service unavailable
264
   */
265 View Code Duplication
    elseif (\preg_match("/quota\s+exceeded.*<(\S+@\S+\w)>/is", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
266
        $result['rule_cat'] = 'full';
267
        $result['rule_no'] = '0126';
268
        $result['email'] = $match[1];
269
    } /* rule: full
270
   * sample:
271
   *   Hi. This is the qmail-send program at 263.domain.com.
272
   *   <[email protected]>:
273
   *   - User disk quota exceeded. (#4.3.0)
274
   */
275 View Code Duplication
    elseif (\preg_match("/quota\s+exceeded/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
276
        $result['rule_cat'] = 'full';
277
        $result['rule_no'] = '0158';
278
    } /* rule: full
279
   * sample:
280
   *   [email protected]
281
   *   mailbox is full (MTA-imposed quota exceeded while writing to file /mbx201/mbx011/A100/09/35/A1000935772/mail/.inbox):
282
   */
283 View Code Duplication
    elseif (\preg_match('/mailbox.*full/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
284
        $result['rule_cat'] = 'full';
285
        $result['rule_no'] = '0166';
286
    } /* rule: full
287
   * sample:
288
   *   The message to [email protected] is bounced because : Quota exceed the hard limit
289
   */
290 View Code Duplication
    elseif (\preg_match("/The message to (\S+@\S+\w)\s.*bounce.*Quota exceed/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
291
        $result['rule_cat'] = 'full';
292
        $result['rule_no'] = '0168';
293
        $result['email'] = $match[1];
294
    } /* rule: full
295
   * sample:
296
   *   Message rejected. Not enough storage space in user's mailbox to accept message.
297
   */
298 View Code Duplication
    elseif (\preg_match("/not\s+enough\s+storage\s+space/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
299
        $result['rule_cat'] = 'full';
300
        $result['rule_no'] = '0253';
301
    } /* rule: inactive
302
   * sample:
303
   *   [email protected]<br>
304
   *   553 user is inactive (eyou mta)
305
   */
306 View Code Duplication
    elseif (\preg_match('/user is inactive/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
307
        $result['rule_cat'] = 'inactive';
308
        $result['rule_no'] = '0171';
309
    } /*
310
   * <[email protected]> is restricted
311
   */
312 View Code Duplication
    elseif (\preg_match("/(\S+@\S+\w).*n? is restricted/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
313
        $result['rule_cat'] = 'inactive';
314
        $result['rule_no'] = '0201';
315
        $result['email'] = $match[1];
316
    } /* rule: inactive
317
   * sample:
318
   *   [email protected] [Inactive account]
319
   */
320 View Code Duplication
    elseif (\preg_match('/inactive account/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
321
        $result['rule_cat'] = 'inactive';
322
        $result['rule_no'] = '0181';
323
    } /*
324
   *<[email protected]>: host mx3.HOTMAIL.COM said: 550
325
   * Requested action not taken: mailbox unavailable (in reply to RCPT TO command)
326
   */
327 View Code Duplication
    elseif (\preg_match("/<(\S+@\S+\w)>.*\n.*mailbox unavailable/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
328
        $result['rule_cat'] = 'unknown';
329
        $result['rule_no'] = '124';
330
        $result['email'] = $match[1];
331
    } /*
332
   * rule: mailbox unknown;
333
   * sample:
334
   * [email protected]
335
   * 550-5.1.1 The email
336
   * account that you tried to reach does not exist. Please try 550-5.1.1
337
   * double-checking the recipient's email address for typos or 550-5.1.1
338
   * unnecessary spaces. Learn more at 550 5.1.1
339
   * http://support.google.com/mail/bin/answer.py?answer=6596 n7si4762785wiy.46
340
   * (in reply to RCPT TO command)
341
   */
342 View Code Duplication
    elseif (\preg_match("/<(\S+@\S+\w)>.*\n?.*\n?.*account that you tried to reach does not exist/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
343
        $result['rule_cat'] = 'unknown';
344
        $result['rule_no'] = '7770';
345
        $result['email'] = $match[1];
346
    } /* rule: dns_unknown
347
   * sample1:
348
   *   Delivery to the following recipient failed permanently:
349
   *
350
   *     [email protected]
351
   *
352
   *   Technical details of permanent failure:
353
   *   TEMP_FAILURE: Could not initiate SMTP conversation with any hosts:
354
   *   [b.c (1): Connection timed out]
355
   * sample2:
356
   *   Delivery to the following recipient failed permanently:
357
   *
358
   *     [email protected]
359
   *
360
   *   Technical details of permanent failure:
361
   *   TEMP_FAILURE: Could not initiate SMTP conversation with any hosts:
362
   *   [pop.b.c (1): Connection dropped]
363
   */
364 View Code Duplication
    elseif (\preg_match('/Technical details of permanent failure:\s+TEMP_FAILURE: Could not initiate SMTP conversation with any hosts/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
365
        $result['rule_cat'] = 'dns_unknown';
366
        $result['rule_no'] = '0251';
367
    } /* rule: delayed
368
   * sample:
369
   *   Delivery to the following recipient has been delayed:
370
   *
371
   *     [email protected]
372
   *
373
   *   Message will be retried for 2 more day(s)
374
   *
375
   *   Technical details of temporary failure:
376
   *   TEMP_FAILURE: Could not initiate SMTP conversation with any hosts:
377
   *   [b.c (50): Connection timed out]
378
   */
379 View Code Duplication
    elseif (\preg_match('/Technical details of temporary failure:\s+TEMP_FAILURE: Could not initiate SMTP conversation with any hosts/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
380
        $result['rule_cat'] = 'delayed';
381
        $result['rule_no'] = '0252';
382
    } /* rule: delayed
383
   * sample:
384
   *   Delivery to the following recipient has been delayed:
385
   *
386
   *     [email protected]
387
   *
388
   *   Message will be retried for 2 more day(s)
389
   *
390
   *   Technical details of temporary failure:
391
   *   TEMP_FAILURE: The recipient server did not accept our requests to connect. Learn more at ...
392
   *   [b.c (10): Connection dropped]
393
   */
394 View Code Duplication
    elseif (\preg_match('/Technical details of temporary failure:\s+TEMP_FAILURE: The recipient server did not accept our requests to connect./i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
395
        $result['rule_cat'] = 'delayed';
396
        $result['rule_no'] = '0256';
397
    } /* rule: internal_error
398
   * sample:
399
   *   <[email protected]>:
400
   *   Unable to switch to /var/vpopmail/domains/domain.com: input/output error. (#4.3.0)
401
   */
402 View Code Duplication
    elseif (\preg_match("/input\/output error/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
403
        $result['rule_cat'] = 'internal_error';
404
        $result['rule_no'] = '0172';
405
        $result['bounce_type'] = 'hard';
406
        $result['remove'] = 1;
407
    } /* rule: internal_error
408
   * sample:
409
   *   <[email protected]>:
410
   *   can not open new email file errno=13 file=/home/vpopmail/domains/fromc.com/0/domain/Maildir/tmp/1155254417.28358.mx05,S=212350
411
   */
412 View Code Duplication
    elseif (\preg_match('/can not open new email file/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
413
        $result['rule_cat'] = 'internal_error';
414
        $result['rule_no'] = '0173';
415
        $result['bounce_type'] = 'hard';
416
        $result['remove'] = 1;
417
    } /* rule: defer
418
   * sample:
419
   *   <[email protected]>:
420
   *   111.111.111.111 failed after I sent the message.
421
   *   Remote host said: 451 mta283.mail.scd.yahoo.com Resources temporarily unavailable. Please try again later [#4.16.5].
422
   */
423 View Code Duplication
    elseif (\preg_match('/Resources temporarily unavailable/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
424
        $result['rule_cat'] = 'defer';
425
        $result['rule_no'] = '0163';
426
    } /* rule: autoreply
427
   * sample:
428
   *   AutoReply message from [email protected]
429
   */
430 View Code Duplication
    elseif (\preg_match("/^AutoReply message from (\S+@\S+\w)/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
431
        $result['rule_cat'] = 'autoreply';
432
        $result['rule_no'] = '0167';
433
        $result['email'] = $match[1];
434
    } /* rule: block
435
   * sample:
436
   *   Delivery to the following recipient failed permanently:
437
   *     [email protected]
438
   *   Technical details of permanent failure:
439
   *   PERM_FAILURE: SMTP Error (state 9): 550 5.7.1 Your message (sent through 209.85.132.244) was blocked by ROTA DNSBL. If you are not a spammer, open http://www.rota.lv/DNSBL and follow instructions or call +371 7019029, or send an e-mail message from another address to [email protected] with the blocked sender e-mail name.
440
   */
441 View Code Duplication
    elseif (\preg_match("/Your message \([^)]+\) was blocked by/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
442
        $result['rule_cat'] = 'antispam';
443
        $result['rule_no'] = '0250';
444
    } /* rule: content_reject
445
   * sample:
446
   *   Failed to deliver to '<[email protected]>'
447
   *   Messages without To: fields are not accepted here
448
   */
449 View Code Duplication
    elseif (\preg_match("/Messages\s+without\s+\S+\s+fields\s+are\s+not\s+accepted\s+here/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
450
        $result['rule_cat'] = 'content_reject';
451
        $result['rule_no'] = '0248';
452
    }  /* rule: inactive
453
   * sample:
454
   *   <[email protected]>:
455
   *   This address no longer accepts mail.
456
   */
457 View Code Duplication
    elseif (\preg_match("/(?:alias|account|recipient|address|email|mailbox|user).*no\s+longer\s+accepts\s+mail/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
458
        $result['rule_cat'] = 'inactive';
459
        $result['rule_no'] = '0235';
460
    } /* rule: western chars only
461
   * sample:
462
   *   <[email protected]>:
463
   *   The user does not accept email in non-Western (non-Latin) character sets.
464
   */
465 View Code Duplication
    elseif (\preg_match("/does not accept[^\r\n]*non-Western/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
466
        $result['rule_cat'] = 'latin_only';
467
        $result['rule_no'] = '0043';
468
    } /* rule: unknown
469
   * sample:
470
   *   554 delivery error
471
   *   This user doesn't have a yahoo.com account
472
   */
473 View Code Duplication
    elseif (\preg_match("/554.*delivery error.*this user.*doesn't have.*account/is", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
474
        $result['rule_cat'] = 'unknown';
475
        $result['rule_no'] = '0044';
476
    } /* rule: unknown
477
   * sample:
478
   *   550 hotmail.com
479
   */
480 View Code Duplication
    elseif (\preg_match('/550.*Requested.*action.*not.*taken:.*mailbox.*unavailable/is', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
481
        $result['rule_cat'] = 'unknown';
482
        $result['rule_no'] = '0045';
483
    } /* rule: unknown
484
   * sample:
485
   *   550 5.1.1 aim.com
486
   */
487 View Code Duplication
    elseif (\preg_match("/550 5\.1\.1.*Recipient address rejected/is", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
488
        $result['rule_cat'] = 'unknown';
489
        $result['rule_no'] = '0046';
490
    } /* rule: unknown
491
   * sample:
492
   *   550 .* (in reply to end of DATA command)
493
   */
494 View Code Duplication
    elseif (\preg_match('/550.*in reply to end of DATA command/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
495
        $result['rule_cat'] = 'unknown';
496
        $result['rule_no'] = '0047';
497
    } /* rule: unknown
498
   * sample:
499
   *   550 .* (in reply to RCPT TO command)
500
   */
501 View Code Duplication
    elseif (\preg_match('/550.*in reply to RCPT TO command/i', $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
502
        $result['rule_cat'] = 'unknown';
503
        $result['rule_no'] = '0048';
504
    } /* rule: dns_unknown
505
   * sample:
506
   *    [email protected]:
507
   *      unrouteable mail domain "b.c"
508
   */
509 View Code Duplication
    elseif (\preg_match("/unrouteable\s+mail\s+domain/i", $body, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
510
        $result['rule_cat'] = 'dns_unknown';
511
        $result['rule_no'] = '0247';
512
    }
513
514
    if ($result['rule_no'] !== '0000' && $result['email'] === '') {
515
        $preBody = \substr($body, 0, \strpos($body, $match[0]));
516
517
        $count = \preg_match_all('/(\S+@\S+)/', $preBody, $match);
518
        if ($count) {
519
            $result['email'] = \trim($match[1][$count - 1], "'\"()<>.:; \t\r\n\0\x0B");
520
        }
521
    }
522
523
    if ($result['rule_no'] == '0000') {
524
        if ($debug_mode) {
525
            echo 'Body:' . $bmh_newline . $body . $bmh_newline;
526
            echo $bmh_newline;
527
        }
528 View Code Duplication
    } else {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
529
        if ($result['bounce_type'] === false) {
530
            $result['bounce_type'] = $rule_categories[$result['rule_cat']]['bounce_type'];
531
            $result['remove'] = $rule_categories[$result['rule_cat']]['remove'];
532
        }
533
    }
534
535
    return $result;
536
}
537
538
/**
539
 * Defined bounce parsing rules for standard DSN (Delivery Status Notification)
540
 *
541
 * @param string $dsn_msg    human-readable explanation
542
 * @param string $dsn_report delivery-status report
543
 * @param bool   $debug_mode show debug info. or not
544
 *
545
 * @return array $result an array include the following fields: 'email', 'bounce_type','remove','rule_no','rule_cat'
546
 *               if we could NOT detect the type of bounce, return rule_no = '0000'
547
 */
548
function bmhDSNRules($dsn_msg, $dsn_report, $debug_mode = false): array
549
{
550
    global $rule_categories;
551
    global $bmh_newline;
552
553
    // initialize the result array
554
    $result = [
555
        'email'           => '',
556
        'bounce_type'     => false,
557
        'remove'          => 0,
558
        'rule_cat'        => 'unrecognized',
559
        'rule_no'         => '0000',
560
        'status_code'     => '',
561
        'action'          => '',
562
        'diagnostic_code' => '',
563
    ];
564
    $action = false;
565
    $status_code = false;
566
    $diag_code = false;
567
568
    // ======= parse $dsn_report ======
569
    // get the recipient email
570
    if (\preg_match('/Original-Recipient: rfc822;(.*)/i', $dsn_report, $match)) {
571
        $email = \trim($match[1], "<> \t\r\n\0\x0B");
572
        /** @noinspection PhpUsageOfSilenceOperatorInspection */
573
        $email_arr = @\imap_rfc822_parse_adrlist($email, 'default.domain.name');
574 View Code Duplication
        if (isset($email_arr[0]->host) && $email_arr[0]->host != '.SYNTAX-ERROR.' && $email_arr[0]->host != 'default.domain.name') {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
575
            $result['email'] = $email_arr[0]->mailbox . '@' . $email_arr[0]->host;
576
        }
577
    } elseif (\preg_match('/Final-Recipient: rfc822;(.*)/i', $dsn_report, $match)) {
578
        $email = \trim($match[1], "<> \t\r\n\0\x0B");
579
        /** @noinspection PhpUsageOfSilenceOperatorInspection */
580
        $email_arr = @\imap_rfc822_parse_adrlist($email, 'default.domain.name');
581 View Code Duplication
        if (isset($email_arr[0]->host) && $email_arr[0]->host != '.SYNTAX-ERROR.' && $email_arr[0]->host != 'default.domain.name') {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
582
            $result['email'] = $email_arr[0]->mailbox . '@' . $email_arr[0]->host;
583
        }
584
    }
585
586 View Code Duplication
    if (\preg_match('/Action: (.+)/i', $dsn_report, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
587
        $action = \strtolower(\trim($match[1]));
588
        $result['action'] = $action;
589
    }
590
591 View Code Duplication
    if (\preg_match("/Status: ([0-9\.]+)/i", $dsn_report, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
592
        $status_code = $match[1];
593
        $result['status_code'] = $status_code;
594
    }
595
596
    // Could be multi-line , if the new line is beginning with SPACE or HTAB
597
    if (\preg_match("/Diagnostic-Code:((?:[^\n]|\n[\t ])+)(?:\n[^\t ]|$)/i", $dsn_report, $match)) {
598
        $diag_code = $match[1];
599
    }
600
601
    // No Diagnostic-Code in email, use dsn message
602
    if (empty($diag_code)) {
603
        $diag_code = $dsn_msg;
604
    }
605
606
    $result['diagnostic_code'] = $diag_code;
607
608
    // ======= rules ======
609
610
    if (empty($result['email'])) {
611
        /* email address is empty
612
         * rule: full
613
         * sample:   DSN Message only
614
         * User quota exceeded: SMTP <[email protected]>
615
         */
616 View Code Duplication
        if (\preg_match("/quota exceed.*<(\S+@\S+\w)>/is", $dsn_msg, $match)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
617
            $result['rule_cat'] = 'full';
618
            $result['rule_no'] = '0161';
619
            $result['email'] = $match[1];
620
        }
621
    } else {
622
        /* action could be one of them as RFC:1894
623
         * "failed" / "delayed" / "delivered" / "relayed" / "expanded"
624
         */
625
        switch ($action) {
626
      case 'failed':
627
        /* rule: full
628
         * sample:
629
         *   Diagnostic-Code: X-Postfix; me.domain.com platform: said: 552 5.2.2 Over
630
         *     quota (in reply to RCPT TO command)
631
         */
632
        if (\preg_match('/over.*quota/is', $diag_code)) {
633
            $result['rule_cat'] = 'full';
634
            $result['rule_no'] = '0105';
635
        } /* rule: full
636
         * sample:
637
         *   Diagnostic-Code: SMTP; 552 Requested mailbox exceeds quota.
638
         */
639
        elseif (\preg_match('/exceed.*quota/is', $diag_code)) {
640
            $result['rule_cat'] = 'full';
641
            $result['rule_no'] = '0129';
642
        } /* rule: full
643
         * sample 1:
644
         *   Diagnostic-Code: smtp;552 5.2.2 This message is larger than the current system limit or the recipient's mailbox is full. Create a shorter message body or remove attachments and try sending it again.
645
         * sample 2:
646
         *   Diagnostic-Code: X-Postfix; host mta5.us4.domain.com.int[111.111.111.111] said:
647
         *     552 recipient storage full, try again later (in reply to RCPT TO command)
648
         * sample 3:
649
         *   Diagnostic-Code: X-HERMES; host 127.0.0.1[127.0.0.1] said: 551 bounce as<the
650
         *     destination mailbox <[email protected]> is full> queue as
651
         *     [email protected] (in reply to end of
652
         *     DATA command)
653
         */
654
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*full/is', $diag_code)) {
655
            $result['rule_cat'] = 'full';
656
            $result['rule_no'] = '0145';
657
        } /* rule: full
658
         * sample:
659
         *   Diagnostic-Code: SMTP; 452 Insufficient system storage
660
         */
661
        elseif (\preg_match('/Insufficient system storage/i', $diag_code)) {
662
            $result['rule_cat'] = 'full';
663
            $result['rule_no'] = '0134';
664
        } /* rule: full
665
         * sample:
666
         *   Diagnostic-Code: SMTP; 422 Benutzer hat zuviele Mails auf dem Server
667
         */
668
        elseif (\preg_match('/Benutzer hat zuviele Mails auf dem Server/i', $diag_code)) {
669
            $result['rule_cat'] = 'full';
670
            $result['rule_no'] = '0998';
671
        } /* rule: full
672
         * sample:
673
         *   Diagnostic-Code: SMTP; 422 exceeded storage allocation
674
         */
675
        elseif (\preg_match('/exceeded storage allocation/i', $diag_code)) {
676
            $result['rule_cat'] = 'full';
677
            $result['rule_no'] = '0997';
678
        } /* rule: full
679
         * sample:
680
         *   Diagnostic-Code: SMTP; 422 Mailbox quota usage exceeded
681
         */
682
        elseif (\preg_match('/Mailbox quota usage exceeded/i', $diag_code)) {
683
            $result['rule_cat'] = 'full';
684
            $result['rule_no'] = '0996';
685
        } /* rule: full
686
         * sample:
687
         *   Diagnostic-Code: SMTP; 422 User has exhausted allowed storage space
688
         */
689
        elseif (\preg_match('/User has exhausted allowed storage space/i', $diag_code)) {
690
            $result['rule_cat'] = 'full';
691
            $result['rule_no'] = '0995';
692
        } /* rule: full
693
         * sample:
694
         *   Diagnostic-Code: SMTP; 422 User mailbox exceeds allowed size
695
         */
696
        elseif (\preg_match('/User mailbox exceeds allowed size/i', $diag_code)) {
697
            $result['rule_cat'] = 'full';
698
            $result['rule_no'] = '0994';
699
        } /* rule: full
700
         * sample:
701
         *   Diagnostic-Code: smpt; 552 Account(s) <[email protected]> does not have enough space
702
         */
703
        elseif (\preg_match("/not.*enough\s+space/i", $diag_code)) {
704
            $result['rule_cat'] = 'full';
705
            $result['rule_no'] = '0246';
706
        } /* rule: full
707
         * sample 1:
708
         *   Diagnostic-Code: X-Postfix; cannot append message to destination file
709
         *     /var/mail/dale.me89g: error writing message: File too large
710
         * sample 2:
711
         *   Diagnostic-Code: X-Postfix; cannot access mailbox /var/spool/mail/b8843022 for
712
         *     user xxxxx. error writing message: File too large
713
         */
714
        elseif (\preg_match('/File too large/i', $diag_code)) {
715
            $result['rule_cat'] = 'full';
716
            $result['rule_no'] = '0192';
717
        } /* rule: oversize
718
         * sample:
719
         *   Diagnostic-Code: smtp;552 5.2.2 This message is larger than the current system limit or the recipient's mailbox is full. Create a shorter message body or remove attachments and try sending it again.
720
         */
721
        elseif (\preg_match('/larger than.*limit/is', $diag_code)) {
722
            $result['rule_cat'] = 'oversize';
723
            $result['rule_no'] = '0146';
724
        } /* rule: unknown
725
         * sample:
726
         *   Diagnostic-Code: X-Notes; User xxxxx ([email protected]) not listed in public Name & Address Book
727
         */
728
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user)(.*)not(.*)list/is', $diag_code)) {
729
            $result['rule_cat'] = 'unknown';
730
            $result['rule_no'] = '0103';
731
        } /* rule: unknown
732
         * sample:
733
         *   Diagnostic-Code: smtp; 450 user path no exist
734
         */
735
        elseif (\preg_match('/user path no exist/i', $diag_code)) {
736
            $result['rule_cat'] = 'unknown';
737
            $result['rule_no'] = '0106';
738
        } /* rule: unknown
739
         * sample 1:
740
         *   Diagnostic-Code: SMTP; 550 Relaying denied.
741
         * sample 2:
742
         *   Diagnostic-Code: SMTP; 554 <[email protected]>: Relay access denied
743
         * sample 3:
744
         *   Diagnostic-Code: SMTP; 550 relaying to <[email protected]> prohibited by administrator
745
         */
746
        elseif (\preg_match('/Relay.*(?:denied|prohibited)/is', $diag_code)) {
747
            $result['rule_cat'] = 'unknown';
748
            $result['rule_no'] = '0108';
749
        } /* rule: unknown
750
         * sample:
751
         *   Diagnostic-Code: SMTP; 554 qq Sorry, no valid recipients (#5.1.3)
752
         */
753
        elseif (\preg_match('/no.*valid.*(?:alias|account|recipient|address|email|mailbox|user)/is', $diag_code)) {
754
            $result['rule_cat'] = 'unknown';
755
            $result['rule_no'] = '0185';
756
        } /* rule: unknown
757
         * sample 1:
758
         *   Diagnostic-Code: SMTP; 550 «Dªk¦a§} - invalid address (#5.5.0)
759
         * sample 2:
760
         *   Diagnostic-Code: SMTP; 550 Invalid recipient: <[email protected]>
761
         * sample 3:
762
         *   Diagnostic-Code: SMTP; 550 <[email protected]>: Invalid User
763
         */
764
        elseif (\preg_match('/Invalid.*(?:alias|account|recipient|address|email|mailbox|user)/is', $diag_code)) {
765
            $result['rule_cat'] = 'unknown';
766
            $result['rule_no'] = '0111';
767
        } /* rule: unknown
768
         * sample:
769
         *   Diagnostic-Code: SMTP; 554 delivery error: dd Sorry your message to [email protected] cannot be delivered. This account has been disabled or discontinued [#102]. - mta173.mail.tpe.domain.com
770
         */
771
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*(?:disabled|discontinued)/is', $diag_code)) {
772
            $result['rule_cat'] = 'unknown';
773
            $result['rule_no'] = '0114';
774
        } /* rule: unknown
775
         * sample:
776
         *   Diagnostic-Code: SMTP; 554 delivery error: dd This user doesn't have a domain.com account ([email protected]) [0] - mta134.mail.tpe.domain.com
777
         */
778
        elseif (\preg_match("/user doesn't have.*account/is", $diag_code)) {
779
            $result['rule_cat'] = 'unknown';
780
            $result['rule_no'] = '0127';
781
        } /* rule: unknown
782
         * sample:
783
         *   Diagnostic-Code: SMTP; 550 5.1.1 unknown or illegal alias: [email protected]
784
         */
785
        elseif (\preg_match('/(?:unknown|illegal).*(?:alias|account|recipient|address|email|mailbox|user)/is', $diag_code)) {
786
            $result['rule_cat'] = 'unknown';
787
            $result['rule_no'] = '0128';
788
        } /* rule: unknown
789
         * sample 1:
790
         *   Diagnostic-Code: SMTP; 450 mailbox unavailable.
791
         * sample 2:
792
         *   Diagnostic-Code: SMTP; 550 5.7.1 Requested action not taken: mailbox not available
793
         */
794
        elseif (\preg_match("/(?:alias|account|recipient|address|email|mailbox|user).*(?:un|not\s+)available/is", $diag_code)) {
795
            $result['rule_cat'] = 'unknown';
796
            $result['rule_no'] = '0122';
797
        } /* rule: unknown
798
         * sample:
799
         *   Diagnostic-Code: SMTP; 553 sorry, no mailbox here by that name (#5.7.1)
800
         */
801
        elseif (\preg_match('/no (?:alias|account|recipient|address|email|mailbox|user)/i', $diag_code)) {
802
            $result['rule_cat'] = 'unknown';
803
            $result['rule_no'] = '0123';
804
        } /* rule: unknown
805
         * sample 1:
806
         *   Diagnostic-Code: SMTP; 550 User ([email protected]) unknown.
807
         * sample 2:
808
         *   Diagnostic-Code: SMTP; 553 5.3.0 <[email protected]>... Addressee unknown, relay=[111.111.111.000]
809
         */
810
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*unknown/is', $diag_code)) {
811
            $result['rule_cat'] = 'unknown';
812
            $result['rule_no'] = '0125';
813
        } /* rule: unknown
814
         * sample 1:
815
         *   Diagnostic-Code: SMTP; 550 user disabled
816
         * sample 2:
817
         *   Diagnostic-Code: SMTP; 452 4.2.1 mailbox temporarily disabled: [email protected]
818
         */
819
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*disabled/is', $diag_code)) {
820
            $result['rule_cat'] = 'unknown';
821
            $result['rule_no'] = '0133';
822
        } /* rule: unknown
823
         * sample:
824
         *   Diagnostic-Code: SMTP; 550 <[email protected]>: Recipient address rejected: No such user ([email protected])
825
         */
826
        elseif (\preg_match('/No such (?:alias|account|recipient|address|email|mailbox|user)/i', $diag_code)) {
827
            $result['rule_cat'] = 'unknown';
828
            $result['rule_no'] = '0143';
829
        } /* rule: unknown
830
         * sample 1:
831
         *   Diagnostic-Code: SMTP; 550 MAILBOX NOT FOUND
832
         * sample 2:
833
         *   Diagnostic-Code: SMTP; 550 Mailbox ( [email protected] ) not found or inactivated
834
         */
835
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*NOT FOUND/is', $diag_code)) {
836
            $result['rule_cat'] = 'unknown';
837
            $result['rule_no'] = '0136';
838
        } /* rule: unknown
839
         * sample:
840
         *    Diagnostic-Code: X-Postfix; host m2w-in1.domain.com[111.111.111.000] said: 551
841
         *    <[email protected]> is a deactivated mailbox (in reply to RCPT TO
842
         *    command)
843
         */
844
        elseif (\preg_match('/deactivated (?:alias|account|recipient|address|email|mailbox|user)/i', $diag_code)) {
845
            $result['rule_cat'] = 'unknown';
846
            $result['rule_no'] = '0138';
847
        } /* rule: unknown
848
         * sample:
849
         *   Diagnostic-Code: SMTP; 550 <[email protected]> recipient rejected
850
         *   ...
851
         *   <<< 550 <[email protected]> recipient rejected
852
         *   550 5.1.1 [email protected]... User unknown
853
         */
854
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*reject/is', $diag_code)) {
855
            $result['rule_cat'] = 'unknown';
856
            $result['rule_no'] = '0148';
857
        } /* rule: unknown
858
         * sample:
859
         *   Diagnostic-Code: smtp; 5.x.0 - Message bounced by administrator  (delivery attempts: 0)
860
         */
861
        elseif (\preg_match('/bounce.*administrator/is', $diag_code)) {
862
            $result['rule_cat'] = 'unknown';
863
            $result['rule_no'] = '0151';
864
        } /* rule: unknown
865
         * sample:
866
         *   Diagnostic-Code: SMTP; 550 <maxqin> is now disabled with MTA service.
867
         */
868
        elseif (\preg_match('/<.*>.*disabled/is', $diag_code)) {
869
            $result['rule_cat'] = 'unknown';
870
            $result['rule_no'] = '0152';
871
        } /* rule: unknown
872
         * sample:
873
         *   Diagnostic-Code: SMTP; 551 not our customer
874
         */
875
        elseif (\preg_match('/not our customer/i', $diag_code)) {
876
            $result['rule_cat'] = 'unknown';
877
            $result['rule_no'] = '0154';
878
        } /* rule: unknown
879
         * sample:
880
         *   Diagnostic-Code: smtp; 5.1.0 - Unknown address error 540-'Error: Wrong recipients' (delivery attempts: 0)
881
         */
882
        elseif (\preg_match('/Wrong (?:alias|account|recipient|address|email|mailbox|user)/i', $diag_code)) {
883
            $result['rule_cat'] = 'unknown';
884
            $result['rule_no'] = '0159';
885
        } /* rule: unknown
886
         * sample:
887
         *   Diagnostic-Code: smtp; 5.1.0 - Unknown address error 540-'Error: Wrong recipients' (delivery attempts: 0)
888
         * sample 2:
889
         *   Diagnostic-Code: SMTP; 501 #5.1.1 bad address [email protected]
890
         */
891
        elseif (\preg_match('/(?:unknown|bad).*(?:alias|account|recipient|address|email|mailbox|user)/is', $diag_code)) {
892
            $result['rule_cat'] = 'unknown';
893
            $result['rule_no'] = '0160';
894
        } /* rule: unknown
895
         * sample:
896
         *   Status: 5.1.1 (bad destination mailbox address)
897
         */
898
        elseif (\preg_match('/(?:unknown|bad).*(?:alias|account|recipient|address|email|mailbox|user)/is', $status_code)) {
899
            $result['rule_cat'] = 'unknown';
900
            $result['rule_no'] = '01601';
901
        } /* rule: unknown
902
         * sample:
903
         *   Diagnostic-Code: SMTP; 550 Command RCPT User <[email protected]> not OK
904
         */
905
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*not OK/is', $diag_code)) {
906
            $result['rule_cat'] = 'unknown';
907
            $result['rule_no'] = '0186';
908
        } /* rule: unknown
909
         * sample:
910
         *   Diagnostic-Code: SMTP; 550 5.7.1 Access-Denied-XM.SSR-001
911
         */
912
        elseif (\preg_match('/Access.*Denied/is', $diag_code)) {
913
            $result['rule_cat'] = 'unknown';
914
            $result['rule_no'] = '0189';
915
        } /* rule: unknown
916
         * sample:
917
         *   Diagnostic-Code: SMTP; 550 5.1.1 <[email protected]>... email address lookup in domain map failed
918
         */
919
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*lookup.*fail/is', $diag_code)) {
920
            $result['rule_cat'] = 'unknown';
921
            $result['rule_no'] = '0195';
922
        } /* rule: unknown
923
         * sample:
924
         *   Diagnostic-Code: SMTP; 550 User not a member of domain: <[email protected]>
925
         */
926
        elseif (\preg_match('/(?:recipient|address|email|mailbox|user).*not.*member of domain/is', $diag_code)) {
927
            $result['rule_cat'] = 'unknown';
928
            $result['rule_no'] = '0198';
929
        } /* rule: unknown
930
         * sample:
931
         *   Diagnostic-Code: SMTP; 550-"The recipient cannot be verified.  Please check all recipients of this
932
         */
933
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*cannot be verified/is', $diag_code)) {
934
            $result['rule_cat'] = 'unknown';
935
            $result['rule_no'] = '0202';
936
        } /* rule: unknown
937
         * sample:
938
         *   Diagnostic-Code: SMTP; 550 Unable to relay for [email protected]
939
         */
940
        elseif (\preg_match('/Unable to relay/i', $diag_code)) {
941
            $result['rule_cat'] = 'unknown';
942
            $result['rule_no'] = '0203';
943
        } /* rule: unknown
944
         * sample 1:
945
         *   Diagnostic-Code: SMTP; 550 [email protected]:user not exist
946
         * sample 2:
947
         *   Diagnostic-Code: SMTP; 550 sorry, that recipient doesn't exist (#5.7.1)
948
         */
949
        elseif (\preg_match("/(?:alias|account|recipient|address|email|mailbox|user).*(?:n't|not) exist/is", $diag_code)) {
950
            $result['rule_cat'] = 'unknown';
951
            $result['rule_no'] = '0205';
952
        } /* rule: unknown
953
         * sample:
954
         *   Diagnostic-Code: SMTP; 550-I'm sorry but [email protected] does not have an account here. I will not
955
         */
956
        elseif (\preg_match('/not have an account/i', $diag_code)) {
957
            $result['rule_cat'] = 'unknown';
958
            $result['rule_no'] = '0207';
959
        } /* rule: unknown
960
         * sample:
961
         *   Diagnostic-Code: SMTP; 550 This account is not [email protected]
962
         */
963
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*is not allowed/is', $diag_code)) {
964
            $result['rule_cat'] = 'unknown';
965
            $result['rule_no'] = '0220';
966
        } /* rule: unknown
967
         * sample:
968
         *   Diagnostic-Code: X-Notes; Recipient user name info ([email protected]) not unique.  Several matches found in Domino Directory.
969
         */
970
        elseif (\preg_match('/not unique.\s+Several matches found/i', $diag_code)) {
971
            $result['rule_cat'] = 'unknown';
972
            $result['rule_no'] = '0255';
973
        } /* rule: inactive
974
         * sample:
975
         *   Diagnostic-Code: SMTP; 550 <[email protected]>: inactive user
976
         */
977
        elseif (\preg_match('/inactive.*(?:alias|account|recipient|address|email|mailbox|user)/is', $diag_code)) {
978
            $result['rule_cat'] = 'inactive';
979
            $result['rule_no'] = '0135';
980
        } /* rule: inactive
981
         * sample:
982
         *   Diagnostic-Code: SMTP; 550 [email protected] Account Inactive
983
         */
984
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*Inactive/is', $diag_code)) {
985
            $result['rule_cat'] = 'inactive';
986
            $result['rule_no'] = '0155';
987
        } /* rule: inactive
988
         * sample:
989
         *   Diagnostic-Code: SMTP; 550 <[email protected]>: Recipient address rejected: Account closed due to inactivity. No forwarding information is available.
990
         */
991
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user) closed due to inactivity/i', $diag_code)) {
992
            $result['rule_cat'] = 'inactive';
993
            $result['rule_no'] = '0170';
994
        } /* rule: inactive
995
         * sample:
996
         *   Diagnostic-Code: SMTP; 550 <[email protected]>... User account not activated
997
         */
998
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user) not activated/i', $diag_code)) {
999
            $result['rule_cat'] = 'inactive';
1000
            $result['rule_no'] = '0177';
1001
        } /* rule: inactive
1002
         * sample 1:
1003
         *   Diagnostic-Code: SMTP; 550 User suspended
1004
         * sample 2:
1005
         *   Diagnostic-Code: SMTP; 550 account expired
1006
         */
1007
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*(?:suspend|expire)/is', $diag_code)) {
1008
            $result['rule_cat'] = 'inactive';
1009
            $result['rule_no'] = '0183';
1010
        } /* rule: inactive
1011
         * sample:
1012
         *   Diagnostic-Code: SMTP; 553 5.3.0 <[email protected]>... Recipient address no longer exists
1013
         */
1014
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*no longer exist/is', $diag_code)) {
1015
            $result['rule_cat'] = 'inactive';
1016
            $result['rule_no'] = '0184';
1017
        } /* rule: inactive
1018
         * sample:
1019
         *   Diagnostic-Code: SMTP; 553 VS10-RT Possible forgery or deactivated due to abuse (#5.1.1) 111.111.111.211
1020
         */
1021
        elseif (\preg_match('/(?:forgery|abuse)/i', $diag_code)) {
1022
            $result['rule_cat'] = 'inactive';
1023
            $result['rule_no'] = '0196';
1024
        } /* rule: inactive
1025
         * sample:
1026
         *   Diagnostic-Code: SMTP; 553 mailbox [email protected] is restricted
1027
         */
1028
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*restrict/is', $diag_code)) {
1029
            $result['rule_cat'] = 'inactive';
1030
            $result['rule_no'] = '0209';
1031
        } /* rule: inactive
1032
         * sample:
1033
         *   Diagnostic-Code: SMTP; 550 <[email protected]>: User status is locked.
1034
         */
1035
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*locked/is', $diag_code)) {
1036
            $result['rule_cat'] = 'inactive';
1037
            $result['rule_no'] = '0228';
1038
        } /* rule: user_reject
1039
         * sample:
1040
         *   Diagnostic-Code: SMTP; 553 User refused to receive this mail.
1041
         */
1042
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user) refused/i', $diag_code)) {
1043
            $result['rule_cat'] = 'user_reject';
1044
            $result['rule_no'] = '0156';
1045
        } /* rule: user_reject
1046
         * sample:
1047
         *   Diagnostic-Code: SMTP; 501 [email protected] Sender email is not in my domain
1048
         */
1049
        elseif (\preg_match('/sender.*not/is', $diag_code)) {
1050
            $result['rule_cat'] = 'user_reject';
1051
            $result['rule_no'] = '0206';
1052
        } /* rule: command_reject
1053
         * sample:
1054
         *   Diagnostic-Code: SMTP; 554 Message refused
1055
         */
1056
        elseif (\preg_match('/Message refused/i', $diag_code)) {
1057
            $result['rule_cat'] = 'command_reject';
1058
            $result['rule_no'] = '0175';
1059
        } /* rule: command_reject
1060
         * sample:
1061
         *   Diagnostic-Code: SMTP; 550 5.0.0 <[email protected]>... No permit
1062
         */
1063
        elseif (\preg_match('/No permit/i', $diag_code)) {
1064
            $result['rule_cat'] = 'command_reject';
1065
            $result['rule_no'] = '0190';
1066
        } /* rule: command_reject
1067
         * sample:
1068
         *   Diagnostic-Code: SMTP; 553 sorry, that domain isn't in my list of allowed rcpthosts (#5.5.3 - chkuser)
1069
         */
1070
        elseif (\preg_match("/domain isn't in.*allowed rcpthost/is", $diag_code)) {
1071
            $result['rule_cat'] = 'command_reject';
1072
            $result['rule_no'] = '0191';
1073
        } /* rule: command_reject
1074
         * sample:
1075
         *   Diagnostic-Code: SMTP; 553 AUTH FAILED - [email protected]
1076
         */
1077
        elseif (\preg_match('/AUTH FAILED/i', $diag_code)) {
1078
            $result['rule_cat'] = 'command_reject';
1079
            $result['rule_no'] = '0197';
1080
        } /* rule: command_reject
1081
         * sample 1:
1082
         *   Diagnostic-Code: SMTP; 550 relay not permitted
1083
         * sample 2:
1084
         *   Diagnostic-Code: SMTP; 530 5.7.1 Relaying not allowed: [email protected]
1085
         */
1086
        elseif (\preg_match('/relay.*not.*(?:permit|allow)/is', $diag_code)) {
1087
            $result['rule_cat'] = 'command_reject';
1088
            $result['rule_no'] = '0241';
1089
        } /* rule: command_reject
1090
         * sample:
1091
         *   Diagnostic-Code: SMTP; 550 not local host domain.com, not a gateway
1092
         */
1093
        elseif (\preg_match('/not local host/i', $diag_code)) {
1094
            $result['rule_cat'] = 'command_reject';
1095
            $result['rule_no'] = '0204';
1096
        } /* rule: command_reject
1097
         * sample:
1098
         *   Diagnostic-Code: SMTP; 500 Unauthorized relay msg rejected
1099
         */
1100
        elseif (\preg_match('/Unauthorized relay/i', $diag_code)) {
1101
            $result['rule_cat'] = 'command_reject';
1102
            $result['rule_no'] = '0215';
1103
        } /* rule: command_reject
1104
         * sample:
1105
         *   Diagnostic-Code: SMTP; 554 Transaction failed
1106
         */
1107
        elseif (\preg_match('/Transaction.*fail/is', $diag_code)) {
1108
            $result['rule_cat'] = 'command_reject';
1109
            $result['rule_no'] = '0221';
1110
        } /* rule: command_reject
1111
         * sample:
1112
         *   Diagnostic-Code: smtp;554 5.5.2 Invalid data in message
1113
         */
1114
        elseif (\preg_match('/Invalid data/i', $diag_code)) {
1115
            $result['rule_cat'] = 'command_reject';
1116
            $result['rule_no'] = '0223';
1117
        } /* rule: command_reject
1118
         * sample:
1119
         *   Diagnostic-Code: SMTP; 550 Local user only or Authentication mechanism
1120
         */
1121
        elseif (\preg_match('/Local user only/i', $diag_code)) {
1122
            $result['rule_cat'] = 'command_reject';
1123
            $result['rule_no'] = '0224';
1124
        } /* rule: command_reject
1125
         * sample:
1126
         *   Diagnostic-Code: SMTP; 550-ds176.domain.com [111.111.111.211] is currently not permitted to
1127
         *   relay through this server. Perhaps you have not logged into the pop/imap
1128
         *   server in the last 30 minutes or do not have SMTP Authentication turned on
1129
         *   in your email client.
1130
         */
1131
        elseif (\preg_match('/not.*permit.*to/is', $diag_code)) {
1132
            $result['rule_cat'] = 'command_reject';
1133
            $result['rule_no'] = '0225';
1134
        } /* rule: content_reject
1135
         * sample:
1136
         *   Diagnostic-Code: SMTP; 550 Content reject. FAAAANsG60M9BmDT.1
1137
         */
1138
        elseif (\preg_match('/Content reject/i', $diag_code)) {
1139
            $result['rule_cat'] = 'content_reject';
1140
            $result['rule_no'] = '0165';
1141
        } /* rule: content_reject
1142
         * sample:
1143
         *   Diagnostic-Code: SMTP; 552 MessageWall: MIME/REJECT: Invalid structure
1144
         */
1145
        elseif (\preg_match("/MIME\/REJECT/i", $diag_code)) {
1146
            $result['rule_cat'] = 'content_reject';
1147
            $result['rule_no'] = '0212';
1148
        } /* rule: content_reject
1149
         * sample:
1150
         *   Diagnostic-Code: smtp; 554 5.6.0 Message with invalid header rejected, id=13462-01 - MIME error: error: UnexpectedBound: part didn't end with expected boundary [in multipart message]; EOSToken: EOF; EOSType: EOF
1151
         */
1152
        elseif (\preg_match('/MIME error/i', $diag_code)) {
1153
            $result['rule_cat'] = 'content_reject';
1154
            $result['rule_no'] = '0217';
1155
        } /* rule: content_reject
1156
         * sample:
1157
         *   Diagnostic-Code: SMTP; 553 Mail data refused by AISP, rule [169648].
1158
         */
1159
        elseif (\preg_match('/Mail data refused.*AISP/is', $diag_code)) {
1160
            $result['rule_cat'] = 'content_reject';
1161
            $result['rule_no'] = '0218';
1162
        } /* rule: dns_unknown
1163
         * sample:
1164
         *   Diagnostic-Code: SMTP; 550 Host unknown
1165
         */
1166
        elseif (\preg_match('/Host unknown/i', $diag_code)) {
1167
            $result['rule_cat'] = 'dns_unknown';
1168
            $result['rule_no'] = '0130';
1169
        } /* rule: dns_unknown
1170
         * sample:
1171
         *   Diagnostic-Code: SMTP; 553 Specified domain is not allowed.
1172
         */
1173
        elseif (\preg_match('/Specified domain.*not.*allow/is', $diag_code)) {
1174
            $result['rule_cat'] = 'dns_unknown';
1175
            $result['rule_no'] = '0180';
1176
        } /* rule: dns_unknown
1177
         * sample:
1178
         *   Diagnostic-Code: X-Postfix; delivery temporarily suspended: connect to
1179
         *   111.111.11.112[111.111.11.112]: No route to host
1180
         */
1181
        elseif (\preg_match('/No route to host/i', $diag_code)) {
1182
            $result['rule_cat'] = 'dns_unknown';
1183
            $result['rule_no'] = '0188';
1184
        } /* rule: dns_unknown
1185
         * sample:
1186
         *   Diagnostic-Code: SMTP; 550 unrouteable address
1187
         */
1188
        elseif (\preg_match('/unrouteable address/i', $diag_code)) {
1189
            $result['rule_cat'] = 'dns_unknown';
1190
            $result['rule_no'] = '0208';
1191
        } /* rule: dns_unknown
1192
         * sample:
1193
         *   Diagnostic-Code: X-Postfix; Host or domain name not found. Name service error
1194
         *     for name=aaaaaaaaaaa type=A: Host not found
1195
         */
1196
        elseif (\preg_match('/Host or domain name not found/i', $diag_code)) {
1197
            $result['rule_cat'] = 'dns_unknown';
1198
            $result['rule_no'] = '0238';
1199
        } /* rule: dns_loop
1200
         * sample:
1201
         *   Diagnostic-Code: X-Postfix; mail for mta.example.com loops back to myself
1202
         */
1203
        elseif (\preg_match('/loops back to myself/i', $diag_code)) {
1204
            $result['rule_cat'] = 'dns_loop';
1205
            $result['rule_no'] = '0245';
1206
        } /* rule: defer
1207
         * sample:
1208
         *   Diagnostic-Code: SMTP; 451 System(u) busy, try again later.
1209
         */
1210
        elseif (\preg_match('/System.*busy/is', $diag_code)) {
1211
            $result['rule_cat'] = 'defer';
1212
            $result['rule_no'] = '0112';
1213
        } /* rule: defer
1214
         * sample:
1215
         *   Diagnostic-Code: SMTP; 451 mta172.mail.tpe.domain.com Resources temporarily unavailable. Please try again later.  [#4.16.4:70].
1216
         */
1217
        elseif (\preg_match('/Resources temporarily unavailable/i', $diag_code)) {
1218
            $result['rule_cat'] = 'defer';
1219
            $result['rule_no'] = '0116';
1220
        } /* rule: antispam, deny ip
1221
         * sample:
1222
         *   Diagnostic-Code: SMTP; 554 sender is rejected: 0,mx20,wKjR5bDrnoM2yNtEZVAkBg==.32467S2
1223
         */
1224
        elseif (\preg_match('/sender is rejected/i', $diag_code)) {
1225
            $result['rule_cat'] = 'antispam';
1226
            $result['rule_no'] = '0101';
1227
        } /* rule: antispam, deny ip
1228
         * sample:
1229
         *   Diagnostic-Code: SMTP; 554 <unknown[111.111.111.000]>: Client host rejected: Access denied
1230
         */
1231
        elseif (\preg_match('/Client host rejected/i', $diag_code)) {
1232
            $result['rule_cat'] = 'antispam';
1233
            $result['rule_no'] = '0102';
1234
        } /* rule: antispam, mismatch ip
1235
         * sample:
1236
         *   Diagnostic-Code: SMTP; 554 Connection refused(mx). MAIL FROM [[email protected]] mismatches client IP [111.111.111.000].
1237
         */
1238
        elseif (\preg_match('/MAIL FROM(.*)mismatches client IP/is', $diag_code)) {
1239
            $result['rule_cat'] = 'antispam';
1240
            $result['rule_no'] = '0104';
1241
        } /* rule: antispam, deny ip
1242
         * sample:
1243
         *   Diagnostic-Code: SMTP; 554 Please visit http:// antispam.domain.com/denyip.php?IP=111.111.111.000 (#5.7.1)
1244
         */
1245 View Code Duplication
        elseif (\stripos($diag_code, 'denyip') !== false) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
1246
            $result['rule_cat'] = 'antispam';
1247
            $result['rule_no'] = '0144';
1248
        } /* rule: antispam, deny ip
1249
         * sample:
1250
         *   Diagnostic-Code: SMTP; 554 Service unavailable; Client host [111.111.111.211] blocked using dynablock.domain.com; Your message could not be delivered due to complaints we received regarding the IP address you're using or your ISP. See http:// blackholes.domain.com/ Error: WS-02
1251
         */
1252
        elseif (\preg_match('/client host.*blocked/is', $diag_code)) {
1253
            $result['rule_cat'] = 'antispam';
1254
            $result['rule_no'] = '0242';
1255
        } /* rule: antispam, reject
1256
         * sample:
1257
         *   Diagnostic-Code: SMTP; 550 Requested action not taken: mail IsCNAPF76kMDARUY.56621S2 is rejected,mx3,BM
1258
         */
1259
        elseif (\preg_match('/mail.*reject/is', $diag_code)) {
1260
            $result['rule_cat'] = 'antispam';
1261
            $result['rule_no'] = '0147';
1262
        } /* rule: antispam
1263
         * sample:
1264
         *   Diagnostic-Code: SMTP; 552 sorry, the spam message is detected (#5.6.0)
1265
         */
1266
        elseif (\preg_match('/spam.*detect/is', $diag_code)) {
1267
            $result['rule_cat'] = 'antispam';
1268
            $result['rule_no'] = '0162';
1269
        } /* rule: antispam
1270
         * sample:
1271
         *   Diagnostic-Code: SMTP; 554 5.7.1 Rejected as Spam see: http:// rejected.domain.com/help/spam/rejected.html
1272
         */
1273
        elseif (\preg_match('/reject.*spam/is', $diag_code)) {
1274
            $result['rule_cat'] = 'antispam';
1275
            $result['rule_no'] = '0216';
1276
        } /* rule: antispam
1277
         * sample:
1278
         *   Diagnostic-Code: SMTP; 553 5.7.1 <[email protected]>... SpamTrap=reject mode, dsn=5.7.1, Message blocked by BOX Solutions (www.domain.com) SpamTrap Technology, please contact the domain.com site manager for help: (ctlusr8012).
1279
         */
1280 View Code Duplication
        elseif (\stripos($diag_code, 'SpamTrap') !== false) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
1281
            $result['rule_cat'] = 'antispam';
1282
            $result['rule_no'] = '0200';
1283
        } /* rule: antispam, mailfrom mismatch
1284
         * sample:
1285
         *   Diagnostic-Code: SMTP; 550 Verify mailfrom failed,blocked
1286
         */
1287
        elseif (\preg_match('/Verify mailfrom failed/i', $diag_code)) {
1288
            $result['rule_cat'] = 'antispam';
1289
            $result['rule_no'] = '0210';
1290
        } /* rule: antispam, mailfrom mismatch
1291
         * sample:
1292
         *   Diagnostic-Code: SMTP; 550 Error: MAIL FROM is mismatched with message header from address!
1293
         */
1294
        elseif (\preg_match('/MAIL.*FROM.*mismatch/is', $diag_code)) {
1295
            $result['rule_cat'] = 'antispam';
1296
            $result['rule_no'] = '0226';
1297
        } /* rule: antispam
1298
         * sample:
1299
         *   Diagnostic-Code: SMTP; 554 5.7.1 Message scored too high on spam scale.  For help, please quote incident ID 22492290.
1300
         */
1301
        elseif (\preg_match('/spam scale/i', $diag_code)) {
1302
            $result['rule_cat'] = 'antispam';
1303
            $result['rule_no'] = '0211';
1304
        } /* rule: antispam
1305
         * sample:
1306
         *   Diagnostic-Code: SMTP; 554 5.7.1 reject: Client host bypassing service provider's mail relay: ds176.domain.com
1307
         */
1308
        elseif (\preg_match('/Client host bypass/i', $diag_code)) {
1309
            $result['rule_cat'] = 'antispam';
1310
            $result['rule_no'] = '0229';
1311
        } /* rule: antispam
1312
         * sample:
1313
         *   Diagnostic-Code: SMTP; 550 sorry, it seems as a junk mail
1314
         */
1315
        elseif (\preg_match('/junk mail/i', $diag_code)) {
1316
            $result['rule_cat'] = 'antispam';
1317
            $result['rule_no'] = '0230';
1318
        } /* rule: antispam
1319
         * sample:
1320
         *   Diagnostic-Code: SMTP; 553-Message filtered. Please see the FAQs section on spam
1321
         */
1322
        elseif (\preg_match('/message filtered/i', $diag_code)) {
1323
            $result['rule_cat'] = 'antispam';
1324
            $result['rule_no'] = '0243';
1325
        } /* rule: antispam, subject filter
1326
         * sample:
1327
         *   Diagnostic-Code: SMTP; 554 5.7.1 The message from (<[email protected]>) with the subject of ( *(ca2639) 7|-{%2E* : {2"(%EJ;y} (SBI$#$@<K*:7s1!=l~) matches a profile the Internet community may consider spam. Please revise your message before resending.
1328
         */
1329
        elseif (\preg_match('/subject.*consider.*spam/is', $diag_code)) {
1330
            $result['rule_cat'] = 'antispam';
1331
            $result['rule_no'] = '0222';
1332
        } /* rule: internal_error
1333
         * sample:
1334
         *   Diagnostic-Code: SMTP; 451 Temporary local problem - please try later
1335
         */
1336
        elseif (\preg_match('/Temporary local problem/i', $diag_code)) {
1337
            $result['rule_cat'] = 'internal_error';
1338
            $result['rule_no'] = '0142';
1339
        } /* rule: internal_error
1340
         * sample:
1341
         *   Diagnostic-Code: SMTP; 553 5.3.5 system config error
1342
         */
1343
        elseif (\preg_match('/system config error/i', $diag_code)) {
1344
            $result['rule_cat'] = 'internal_error';
1345
            $result['rule_no'] = '0153';
1346
        } /* rule: delayed
1347
         * sample:
1348
         *   Diagnostic-Code: X-Postfix; delivery temporarily suspended: conversation with
1349
         *   111.111.111.11[111.111.111.11] timed out while sending end of data -- message may be
1350
         *   sent more than once
1351
         */
1352
        elseif (\preg_match('/delivery.*suspend/is', $diag_code)) {
1353
            $result['rule_cat'] = 'delayed';
1354
            $result['rule_no'] = '0213';
1355
        }
1356
1357
        // =========== rules based on the dsn_msg ===============
1358
1359
        /* rule: unknown
1360
         * sample:
1361
         *   ----- The following addresses had permanent fatal errors -----
1362
         *   <[email protected]>
1363
         *   ----- Transcript of session follows -----
1364
         *   ... while talking to mta1.domain.com.:
1365
         *   >>> DATA
1366
         *   <<< 503 All recipients are invalid
1367
         *   554 5.0.0 Service unavailable
1368
         */
1369
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user)(?:.*)invalid/i', $dsn_msg)) {
1370
            $result['rule_cat'] = 'unknown';
1371
            $result['rule_no'] = '0107';
1372
        } /* rule: unknown
1373
         * sample:
1374
         *   ----- Transcript of session follows -----
1375
         *   [email protected]... Deferred: No such file or directory
1376
         */
1377
        elseif (\preg_match('/Deferred.*No such.*(?:file|directory)/i', $dsn_msg)) {
1378
            $result['rule_cat'] = 'unknown';
1379
            $result['rule_no'] = '0141';
1380
        } /* rule: unknown
1381
         * sample:
1382
         *   Failed to deliver to '<[email protected]>'
1383
         *   LOCAL module(account xxxx) reports:
1384
         *   mail receiving disabled
1385
         */
1386
        elseif (\preg_match('/mail receiving disabled/i', $dsn_msg)) {
1387
            $result['rule_cat'] = 'unknown';
1388
            $result['rule_no'] = '0194';
1389
        } /* rule: unknown
1390
         * sample:
1391
         *   - These recipients of your message have been processed by the mail server:
1392
         *   [email protected]; Failed; 5.1.1 (bad destination mailbox address)
1393
         */
1394
        elseif (\preg_match('/bad.*(?:alias|account|recipient|address|email|mailbox|user)/i', $status_code)) {
1395
            $result['rule_cat'] = 'unknown';
1396
            $result['rule_no'] = '02441';
1397
        } /* rule: unknown
1398
         * sample:
1399
         *   - These recipients of your message have been processed by the mail server:
1400
         *   [email protected]; Failed; 5.1.1 (bad destination mailbox address)
1401
         */
1402
        elseif (\preg_match('/bad.*(?:alias|account|recipient|address|email|mailbox|user)/i', $dsn_msg)) {
1403
            $result['rule_cat'] = 'unknown';
1404
            $result['rule_no'] = '0244';
1405
        } /* rule: full
1406
         * sample 1:
1407
         *   This Message was undeliverable due to the following reason:
1408
         *   The user(s) account is temporarily over quota.
1409
         *   <[email protected]>
1410
         * sample 2:
1411
         *   Recipient address: [email protected]
1412
         *   Reason: Over quota
1413
         */
1414
        elseif (\preg_match('/over.*quota/i', $dsn_msg)) {
1415
            $result['rule_cat'] = 'full';
1416
            $result['rule_no'] = '0131';
1417
        } /* rule: full
1418
         * sample:
1419
         *   Sorry the recipient quota limit is exceeded.
1420
         *   This message is returned as an error.
1421
         */
1422
        elseif (\preg_match('/quota.*exceeded/i', $dsn_msg)) {
1423
            $result['rule_cat'] = 'full';
1424
            $result['rule_no'] = '0150';
1425
        } /* rule: full
1426
         * sample:
1427
         *   The user to whom this message was addressed has exceeded the allowed mailbox
1428
         *   quota. Please resend the message at a later time.
1429
         */
1430
        elseif (\preg_match("/exceed.*\n?.*quota/i", $dsn_msg)) {
1431
            $result['rule_cat'] = 'full';
1432
            $result['rule_no'] = '0187';
1433
        } /* rule: full
1434
         * sample 1:
1435
         *   Failed to deliver to '<[email protected]>'
1436
         *   LOCAL module(account xxxxxx) reports:
1437
         *   account is full (quota exceeded)
1438
         * sample 2:
1439
         *   Error in fabiomod_sql_glob_init: no data source specified - database access disabled
1440
         *   [Fri Feb 17 23:29:38 PST 2006] full error for caltsmy:
1441
         *   that member's mailbox is full
1442
         *   550 5.0.0 <[email protected]>... Can't create output
1443
         */
1444
        elseif (\preg_match('/(?:alias|account|recipient|address|email|mailbox|user).*full/i', $dsn_msg)) {
1445
            $result['rule_cat'] = 'full';
1446
            $result['rule_no'] = '0132';
1447
        } /* rule: full
1448
         * sample:
1449
         *   gaosong "(0), ErrMsg=Mailbox space not enough (space limit is 10240KB)
1450
         */
1451
        elseif (\preg_match('/space.*not.*enough/i', $dsn_msg)) {
1452
            $result['rule_cat'] = 'full';
1453
            $result['rule_no'] = '0219';
1454
        } /* rule: defer
1455
         * sample 1:
1456
         *   ----- Transcript of session follows -----
1457
         *   [email protected]... Deferred: Connection refused by nomail.tpe.domain.com.
1458
         *   Message could not be delivered for 5 days
1459
         *   Message will be deleted from queue
1460
         * sample 2:
1461
         *   451 4.4.1 reply: read error from www.domain.com.
1462
         *   [email protected]... Deferred: Connection reset by www.domain.com.
1463
         */
1464
        elseif (\preg_match('/Deferred.*Connection (?:refused|reset)/i', $dsn_msg)) {
1465
            $result['rule_cat'] = 'defer';
1466
            $result['rule_no'] = '0115';
1467
        } /* rule: dns_unknown
1468
         * sample:
1469
         *   ----- The following addresses had permanent fatal errors -----
1470
         *   Tan XXXX SSSS <[email protected]>
1471
         *   ----- Transcript of session follows -----
1472
         *   553 5.1.2 XXXX SSSS <[email protected]>... Invalid host name
1473
         */
1474
        elseif (\preg_match('/Invalid host name/i', $dsn_msg)) {
1475
            $result['rule_cat'] = 'dns_unknown';
1476
            $result['rule_no'] = '0239';
1477
        } /* rule: dns_unknown
1478
         * sample:
1479
         *   ----- Transcript of session follows -----
1480
         *   [email protected]... Deferred: mail.domain.com.: No route to host
1481
         */
1482
        elseif (\preg_match('/Deferred.*No route to host/i', $dsn_msg)) {
1483
            $result['rule_cat'] = 'dns_unknown';
1484
            $result['rule_no'] = '0240';
1485
        } /* rule: dns_unknown
1486
         * sample:
1487
         *   ----- Transcript of session follows -----
1488
         *   550 5.1.2 [email protected]... Host unknown (Name server: .: no data known)
1489
         */
1490
        elseif (\preg_match('/Host unknown/i', $dsn_msg)) {
1491
            $result['rule_cat'] = 'dns_unknown';
1492
            $result['rule_no'] = '0140';
1493
        } /* rule: dns_unknown
1494
         * sample:
1495
         *   ----- Transcript of session follows -----
1496
         *   451 HOTMAIL.com.tw: Name server timeout
1497
         *   Message could not be delivered for 5 days
1498
         *   Message will be deleted from queue
1499
         */
1500
        elseif (\preg_match('/Name server timeout/i', $dsn_msg)) {
1501
            $result['rule_cat'] = 'dns_unknown';
1502
            $result['rule_no'] = '0118';
1503
        } /* rule: dns_unknown
1504
         * sample:
1505
         *   ----- Transcript of session follows -----
1506
         *   [email protected]... Deferred: Connection timed out with hkfight.com.
1507
         *   Message could not be delivered for 5 days
1508
         *   Message will be deleted from queue
1509
         */
1510
        elseif (\preg_match('/Deferred.*Connection.*tim(?:e|ed).*out/i', $dsn_msg)) {
1511
            $result['rule_cat'] = 'dns_unknown';
1512
            $result['rule_no'] = '0119';
1513
        } /* rule: dns_unknown
1514
         * sample:
1515
         *   ----- Transcript of session follows -----
1516
         *   [email protected]... Deferred: Name server: domain.com.: host name lookup failure
1517
         */
1518
        elseif (\preg_match('/Deferred.*host name lookup failure/i', $dsn_msg)) {
1519
            $result['rule_cat'] = 'dns_unknown';
1520
            $result['rule_no'] = '0121';
1521
        } /* rule: dns_loop
1522
         * sample:
1523
         *   ----- Transcript of session follows -----
1524
         *   554 5.0.0 MX list for znet.ws. points back to mail01.domain.com
1525
         *   554 5.3.5 Local configuration error
1526
         */
1527
        elseif (\preg_match('/MX list.*point.*back/i', $dsn_msg)) {
1528
            $result['rule_cat'] = 'dns_loop';
1529
            $result['rule_no'] = '0199';
1530
        } /* rule: internal_error
1531
         * sample:
1532
         *   ----- Transcript of session follows -----
1533
         *   451 4.0.0 I/O error
1534
         */
1535
        elseif (\preg_match("/I\/O error/i", $dsn_msg)) {
1536
            $result['rule_cat'] = 'internal_error';
1537
            $result['rule_no'] = '0120';
1538
        } /* rule: internal_error
1539
         * sample:
1540
         *   Failed to deliver to '[email protected]'
1541
         *   SMTP module(domain domain.com) reports:
1542
         *   connection with mx1.mail.domain.com is broken
1543
         */
1544
        elseif (\preg_match('/connection.*broken/i', $dsn_msg)) {
1545
            $result['rule_cat'] = 'internal_error';
1546
            $result['rule_no'] = '0231';
1547
        } /* rule: other
1548
         * sample:
1549
         *   Delivery to the following recipients failed.
1550
         *   [email protected]
1551
         */
1552
        elseif (\preg_match("/Delivery to the following recipients failed.*\n.*\n.*" . \preg_quote($result['email'], '/') . '/i', $dsn_msg)) {
1553
            $result['rule_cat'] = 'other';
1554
            $result['rule_no'] = '0176';
1555
        }
1556
1557
        // Followings are wind-up rule: must be the last one
1558
        //   many other rules msg end up with "550 5.1.1 ... User unknown"
1559
        //   many other rules msg end up with "554 5.0.0 Service unavailable"
1560
1561
        /* rule: unknown
1562
         * sample 1:
1563
         *   ----- The following addresses had permanent fatal errors -----
1564
         *   <[email protected]>
1565
         *   (reason: User unknown)
1566
         * sample 2:
1567
         *   550 5.1.1 [email protected]... User unknown
1568
         */
1569
        elseif (\preg_match('/(?:User unknown|Unknown user)/i', $dsn_msg)) {
1570
            $result['rule_cat'] = 'unknown';
1571
            $result['rule_no'] = '0193';
1572
        } /* rule: unknown
1573
         * sample:
1574
         *   554 5.0.0 Service unavailable
1575
         */
1576
        elseif (\preg_match('/Service unavailable/i', $dsn_msg)) {
1577
            $result['rule_cat'] = 'unknown';
1578
            $result['rule_no'] = '0214';
1579
        }
1580
1581
        break;
1582
1583
      case 'delayed':
1584
        $result['rule_cat'] = 'delayed';
1585
        $result['rule_no'] = '0110';
1586
1587
        break;
1588
1589
      case 'delivered':
1590
      case 'relayed':
1591
      case 'expanded': // unhandled cases
1592
        break;
1593
1594
      default:
1595
        break;
1596
    }
1597
    }
1598
1599
    if ($result['rule_no'] == '0000') {
1600
        if ($debug_mode) {
1601
            echo 'email: ' . $result['email'] . $bmh_newline;
1602
            echo 'Action: ' . $action . $bmh_newline;
1603
            echo 'Status: ' . $status_code . $bmh_newline;
1604
            echo 'Diagnostic-Code: ' . $diag_code . $bmh_newline;
1605
            echo "DSN Message:<br />\n" . $dsn_msg . $bmh_newline;
1606
            echo $bmh_newline;
1607
        }
1608 View Code Duplication
    } else {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
1609
        if ($result['bounce_type'] === false) {
1610
            $result['bounce_type'] = $rule_categories[$result['rule_cat']]['bounce_type'];
1611
            $result['remove'] = $rule_categories[$result['rule_cat']]['remove'];
1612
        }
1613
    }
1614
1615
    return $result;
1616
}
1617