sisimai 5.0.3 → 5.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (258) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/codecovio.yml +3 -1
  3. data/.github/workflows/rake-test.yml +7 -3
  4. data/ChangeLog.md +136 -0
  5. data/Makefile +4 -2
  6. data/README-JA.md +32 -22
  7. data/README.md +31 -21
  8. data/lib/sisimai/arf.rb +124 -213
  9. data/lib/sisimai/fact/json.rb +2 -2
  10. data/lib/sisimai/fact/yaml.rb +2 -2
  11. data/lib/sisimai/fact.rb +208 -173
  12. data/lib/sisimai/lda.rb +98 -0
  13. data/lib/sisimai/lhost/activehunter.rb +5 -4
  14. data/lib/sisimai/lhost/amazonses.rb +189 -305
  15. data/lib/sisimai/lhost/apachejames.rb +52 -55
  16. data/lib/sisimai/lhost/biglobe.rb +5 -6
  17. data/lib/sisimai/lhost/courier.rb +14 -12
  18. data/lib/sisimai/lhost/domino.rb +29 -29
  19. data/lib/sisimai/lhost/dragonfly.rb +113 -0
  20. data/lib/sisimai/lhost/einsundeins.rb +7 -8
  21. data/lib/sisimai/lhost/exchange2003.rb +10 -11
  22. data/lib/sisimai/lhost/exchange2007.rb +115 -104
  23. data/lib/sisimai/lhost/exim.rb +236 -246
  24. data/lib/sisimai/lhost/ezweb.rb +47 -55
  25. data/lib/sisimai/lhost/fml.rb +6 -7
  26. data/lib/sisimai/lhost/gmail.rb +36 -32
  27. data/lib/sisimai/lhost/gmx.rb +8 -20
  28. data/lib/sisimai/lhost/googlegroups.rb +13 -12
  29. data/lib/sisimai/lhost/googleworkspace.rb +94 -0
  30. data/lib/sisimai/lhost/imailserver.rb +11 -19
  31. data/lib/sisimai/lhost/interscanmss.rb +6 -5
  32. data/lib/sisimai/lhost/kddi.rb +7 -8
  33. data/lib/sisimai/lhost/mailfoundry.rb +6 -9
  34. data/lib/sisimai/lhost/mailmarshalsmtp.rb +6 -6
  35. data/lib/sisimai/lhost/messagingserver.rb +19 -17
  36. data/lib/sisimai/lhost/mfilter.rb +8 -7
  37. data/lib/sisimai/lhost/notes.rb +6 -8
  38. data/lib/sisimai/lhost/opensmtpd.rb +11 -9
  39. data/lib/sisimai/lhost/postfix.rb +29 -31
  40. data/lib/sisimai/lhost/qmail.rb +136 -112
  41. data/lib/sisimai/lhost/sendmail.rb +23 -22
  42. data/lib/sisimai/lhost/v5sendmail.rb +93 -64
  43. data/lib/sisimai/lhost/verizon.rb +6 -6
  44. data/lib/sisimai/lhost/x1.rb +4 -4
  45. data/lib/sisimai/lhost/x2.rb +4 -5
  46. data/lib/sisimai/lhost/x3.rb +5 -5
  47. data/lib/sisimai/lhost/x6.rb +4 -4
  48. data/lib/sisimai/lhost/zoho.rb +6 -6
  49. data/lib/sisimai/lhost.rb +21 -24
  50. data/lib/sisimai/mail/maildir.rb +1 -1
  51. data/lib/sisimai/mail/stdin.rb +1 -1
  52. data/lib/sisimai/message.rb +100 -153
  53. data/lib/sisimai/order.rb +22 -77
  54. data/lib/sisimai/reason/authfailure.rb +1 -4
  55. data/lib/sisimai/reason/badreputation.rb +3 -3
  56. data/lib/sisimai/reason/blocked.rb +7 -10
  57. data/lib/sisimai/reason/contenterror.rb +7 -1
  58. data/lib/sisimai/reason/exceedlimit.rb +1 -4
  59. data/lib/sisimai/reason/failedstarttls.rb +42 -0
  60. data/lib/sisimai/reason/filtered.rb +5 -4
  61. data/lib/sisimai/reason/hasmoved.rb +1 -2
  62. data/lib/sisimai/reason/hostunknown.rb +3 -3
  63. data/lib/sisimai/reason/mailboxfull.rb +2 -4
  64. data/lib/sisimai/reason/mailererror.rb +1 -2
  65. data/lib/sisimai/reason/mesgtoobig.rb +2 -4
  66. data/lib/sisimai/reason/norelaying.rb +3 -3
  67. data/lib/sisimai/reason/notaccept.rb +2 -3
  68. data/lib/sisimai/reason/notcompliantrfc.rb +10 -4
  69. data/lib/sisimai/reason/rejected.rb +2 -1
  70. data/lib/sisimai/reason/requireptr.rb +2 -2
  71. data/lib/sisimai/reason/securityerror.rb +1 -3
  72. data/lib/sisimai/reason/spamdetected.rb +6 -8
  73. data/lib/sisimai/reason/speeding.rb +1 -2
  74. data/lib/sisimai/reason/suppressed.rb +36 -0
  75. data/lib/sisimai/reason/suspend.rb +1 -3
  76. data/lib/sisimai/reason/systemerror.rb +5 -0
  77. data/lib/sisimai/reason/toomanyconn.rb +1 -2
  78. data/lib/sisimai/reason/userunknown.rb +1 -1
  79. data/lib/sisimai/reason/virusdetected.rb +5 -6
  80. data/lib/sisimai/reason.rb +82 -78
  81. data/lib/sisimai/rfc1123.rb +152 -0
  82. data/lib/sisimai/rfc1894.rb +102 -62
  83. data/lib/sisimai/rfc2045.rb +2 -1
  84. data/lib/sisimai/rfc3464/thirdparty.rb +102 -0
  85. data/lib/sisimai/rfc3464.rb +224 -345
  86. data/lib/sisimai/rfc3834.rb +3 -3
  87. data/lib/sisimai/rfc5322.rb +7 -17
  88. data/lib/sisimai/rfc791.rb +69 -0
  89. data/lib/sisimai/rhost/aol.rb +36 -0
  90. data/lib/sisimai/rhost/apple.rb +95 -0
  91. data/lib/sisimai/rhost/cox.rb +84 -34
  92. data/lib/sisimai/rhost/facebook.rb +100 -0
  93. data/lib/sisimai/rhost/franceptt.rb +87 -83
  94. data/lib/sisimai/rhost/godaddy.rb +208 -45
  95. data/lib/sisimai/rhost/google.rb +22 -22
  96. data/lib/sisimai/rhost/gsuite.rb +42 -0
  97. data/lib/sisimai/rhost/iua.rb +5 -5
  98. data/lib/sisimai/rhost/kddi.rb +9 -7
  99. data/lib/sisimai/rhost/messagelabs.rb +37 -0
  100. data/lib/sisimai/rhost/microsoft.rb +60 -54
  101. data/lib/sisimai/rhost/mimecast.rb +44 -31
  102. data/lib/sisimai/rhost/nttdocomo.rb +5 -4
  103. data/lib/sisimai/rhost/outlook.rb +36 -0
  104. data/lib/sisimai/rhost/spectrum.rb +102 -41
  105. data/lib/sisimai/rhost/tencent.rb +48 -26
  106. data/lib/sisimai/rhost/yahooinc.rb +111 -0
  107. data/lib/sisimai/rhost.rb +65 -42
  108. data/lib/sisimai/smtp/command.rb +31 -21
  109. data/lib/sisimai/smtp/failure.rb +103 -0
  110. data/lib/sisimai/smtp/reply.rb +29 -24
  111. data/lib/sisimai/smtp/status.rb +36 -19
  112. data/lib/sisimai/smtp/transcript.rb +18 -18
  113. data/lib/sisimai/string.rb +0 -46
  114. data/lib/sisimai/version.rb +1 -1
  115. data/lib/sisimai.rb +0 -6
  116. data/set-of-emails/maildir/bsd/lhost-dragonfly-01.eml +36 -0
  117. data/set-of-emails/maildir/bsd/lhost-dragonfly-02.eml +32 -0
  118. data/set-of-emails/maildir/bsd/lhost-dragonfly-03.eml +32 -0
  119. data/set-of-emails/maildir/bsd/lhost-dragonfly-04.eml +31 -0
  120. data/set-of-emails/maildir/bsd/lhost-dragonfly-05.eml +32 -0
  121. data/set-of-emails/maildir/bsd/lhost-dragonfly-06.eml +32 -0
  122. data/set-of-emails/maildir/bsd/lhost-dragonfly-07.eml +32 -0
  123. data/set-of-emails/maildir/bsd/lhost-dragonfly-08.eml +32 -0
  124. data/set-of-emails/maildir/bsd/lhost-dragonfly-09.eml +32 -0
  125. data/set-of-emails/maildir/bsd/lhost-dragonfly-10.eml +32 -0
  126. data/set-of-emails/maildir/bsd/lhost-dragonfly-11.eml +32 -0
  127. data/set-of-emails/maildir/bsd/lhost-dragonfly-12.eml +32 -0
  128. data/set-of-emails/maildir/bsd/lhost-dragonfly-13.eml +32 -0
  129. data/set-of-emails/maildir/bsd/lhost-dragonfly-14.eml +32 -0
  130. data/set-of-emails/maildir/bsd/lhost-dragonfly-15.eml +32 -0
  131. data/set-of-emails/maildir/bsd/lhost-dragonfly-16.eml +32 -0
  132. data/set-of-emails/maildir/bsd/lhost-dragonfly-17.eml +32 -0
  133. data/set-of-emails/maildir/bsd/lhost-dragonfly-18.eml +32 -0
  134. data/set-of-emails/maildir/bsd/lhost-dragonfly-19.eml +32 -0
  135. data/set-of-emails/maildir/bsd/lhost-dragonfly-20.eml +32 -0
  136. data/set-of-emails/maildir/bsd/lhost-dragonfly-21.eml +33 -0
  137. data/set-of-emails/maildir/bsd/lhost-dragonfly-22.eml +32 -0
  138. data/set-of-emails/maildir/bsd/lhost-dragonfly-23.eml +32 -0
  139. data/set-of-emails/maildir/bsd/lhost-dragonfly-24.eml +32 -0
  140. data/set-of-emails/maildir/bsd/lhost-dragonfly-25.eml +33 -0
  141. data/set-of-emails/maildir/bsd/lhost-dragonfly-26.eml +33 -0
  142. data/set-of-emails/maildir/bsd/lhost-dragonfly-27.eml +47 -0
  143. data/set-of-emails/maildir/bsd/lhost-dragonfly-28.eml +47 -0
  144. data/set-of-emails/maildir/bsd/lhost-dragonfly-29.eml +32 -0
  145. data/set-of-emails/maildir/bsd/lhost-dragonfly-30.eml +32 -0
  146. data/set-of-emails/maildir/bsd/lhost-opensmtpd-10.eml +58 -0
  147. data/set-of-emails/maildir/bsd/lhost-opensmtpd-11.eml +58 -0
  148. data/set-of-emails/maildir/bsd/lhost-opensmtpd-12.eml +62 -0
  149. data/set-of-emails/maildir/bsd/lhost-opensmtpd-13.eml +62 -0
  150. data/set-of-emails/maildir/bsd/lhost-opensmtpd-14.eml +58 -0
  151. data/set-of-emails/maildir/bsd/lhost-opensmtpd-15.eml +63 -0
  152. data/set-of-emails/maildir/bsd/lhost-opensmtpd-16.eml +62 -0
  153. data/set-of-emails/maildir/bsd/lhost-opensmtpd-17.eml +63 -0
  154. data/set-of-emails/maildir/bsd/lhost-postfix-30.eml +81 -81
  155. data/set-of-emails/maildir/bsd/lhost-qmail-11.eml +29 -0
  156. data/set-of-emails/maildir/bsd/lhost-qmail-12.eml +29 -0
  157. data/set-of-emails/maildir/bsd/lhost-qmail-13.eml +29 -0
  158. data/set-of-emails/maildir/bsd/lhost-qmail-14.eml +34 -0
  159. data/set-of-emails/maildir/bsd/lhost-qmail-15.eml +30 -0
  160. data/set-of-emails/maildir/bsd/lhost-qmail-16.eml +31 -0
  161. data/set-of-emails/maildir/bsd/lhost-qmail-17.eml +38 -0
  162. data/set-of-emails/maildir/bsd/lhost-qmail-18.eml +31 -0
  163. data/set-of-emails/maildir/bsd/lhost-qmail-19.eml +31 -0
  164. data/set-of-emails/maildir/bsd/lhost-qmail-20.eml +46 -0
  165. data/set-of-emails/maildir/bsd/lhost-qmail-21.eml +41 -0
  166. data/set-of-emails/maildir/bsd/lhost-qmail-22.eml +42 -0
  167. data/set-of-emails/maildir/bsd/lhost-qmail-23.eml +43 -0
  168. data/set-of-emails/maildir/bsd/lhost-qmail-24.eml +43 -0
  169. data/set-of-emails/maildir/bsd/lhost-qmail-25.eml +54 -0
  170. data/set-of-emails/maildir/bsd/{lhost-aol-03.eml → rhost-aol-03.eml} +1264 -1264
  171. data/set-of-emails/maildir/bsd/{lhost-aol-04.eml → rhost-aol-04.eml} +1260 -1260
  172. data/set-of-emails/maildir/bsd/{lhost-aol-05.eml → rhost-aol-05.eml} +105 -105
  173. data/set-of-emails/maildir/bsd/{lhost-aol-06.eml → rhost-aol-06.eml} +105 -105
  174. data/set-of-emails/maildir/bsd/rhost-apple-01.eml +79 -0
  175. data/set-of-emails/maildir/bsd/rhost-apple-02.eml +81 -0
  176. data/set-of-emails/maildir/bsd/rhost-apple-03.eml +75 -0
  177. data/set-of-emails/maildir/bsd/rhost-apple-04.eml +74 -0
  178. data/set-of-emails/maildir/bsd/rhost-gsuite-01.eml +189 -0
  179. data/set-of-emails/maildir/bsd/rhost-gsuite-02.eml +180 -0
  180. data/set-of-emails/maildir/bsd/rhost-gsuite-03.eml +251 -0
  181. data/set-of-emails/maildir/bsd/rhost-gsuite-04.eml +211 -0
  182. data/set-of-emails/maildir/bsd/rhost-gsuite-05.eml +226 -0
  183. data/set-of-emails/maildir/bsd/rhost-gsuite-06.eml +257 -0
  184. data/set-of-emails/maildir/bsd/rhost-gsuite-07.eml +289 -0
  185. data/set-of-emails/maildir/bsd/rhost-gsuite-08.eml +231 -0
  186. data/set-of-emails/maildir/bsd/rhost-gsuite-09.eml +231 -0
  187. data/set-of-emails/maildir/bsd/rhost-gsuite-10.eml +254 -0
  188. data/set-of-emails/maildir/bsd/rhost-gsuite-11.eml +228 -0
  189. data/set-of-emails/maildir/bsd/rhost-gsuite-12.eml +271 -0
  190. data/set-of-emails/maildir/bsd/rhost-gsuite-13.eml +261 -0
  191. data/set-of-emails/maildir/bsd/rhost-gsuite-14.eml +273 -0
  192. data/set-of-emails/maildir/bsd/rhost-gsuite-15.eml +229 -0
  193. data/set-of-emails/maildir/bsd/{lhost-messagelabs-01.eml → rhost-messagelabs-01.eml} +93 -93
  194. data/set-of-emails/maildir/bsd/rhost-outlook-01.eml +72 -0
  195. data/set-of-emails/maildir/bsd/rhost-outlook-02.eml +72 -0
  196. data/set-of-emails/maildir/bsd/rhost-outlook-03.eml +72 -0
  197. data/set-of-emails/maildir/bsd/rhost-outlook-04.eml +79 -0
  198. data/set-of-emails/maildir/bsd/rhost-outlook-06.eml +75 -0
  199. data/set-of-emails/maildir/bsd/rhost-outlook-07.eml +70 -0
  200. data/set-of-emails/maildir/bsd/rhost-outlook-08.eml +70 -0
  201. data/set-of-emails/maildir/bsd/rhost-outlook-09.eml +56 -0
  202. data/set-of-emails/maildir/bsd/rhost-yahooinc-01.eml +80 -0
  203. data/set-of-emails/maildir/bsd/rhost-yahooinc-02.eml +83 -0
  204. data/set-of-emails/maildir/bsd/rhost-yahooinc-03.eml +125 -0
  205. data/set-of-emails/maildir/tmp/arf-22.eml +49 -0
  206. data/set-of-emails/maildir/tmp/arf-23.eml +49 -0
  207. data/set-of-emails/maildir/tmp/arf-24.eml +50 -0
  208. data/set-of-emails/maildir/tmp/lhost-exim-07.eml +28 -0
  209. metadata +136 -56
  210. data/lib/sisimai/lhost/amavis.rb +0 -163
  211. data/lib/sisimai/lhost/amazonworkmail.rb +0 -127
  212. data/lib/sisimai/lhost/aol.rb +0 -125
  213. data/lib/sisimai/lhost/barracuda.rb +0 -92
  214. data/lib/sisimai/lhost/bigfoot.rb +0 -125
  215. data/lib/sisimai/lhost/facebook.rb +0 -188
  216. data/lib/sisimai/lhost/gsuite.rb +0 -194
  217. data/lib/sisimai/lhost/mailru.rb +0 -214
  218. data/lib/sisimai/lhost/mcafee.rb +0 -109
  219. data/lib/sisimai/lhost/messagelabs.rb +0 -119
  220. data/lib/sisimai/lhost/mxlogic.rb +0 -198
  221. data/lib/sisimai/lhost/office365.rb +0 -252
  222. data/lib/sisimai/lhost/outlook.rb +0 -129
  223. data/lib/sisimai/lhost/powermta.rb +0 -118
  224. data/lib/sisimai/lhost/receivingses.rb +0 -126
  225. data/lib/sisimai/lhost/sendgrid.rb +0 -150
  226. data/lib/sisimai/lhost/surfcontrol.rb +0 -105
  227. data/lib/sisimai/lhost/x4.rb +0 -269
  228. data/lib/sisimai/lhost/x5.rb +0 -112
  229. data/lib/sisimai/lhost/yahoo.rb +0 -102
  230. data/lib/sisimai/lhost/yandex.rb +0 -118
  231. data/lib/sisimai/mda.rb +0 -121
  232. data/lib/sisimai/smtp/error.rb +0 -119
  233. /data/set-of-emails/maildir/bsd/{lhost-googlegroups-15.eml → lhost-googleworkspace-01.eml} +0 -0
  234. /data/set-of-emails/maildir/bsd/{lhost-x4-08.eml → lhost-x2-06.eml} +0 -0
  235. /data/set-of-emails/maildir/bsd/{lhost-gsuite-01.eml → rfc3464-51.eml} +0 -0
  236. /data/set-of-emails/maildir/bsd/{lhost-gsuite-03.eml → rfc3464-52.eml} +0 -0
  237. /data/set-of-emails/maildir/bsd/{lhost-gsuite-04.eml → rfc3464-53.eml} +0 -0
  238. /data/set-of-emails/maildir/bsd/{lhost-gsuite-05.eml → rfc3464-54.eml} +0 -0
  239. /data/set-of-emails/maildir/bsd/{lhost-gsuite-06.eml → rfc3464-55.eml} +0 -0
  240. /data/set-of-emails/maildir/bsd/{lhost-gsuite-07.eml → rfc3464-56.eml} +0 -0
  241. /data/set-of-emails/maildir/bsd/{lhost-gsuite-08.eml → rfc3464-57.eml} +0 -0
  242. /data/set-of-emails/maildir/bsd/{lhost-gsuite-09.eml → rfc3464-58.eml} +0 -0
  243. /data/set-of-emails/maildir/bsd/{lhost-gsuite-10.eml → rfc3464-59.eml} +0 -0
  244. /data/set-of-emails/maildir/bsd/{lhost-gsuite-11.eml → rfc3464-60.eml} +0 -0
  245. /data/set-of-emails/maildir/bsd/{lhost-gsuite-12.eml → rfc3464-61.eml} +0 -0
  246. /data/set-of-emails/maildir/bsd/{lhost-gsuite-13.eml → rfc3464-62.eml} +0 -0
  247. /data/set-of-emails/maildir/bsd/{lhost-gsuite-14.eml → rfc3464-63.eml} +0 -0
  248. /data/set-of-emails/maildir/bsd/{lhost-gsuite-15.eml → rfc3464-64.eml} +0 -0
  249. /data/set-of-emails/maildir/bsd/{lhost-gsuite-02.eml → rfc3464-65.eml} +0 -0
  250. /data/set-of-emails/maildir/bsd/{lhost-aol-01.eml → rhost-aol-01.eml} +0 -0
  251. /data/set-of-emails/maildir/bsd/{lhost-aol-02.eml → rhost-aol-02.eml} +0 -0
  252. /data/set-of-emails/maildir/bsd/{lhost-facebook-03.eml → rhost-facebook-03.eml} +0 -0
  253. /data/set-of-emails/maildir/bsd/{lhost-facebook-04.eml → rhost-facebook-04.eml} +0 -0
  254. /data/set-of-emails/maildir/bsd/{lhost-messagelabs-02.eml → rhost-messagelabs-02.eml} +0 -0
  255. /data/set-of-emails/maildir/bsd/{lhost-messagelabs-03.eml → rhost-messagelabs-03.eml} +0 -0
  256. /data/set-of-emails/maildir/{bsd → tmp}/rfc3464-37.eml +0 -0
  257. /data/set-of-emails/maildir/{bsd → tmp}/rfc3464-38.eml +0 -0
  258. /data/set-of-emails/maildir/{bsd → tmp}/rfc3464-39.eml +0 -0
@@ -1,16 +1,17 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::InterScanMSS parses a bounce email which created by Trend Micro InterScan Messaging
3
- # Security Suite. Methods in the module are called from only Sisimai::Message.
2
+ # Sisimai::Lhost::InterScanMSS decodes a bounce email which created by Trend Micro InterScan
3
+ # Messaging Security Suite https://www.trendmicro.com/en_us/business/products/user-protection/sps/email-and-collaboration/interscan-messaging.html.
4
+ # Methods in the module are called from only Sisimai::Message.
4
5
  module InterScanMSS
5
6
  class << self
6
7
  require 'sisimai/lhost'
7
8
  Boundaries = ['Content-Type: message/rfc822'].freeze
8
9
 
9
- # Parse bounce messages from InterScanMSS
10
+ # @abstract Decodes the bounce message from Trend Micro InterScanMSS Messaging Secutiry Suie
10
11
  # @param [Hash] mhead Message headers of a bounce email
11
12
  # @param [String] mbody Message body of a bounce email
12
13
  # @return [Hash] Bounce data list and message/rfc822 part
13
- # @return [Nil] it failed to parse or the arguments are missing
14
+ # @return [Nil] it failed to decode or the arguments are missing
14
15
  def inquire(mhead, mbody)
15
16
  # :received => %r/[ ][(]InterScanMSS[)][ ]with[ ]/,
16
17
  match = 0
@@ -45,7 +46,7 @@ module Sisimai::Lhost
45
46
  # Unable to deliver message to <kijitora@neko.example.jp>
46
47
  cr = e[e.rindex('<') + 1, e.rindex('>') - e.rindex('<') - 1]
47
48
 
48
- if v['recipient'] && cr != v['recipient']
49
+ if v["recipient"] != "" && cr != v['recipient']
49
50
  # There are multiple recipient addresses in the message body.
50
51
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
51
52
  v = dscontents[-1]
@@ -1,24 +1,24 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::KDDI parses a bounce email which created by au by KDDI. Methods in the module are
3
- # called from only Sisimai::Message.
2
+ # Sisimai::Lhost::KDDI decodes a bounce email which created by au by KDDI https://www.au.com/.
3
+ # Methods in the module are called from only Sisimai::Message.
4
4
  module KDDI
5
5
  class << self
6
6
  require 'sisimai/lhost'
7
7
 
8
8
  Indicators = Sisimai::Lhost.INDICATORS
9
9
  Boundaries = ['Content-Type: message/rfc822'].freeze
10
- MarkingsOf = { message: ['Your mail sent on:', 'Your mail attempted to be delivered on:'] }.freeze
10
+ StartingOf = { message: ['Your mail sent on:', 'Your mail attempted to be delivered on:'] }.freeze
11
11
  MessagesOf = {
12
12
  'mailboxfull' => ['As their mailbox is full'],
13
13
  'norelaying' => ['Due to the following SMTP relay error'],
14
14
  'hostunknown' => ['As the remote domain doesnt exist'],
15
15
  }.freeze
16
16
 
17
- # Parse bounce messages from au by KDDI
17
+ # @abstract Decodes the bounce message from au by KDDI
18
18
  # @param [Hash] mhead Message headers of a bounce email
19
19
  # @param [String] mbody Message body of a bounce email
20
20
  # @return [Hash] Bounce data list and message/rfc822 part
21
- # @return [Nil] it failed to parse or the arguments are missing
21
+ # @return [Nil] it failed to decode or the arguments are missing
22
22
  def inquire(mhead, mbody)
23
23
  # :'message-id' => %r/[@].+[.]ezweb[.]ne[.]jp[>]\z/,
24
24
  match = 0
@@ -40,7 +40,7 @@ module Sisimai::Lhost
40
40
  # line of the beginning of the original message.
41
41
  if readcursor == 0
42
42
  # Beginning of the bounce message or delivery status part
43
- readcursor |= Indicators[:deliverystatus] if MarkingsOf[:message].any? { |a| e.start_with?(a) }
43
+ readcursor |= Indicators[:deliverystatus] if StartingOf[:message].any? { |a| e.start_with?(a) }
44
44
  next
45
45
  end
46
46
  next if (readcursor & Indicators[:deliverystatus]) == 0
@@ -51,7 +51,7 @@ module Sisimai::Lhost
51
51
  # Your mail sent on: Thu, 29 Apr 2010 11:04:47 +0900
52
52
  # Could not be delivered to: <******@**.***.**>
53
53
  # As their mailbox is full.
54
- if v['recipient']
54
+ if v["recipient"] != ""
55
55
  # There are multiple recipient addresses in the message body.
56
56
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
57
57
  v = dscontents[-1]
@@ -66,7 +66,6 @@ module Sisimai::Lhost
66
66
  v['date'] = e[19, e.size]
67
67
  else
68
68
  # As their mailbox is full.
69
- v['diagnosis'] ||= ''
70
69
  v['diagnosis'] << e + ' ' if e.start_with?(' ')
71
70
  end
72
71
  end
@@ -1,6 +1,6 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::MailFoundry parses a bounce email which created by MailFoundry. Methods in the
3
- # module are called from only Sisimai::Message.
2
+ # Sisimai::Lhost::MailFoundry decodes a bounce email which created by MailFoundry https://www.barracuda.com/.
3
+ # Methods in the module are called from only Sisimai::Message.
4
4
  module MailFoundry
5
5
  class << self
6
6
  require 'sisimai/lhost'
@@ -12,11 +12,11 @@ module Sisimai::Lhost
12
12
  error: ['Delivery failed for the following reason:'],
13
13
  }.freeze
14
14
 
15
- # Parse bounce messages from MailFoundry
15
+ # @abstract Decodes the bounce message from MailFoundry
16
16
  # @param [Hash] mhead Message headers of a bounce email
17
17
  # @param [String] mbody Message body of a bounce email
18
18
  # @return [Hash] Bounce data list and message/rfc822 part
19
- # @return [Nil] it failed to parse or the arguments are missing
19
+ # @return [Nil] it failed to decode or the arguments are missing
20
20
  def inquire(mhead, mbody)
21
21
  return nil unless mhead['subject'] == 'Message delivery has failed'
22
22
  return nil unless mhead['received'].any? { |a| a.include?('(MAILFOUNDRY) id ') }
@@ -47,7 +47,7 @@ module Sisimai::Lhost
47
47
 
48
48
  if e.start_with?('Unable to deliver message to: <') && e.index('@') > 1
49
49
  # Unable to deliver message to: <kijitora@example.org>
50
- if v['recipient']
50
+ if v["recipient"] != ""
51
51
  # There are multiple recipient addresses in the message body.
52
52
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
53
53
  v = dscontents[-1]
@@ -55,17 +55,14 @@ module Sisimai::Lhost
55
55
  v['recipient'] = e[e.index('<'), e.size]
56
56
  recipients += 1
57
57
  else
58
- # Error message
58
+ # Error messages
59
59
  if e == StartingOf[:error][0]
60
60
  # Delivery failed for the following reason:
61
61
  v['diagnosis'] = e
62
62
  else
63
63
  # Detect error message
64
- next if e.empty?
65
64
  next if v['diagnosis'].nil? || v['diagnosis'].empty?
66
65
  next if e.start_with?('-')
67
-
68
- # Server mx22.example.org[192.0.2.222] failed with: 550 <kijitora@example.org> No such user here
69
66
  v['diagnosis'] << ' ' << e
70
67
  end
71
68
  end
@@ -1,6 +1,7 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::MailMarshalSMTP parses a bounce email which created by Trustwave Secure Email
3
- # Gateway: formerly MailMarshal SMTP. Methods in the module are called from only Sisimai::Message.
2
+ # Sisimai::Lhost::MailMarshalSMTP decodes a bounce email which created by Trustwave Secure Email
3
+ # Gateway: formerly MailMarshal SMTP https://www.trustwave.com/en-us/services/email-security/.
4
+ # Methods in the module are called from only Sisimai::Message.
4
5
  module MailMarshalSMTP
5
6
  class << self
6
7
  require 'sisimai/lhost'
@@ -13,11 +14,11 @@ module Sisimai::Lhost
13
14
  rcpts: ['The following recipients were affected:'],
14
15
  }.freeze
15
16
 
16
- # Parse bounce messages from MailMarshalSMTP
17
+ # @abstract Decodes the bounce message from Trustwave Secure Email Gateway (Formerly MailMarshalSMTP)
17
18
  # @param [Hash] mhead Message headers of a bounce email
18
19
  # @param [String] mbody Message body of a bounce email
19
20
  # @return [Hash] Bounce data list and message/rfc822 part
20
- # @return [Nil] it failed to parse or the arguments are missing
21
+ # @return [Nil] it failed to decode or the arguments are missing
21
22
  def inquire(mhead, mbody)
22
23
  return nil unless mhead['subject'].start_with?('Undeliverable Mail: "')
23
24
 
@@ -27,7 +28,6 @@ module Sisimai::Lhost
27
28
  readcursor = 0 # (Integer) Points the current cursor position
28
29
  recipients = 0 # (Integer) The number of 'Final-Recipient' header
29
30
  endoferror = false # (Boolean) Flag for the end of error message
30
- regularexp = nil
31
31
  q = Sisimai::RFC2045.boundary(mhead['content-type'], 1); Boundaries << q if q
32
32
  v = nil
33
33
 
@@ -55,7 +55,7 @@ module Sisimai::Lhost
55
55
  if e.start_with?(' ') && e.index('@') > 1
56
56
  # The following recipients were affected:
57
57
  # dummyuser@blabla.xxxxxxxxxxxx.com
58
- if v['recipient']
58
+ if v["recipient"] != ""
59
59
  # There are multiple recipient addresses in the message body.
60
60
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
61
61
  v = dscontents[-1]
@@ -1,6 +1,7 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::MessagingServer parses a bounce email which created by Oracle Communications Messaging
3
- # Server and Sun Java System Messaging Server. Methods in the module are called from only Sisimai::Message.
2
+ # Sisimai::Lhost::MessagingServer decodes a bounce email which created by Oracle Communications
3
+ # Messaging Server and Sun Java System Messaging Server https://docs.oracle.com/en/industries/communications/messaging-server/index.html.
4
+ # Methods in the module are called from only Sisimai::Message.
4
5
  module MessagingServer
5
6
  class << self
6
7
  require 'sisimai/lhost'
@@ -10,11 +11,11 @@ module Sisimai::Lhost
10
11
  StartingOf = { message: ['This report relates to a message you sent with the following header fields:'] }.freeze
11
12
  MessagesOf = { 'hostunknown' => ['Illegal host/domain name found'] }.freeze
12
13
 
13
- # Parse bounce messages from MessagingServer
14
+ # @abstract Decodes the bounce message from MessagingServer
14
15
  # @param [Hash] mhead Message headers of a bounce email
15
16
  # @param [String] mbody Message body of a bounce email
16
17
  # @return [Hash] Bounce data list and message/rfc822 part
17
- # @return [Nil] it failed to parse or the arguments are missing
18
+ # @return [Nil] it failed to decode or the arguments are missing
18
19
  def inquire(mhead, mbody)
19
20
  match = 0
20
21
  match += 1 if mhead['content-type'].include?('Boundary_(ID_')
@@ -59,20 +60,21 @@ module Sisimai::Lhost
59
60
  # Remote system: dns;mx.example.jp (TCP|17.111.174.67|47323|192.0.2.225|25) (6jo.example.jp ESMTP SENDMAIL-VM)
60
61
  v = dscontents[-1]
61
62
 
62
- if e.start_with?(' Recipient address: ') && e.index('@') > 1
63
- # Recipient address: kijitora@example.jp
64
- if v['recipient']
63
+ if Sisimai::String.aligned(e, [' Recipient address: ', '@', '.']) ||
64
+ Sisimai::String.aligned(e, [' Original address: ', '@', '.'])
65
+ # Recipient address: @smtp.example.net:kijitora@server
66
+ # Original address: kijitora@example.jp
67
+ cv = Sisimai::Address.s3s4(e[e.rindex(' ') + 1, e.size])
68
+ next unless Sisimai::Address.is_emailaddress(cv)
69
+
70
+ if v["recipient"] != "" && cv != v['recipient']
65
71
  # There are multiple recipient addresses in the message body.
66
72
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
67
73
  v = dscontents[-1]
68
74
  end
69
- v['recipient'] = Sisimai::Address.s3s4(e[e.rindex(' ') + 1, e.size])
75
+ v['recipient'] = cv
70
76
  recipients += 1
71
77
 
72
- elsif e.start_with?(' Original address: ') && e.index('@') > 1
73
- # Original address: kijitora@example.jp
74
- v['recipient'] = Sisimai::Address.s3s4(e[e.rindex(' ') + 1, e.size])
75
-
76
78
  elsif e.start_with?(' Date: ')
77
79
  # Date: Fri, 21 Nov 2014 23:34:45 +0900
78
80
  v['date'] = e[e.index(':') + 2, e.size]
@@ -119,18 +121,18 @@ module Sisimai::Lhost
119
121
  # Status: 5.1.1 (Remote SMTP server has rejected address)
120
122
  p1 = e.index(':')
121
123
  p2 = e.index('(')
122
- v['status'] = e[p1 + 2, p2 - p1 - 3]
123
- v['diagnosis'] ||= e[p2 + 1, e[e.index(')') - p2 - 1]]
124
+ v['status'] = e[p1 + 2, p2 - p1 - 3]
125
+ v['diagnosis'] = e[p2 + 1, e[e.index(')') - p2 - 1]] if v["diagnosis"].empty?
124
126
 
125
127
  elsif e.start_with?('Arrival-Date: ')
126
128
  # Arrival-date: Thu, 29 Apr 2014 23:34:45 +0000 (GMT)
127
- v['date'] ||= e[e.index(':') + 2, e.size]
129
+ v['date'] = e[e.index(':') + 2, e.size] if v["date"].empty?
128
130
 
129
131
  elsif e.start_with?('Reporting-MTA: ')
130
132
  # Reporting-MTA: dns;mr21p30im-asmtp004.me.com (tcp-daemon)
131
133
  localhost = e[e.index(';') + 1, e.size]
132
- v['lhost'] ||= localhost
133
- v['lhost'] = localhost unless v['lhost'].index('.') > 0
134
+ v['lhost'] = localhost if v["lhost"].empty?
135
+ v['lhost'] = localhost unless v['lhost'].index('.') > 0
134
136
  end
135
137
  end
136
138
  end
@@ -1,6 +1,6 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::mFILTER parses a bounce email which created by Digital Arts m-FILTER. Methods in
3
- # the module are called from only Sisimai::Message.
2
+ # Sisimai::Lhost::mFILTER decodes a bounce email which created by Digital Arts m-FILTER https://www.daj.jp/bs/mf/.
3
+ # Methods in the module are called from only Sisimai::Message.
4
4
  module MFILTER
5
5
  class << self
6
6
  require 'sisimai/lhost'
@@ -12,11 +12,11 @@ module Sisimai::Lhost
12
12
  command: ['-------SMTP command'],
13
13
  }.freeze
14
14
 
15
- # Parse bounce messages from Digital Arts m-FILTER
15
+ # @abstract Decodes the bounce message from Digital Arts m-FILTER
16
16
  # @param [Hash] mhead Message headers of a bounce email
17
17
  # @param [String] mbody Message body of a bounce email
18
18
  # @return [Hash] Bounce data list and message/rfc822 part
19
- # @return [Nil] it failed to parse or the arguments are missing
19
+ # @return [Nil] it failed to decode or the arguments are missing
20
20
  def inquire(mhead, mbody)
21
21
  # X-Mailer: m-FILTER
22
22
  return nil unless mhead['x-mailer'].to_s == 'm-FILTER'
@@ -62,7 +62,7 @@ module Sisimai::Lhost
62
62
  if e.include?('@') && e.include?(' ') == false
63
63
  # 以下のメールアドレスへの送信に失敗しました。
64
64
  # kijitora@example.jp
65
- if v['recipient']
65
+ if v["recipient"] != ""
66
66
  # There are multiple recipient addresses in the message body.
67
67
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
68
68
  v = dscontents[-1]
@@ -75,6 +75,7 @@ module Sisimai::Lhost
75
75
  # DATA
76
76
  next if v['command']
77
77
  v['command'] = e if markingset['command']
78
+
78
79
  else
79
80
  # Get error message and SMTP command
80
81
  if e == StartingOf[:error][0]
@@ -87,7 +88,7 @@ module Sisimai::Lhost
87
88
  else
88
89
  # 550 5.1.1 unknown user <kijitora@example.jp>
89
90
  next if e.start_with?('-')
90
- next if v['diagnosis']
91
+ next if v['diagnosis'] != ""
91
92
  v['diagnosis'] = e
92
93
  end
93
94
  end
@@ -103,7 +104,7 @@ module Sisimai::Lhost
103
104
  rheads = mhead['received']
104
105
  rhosts = Sisimai::RFC5322.received(rheads[-1])
105
106
 
106
- e['lhost'] ||= Sisimai::RFC5322.received(rheads[0]).shift
107
+ e['lhost'] = Sisimai::RFC5322.received(rheads[0]).shift if e["lhost"].empty?
107
108
  [rhosts[0], rhosts[1]].each do |ee|
108
109
  # Avoid "... by m-FILTER"
109
110
  next unless ee.include?('.')
@@ -1,6 +1,6 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::Notes parses a bounce email which created by Lotus Notes Server. Methods in the
3
- # module are called from only Sisimai::Message.
2
+ # Sisimai::Lhost::Notes decodes a bounce email which created by HCL Notes (formerly IMB Notes Server
3
+ # (formerly Lotus Notes Server)). Methods in the module are called from only Sisimai::Message.
4
4
  module Notes
5
5
  class << self
6
6
  require 'sisimai/lhost'
@@ -16,11 +16,11 @@ module Sisimai::Lhost
16
16
  'networkerror' => ['Message has exceeded maximum hop count'],
17
17
  }.freeze
18
18
 
19
- # Parse bounce messages from Lotus Notes
19
+ # @abstract Decodes the bounce messages from HCL Notes (Formerly IBM Notes (Formerly Lotus Notes))
20
20
  # @param [Hash] mhead Message headers of a bounce email
21
21
  # @param [String] mbody Message body of a bounce email
22
22
  # @return [Hash] Bounce data list and message/rfc822 part
23
- # @return [Nil] it failed to parse or the arguments are missing
23
+ # @return [Nil] it failed to decode or the arguments are missing
24
24
  def inquire(mhead, mbody)
25
25
  return nil unless mhead['subject'].start_with?('Undeliverable message')
26
26
 
@@ -58,12 +58,12 @@ module Sisimai::Lhost
58
58
  v = dscontents[-1]
59
59
  if e.include?('@') && e.index(' ').nil?
60
60
  # kijitora@notes.example.jp
61
- if v['recipient']
61
+ if v["recipient"] != ""
62
62
  # There are multiple recipient addresses in the message body.
63
63
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
64
64
  v = dscontents[-1]
65
65
  end
66
- v['recipient'] ||= e
66
+ v["recipient"] = e if v["recipient"].empty?
67
67
  recipients += 1
68
68
  else
69
69
  next if e.empty?
@@ -83,11 +83,9 @@ module Sisimai::Lhost
83
83
  # No character set in Content-Type header
84
84
  encodedmsg = removedmsg
85
85
  end
86
- v['diagnosis'] ||= ''
87
86
  v['diagnosis'] << encodedmsg
88
87
  else
89
88
  # Error message does not include multi-byte character
90
- v['diagnosis'] ||= ''
91
89
  v['diagnosis'] << e
92
90
  end
93
91
  end
@@ -1,6 +1,6 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::OpenSMTPD parses a bounce email which created by OpenSMTPD. Methods in the module
3
- # are called from only Sisimai::Message.
2
+ # Sisimai::Lhost::OpenSMTPD decodes a bounce email which created by OpenSMTPD https://www.opensmtpd.org/.
3
+ # Methods in the module are called from only Sisimai::Message.
4
4
  module OpenSMTPD
5
5
  class << self
6
6
  require 'sisimai/lhost'
@@ -45,7 +45,11 @@ module Sisimai::Lhost
45
45
  'Domain does not exist',
46
46
  ],
47
47
  # smtp/mta.c:1085| relay->failstr = "Destination seem to reject all mails";
48
- 'notaccept' => ['Destination seem to reject all mails'],
48
+ 'notaccept' => [
49
+ 'Destination seem to reject all mails',
50
+ 'No MX found for domain',
51
+ 'No MX found for destination',
52
+ ],
49
53
  # smtpd/mta.c:972| relay->failstr = "Temporary failure in MX lookup";
50
54
  'networkerror' => [
51
55
  'Address family mismatch on destination MXs',
@@ -54,8 +58,6 @@ module Sisimai::Lhost
54
58
  'Could not retrieve source address',
55
59
  'Loop detected',
56
60
  'Network error on destination MXs',
57
- 'No MX found for domain',
58
- 'No MX found for destination',
59
61
  'No valid route to remote MX',
60
62
  'No valid route to destination',
61
63
  'Temporary failure in MX lookup',
@@ -64,11 +66,11 @@ module Sisimai::Lhost
64
66
  'securityerror' => ['Could not retrieve credentials'],
65
67
  }.freeze
66
68
 
67
- # Parse bounce messages from OpenSMTPD
69
+ # @abstract Decodes the bounce message from OpenSMTPD
68
70
  # @param [Hash] mhead Message headers of a bounce email
69
71
  # @param [String] mbody Message body of a bounce email
70
72
  # @return [Hash] Bounce data list and message/rfc822 part
71
- # @return [Nil] it failed to parse or the arguments are missing
73
+ # @return [Nil] it failed to decode or the arguments are missing
72
74
  def inquire(mhead, mbody)
73
75
  return nil unless mhead['subject'].start_with?('Delivery status notification')
74
76
  return nil unless mhead['from'].start_with?('Mailer Daemon <')
@@ -104,9 +106,9 @@ module Sisimai::Lhost
104
106
  # Below is a copy of the original message:
105
107
  v = dscontents[-1]
106
108
 
107
- if e.include?('@') && Sisimai::String.aligned(e, ['@', ' '])
109
+ if Sisimai::String.aligned(e, ['@', ' '])
108
110
  # kijitora@example.jp: 550 5.2.2 <kijitora@example>... Mailbox Full
109
- if v['recipient']
111
+ if v["recipient"] != ""
110
112
  # There are multiple recipient addresses in the message body.
111
113
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
112
114
  v = dscontents[-1]
@@ -1,9 +1,11 @@
1
1
  module Sisimai::Lhost
2
- # Sisimai::Lhost::Postfix parses a bounce email which created by Postfix. Methods in the module are
3
- # called from only Sisimai::Message.
2
+ # Sisimai::Lhost::Postfix decodes a bounce email which created by Postfix https://www.postfix.org/.
3
+ # Methods in the module are called from only Sisimai::Message.
4
4
  module Postfix
5
5
  class << self
6
6
  require 'sisimai/lhost'
7
+ require 'sisimai/rfc1123'
8
+ require 'sisimai/smtp/reply'
7
9
  require 'sisimai/smtp/command'
8
10
 
9
11
  # Postfix manual - bounce(5) - http://www.postfix.org/bounce.5.html
@@ -20,25 +22,23 @@ module Sisimai::Lhost
20
22
  ],
21
23
  }.freeze
22
24
 
23
- # Parse bounce messages from Postfix
25
+ # @abstract Decodes the bounce message from Postfix
24
26
  # @param [Hash] mhead Message headers of a bounce email
25
27
  # @param [String] mbody Message body of a bounce email
26
28
  # @return [Hash] Bounce data list and message/rfc822 part
27
- # @return [Nil] it failed to parse or the arguments are missing
29
+ # @return [Nil] it failed to decode or the arguments are missing
28
30
  def inquire(mhead, mbody)
29
- match = nil
30
- sessx = nil
31
+ match = 0
31
32
 
32
33
  if mhead['subject'].include?('SMTP server: errors from ')
33
34
  # src/smtpd/smtpd_chat.c:|337: post_mail_fprintf(notice, "Subject: %s SMTP server: errors from %s",
34
35
  # src/smtpd/smtpd_chat.c:|338: var_mail_name, state->namaddr);
35
- match = true
36
- sessx = true
36
+ match = 2
37
37
  else
38
38
  # Subject: Undelivered Mail Returned to Sender
39
- match = true if mhead['subject'] == 'Undelivered Mail Returned to Sender'
39
+ match = 1 if mhead['subject'] == 'Undelivered Mail Returned to Sender'
40
40
  end
41
- return nil unless match
41
+ return nil if match == 0
42
42
  return nil if mhead['x-aol-ip']
43
43
 
44
44
  permessage = {} # (Hash) Store values of each Per-Message field
@@ -52,7 +52,7 @@ module Sisimai::Lhost
52
52
  anotherset = {} # Another error information
53
53
  v = nil
54
54
 
55
- if sessx
55
+ if match == 2
56
56
  # The message body starts with 'Transcript of session follows.'
57
57
  require 'sisimai/smtp/transcript'
58
58
  transcript = Sisimai::SMTP::Transcript.rise(emailparts[0], 'In:', 'Out:')
@@ -75,7 +75,7 @@ module Sisimai::Lhost
75
75
 
76
76
  elsif e['command'] == 'RCPT'
77
77
  # RCPT TO: <...>
78
- if v['recipient']
78
+ if v["recipient"] != ""
79
79
  # There are multiple recipient addresses in the transcript of session
80
80
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
81
81
  v = dscontents[-1]
@@ -86,9 +86,9 @@ module Sisimai::Lhost
86
86
 
87
87
  next if p['reply'].to_i < 400
88
88
  commandset << e['command']
89
- v['diagnosis'] ||= p['text'].join(' ')
90
- v['replycode'] ||= p['reply']
91
- v['status'] ||= p['status']
89
+ v['diagnosis'] = p['text'].join(' ') if v["diagnosis"].empty?
90
+ v['replycode'] = p['reply'] if v["replycode"].empty?
91
+ v['status'] = p['status'] if v["status"].empty?
92
92
  end
93
93
  else
94
94
  fieldtable = Sisimai::RFC1894.FIELDTABLE
@@ -107,17 +107,18 @@ module Sisimai::Lhost
107
107
  next if (readcursor & Indicators[:deliverystatus]) == 0
108
108
  next if e.empty?
109
109
 
110
- if f = Sisimai::RFC1894.match(e)
110
+ f = Sisimai::RFC1894.match(e)
111
+ if f > 0
111
112
  # "e" matched with any field defined in RFC3464
112
113
  next unless o = Sisimai::RFC1894.field(e)
113
114
  v = dscontents[-1]
114
115
 
115
- if o[-1] == 'addr'
116
+ if o[3] == 'addr'
116
117
  # Final-Recipient: rfc822; kijitora@example.jp
117
118
  # X-Actual-Recipient: rfc822; kijitora@example.co.jp
118
119
  if o[0] == 'final-recipient'
119
120
  # Final-Recipient: rfc822; kijitora@example.jp
120
- if v['recipient']
121
+ if v["recipient"] != ""
121
122
  # There are multiple recipient addresses in the message body.
122
123
  dscontents << Sisimai::Lhost.DELIVERYSTATUS
123
124
  v = dscontents[-1]
@@ -128,17 +129,18 @@ module Sisimai::Lhost
128
129
  # X-Actual-Recipient: rfc822; kijitora@example.co.jp
129
130
  v['alias'] = o[2]
130
131
  end
131
- elsif o[-1] == 'code'
132
+ elsif o[3] == 'code'
132
133
  # Diagnostic-Code: SMTP; 550 5.1.1 <userunknown@example.jp>... User Unknown
133
134
  v['spec'] = o[1]
134
- v['spec'] = 'SMTP' if v['spec'] == 'X-POSTFIX'
135
+ v['spec'] = 'SMTP' if v['spec'].upcase == 'X-POSTFIX'
135
136
  v['diagnosis'] = o[2]
136
137
  else
137
138
  # Other DSN fields defined in RFC3464
138
139
  next unless fieldtable[o[0]]
140
+ next if o[3] == "host" && Sisimai::RFC1123.is_internethost(o[2]) == false
139
141
  v[fieldtable[o[0]]] = o[2]
140
142
 
141
- next unless f
143
+ next unless f == 1
142
144
  permessage[fieldtable[o[0]]] = o[2]
143
145
  end
144
146
  else
@@ -162,7 +164,7 @@ module Sisimai::Lhost
162
164
  # Alternative error message and recipient
163
165
  if e.include?(' (in reply to ') || e.include?('command)')
164
166
  # 5.1.1 <userunknown@example.co.jp>... User Unknown (in reply to RCPT TO
165
- q = Sisimai::SMTP::Command.find(e); commandset << q if q
167
+ cv = Sisimai::SMTP::Command.find(e) || ""; commandset << cv unless cv.empty?
166
168
  anotherset['diagnosis'] ||= ''
167
169
  anotherset['diagnosis'] << ' ' << e
168
170
 
@@ -205,7 +207,7 @@ module Sisimai::Lhost
205
207
 
206
208
  end
207
209
 
208
- unless recipients > 0
210
+ if recipients == 0
209
211
  # Fallback: get a recipient address from error messages
210
212
  if anotherset['recipient'].to_s.size > 0
211
213
  # Set a recipient address
@@ -241,13 +243,9 @@ module Sisimai::Lhost
241
243
  # More detailed error message is in "anotherset"
242
244
  as = '' # status
243
245
  ar = '' # replycode
244
-
245
- e['status'] ||= ''
246
- e['replycode'] ||= ''
247
-
248
246
  if e['status'].empty? || e['status'].start_with?('4.0.0', '5.0.0')
249
247
  # Check the value of D.S.N. in anotherset
250
- as = Sisimai::SMTP::Status.find(anotherset['diagnosis']) || ''
248
+ as = Sisimai::SMTP::Status.find(anotherset['diagnosis'])
251
249
  if as.size > 0 && as[-4, 4] != '.0.0'
252
250
  # The D.S.N. is neither an empty nor *.0.0
253
251
  e['status'] = as
@@ -256,7 +254,7 @@ module Sisimai::Lhost
256
254
 
257
255
  if e['replycode'].empty? || e['replycode'].end_with?('00')
258
256
  # Check the value of SMTP reply code in $anotherset
259
- ar = Sisimai::SMTP::Reply.find(anotherset['diagnosis']) || ''
257
+ ar = Sisimai::SMTP::Reply.find(anotherset['diagnosis'])
260
258
  if ar.size > 0 && ar.end_with?('00') == false
261
259
  # The SMTP reply code is neither an empty nor *00
262
260
  e['replycode'] = ar
@@ -278,8 +276,8 @@ module Sisimai::Lhost
278
276
 
279
277
  e['diagnosis'] = Sisimai::String.sweep(e['diagnosis']) || ''
280
278
  e['command'] = commandset.shift || Sisimai::SMTP::Command.find(e['diagnosis'])
281
- e['command'] ||= 'HELO' if e['diagnosis'].include?('refused to talk to me:')
282
- e['spec'] ||= 'SMTP' if Sisimai::String.aligned(e['diagnosis'], ['host ', ' said:'])
279
+ e['command'] = 'HELO' if e["command"].empty? && e['diagnosis'].include?('refused to talk to me:')
280
+ e['spec'] = 'SMTP' if e["spec"].empty? && Sisimai::String.aligned(e['diagnosis'], ['host ', ' said:'])
283
281
  end
284
282
 
285
283
  return { 'ds' => dscontents, 'rfc822' => emailparts[1] }