mail 2.5.5 → 2.6.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.
- checksums.yaml +4 -4
- data/CHANGELOG.rdoc +8 -9
- data/CONTRIBUTING.md +13 -0
- data/Dependencies.txt +0 -1
- data/Gemfile +7 -24
- data/README.md +36 -15
- data/Rakefile +10 -2
- data/VERSION +4 -0
- data/lib/mail.rb +1 -1
- data/lib/mail/body.rb +2 -2
- data/lib/mail/check_delivery_params.rb +10 -47
- data/lib/mail/core_extensions/string.rb +12 -2
- data/lib/mail/elements/address.rb +38 -82
- data/lib/mail/elements/address_list.rb +19 -42
- data/lib/mail/elements/content_disposition_element.rb +3 -7
- data/lib/mail/elements/content_location_element.rb +2 -6
- data/lib/mail/elements/content_transfer_encoding_element.rb +3 -10
- data/lib/mail/elements/content_type_element.rb +4 -8
- data/lib/mail/elements/date_time_element.rb +3 -7
- data/lib/mail/elements/envelope_from_element.rb +3 -11
- data/lib/mail/elements/message_ids_element.rb +1 -6
- data/lib/mail/elements/mime_version_element.rb +3 -7
- data/lib/mail/elements/phrase_list.rb +2 -7
- data/lib/mail/elements/received_element.rb +3 -7
- data/lib/mail/encodings.rb +0 -1
- data/lib/mail/envelope.rb +0 -5
- data/lib/mail/field.rb +53 -17
- data/lib/mail/field_list.rb +18 -18
- data/lib/mail/fields/common/common_address.rb +15 -20
- data/lib/mail/fields/common/common_date.rb +0 -7
- data/lib/mail/fields/common/common_field.rb +1 -1
- data/lib/mail/fields/content_transfer_encoding_field.rb +0 -6
- data/lib/mail/fields/resent_sender_field.rb +1 -1
- data/lib/mail/fields/sender_field.rb +1 -1
- data/lib/mail/fields/unstructured_field.rb +7 -1
- data/lib/mail/header.rb +8 -22
- data/lib/mail/mail.rb +12 -0
- data/lib/mail/matchers/has_sent_mail.rb +34 -1
- data/lib/mail/message.rb +18 -11
- data/lib/mail/multibyte/unicode.rb +1 -1
- data/lib/mail/network/delivery_methods/exim.rb +10 -6
- data/lib/mail/network/delivery_methods/file_delivery.rb +8 -4
- data/lib/mail/network/delivery_methods/sendmail.rb +7 -9
- data/lib/mail/network/delivery_methods/smtp.rb +5 -2
- data/lib/mail/network/delivery_methods/smtp_connection.rb +6 -2
- data/lib/mail/network/delivery_methods/test_mailer.rb +8 -5
- data/lib/mail/network/retriever_methods/imap.rb +18 -13
- data/lib/mail/parsers.rb +26 -0
- data/lib/mail/parsers/address_lists_parser.rb +132 -0
- data/lib/mail/parsers/content_disposition_parser.rb +67 -0
- data/lib/mail/parsers/content_location_parser.rb +35 -0
- data/lib/mail/parsers/content_transfer_encoding_parser.rb +33 -0
- data/lib/mail/parsers/content_type_parser.rb +64 -0
- data/lib/mail/parsers/date_time_parser.rb +36 -0
- data/lib/mail/parsers/envelope_from_parser.rb +45 -0
- data/lib/mail/parsers/message_ids_parser.rb +39 -0
- data/lib/mail/parsers/mime_version_parser.rb +41 -0
- data/lib/mail/parsers/phrase_lists_parser.rb +33 -0
- data/lib/mail/parsers/ragel.rb +17 -0
- data/lib/mail/parsers/ragel/common.rl +184 -0
- data/lib/mail/parsers/ragel/date_time.rl +30 -0
- data/lib/mail/parsers/ragel/parser_info.rb +61 -0
- data/lib/mail/parsers/ragel/ruby.rb +29 -0
- data/lib/mail/parsers/ragel/ruby/machines/address_lists_machine.rb +14864 -0
- data/lib/mail/parsers/ragel/ruby/machines/address_lists_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_disposition_machine.rb +751 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_disposition_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_location_machine.rb +614 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_location_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_transfer_encoding_machine.rb +447 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_transfer_encoding_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_type_machine.rb +825 -0
- data/lib/mail/parsers/ragel/ruby/machines/content_type_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/date_time_machine.rb +817 -0
- data/lib/mail/parsers/ragel/ruby/machines/date_time_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/envelope_from_machine.rb +2129 -0
- data/lib/mail/parsers/ragel/ruby/machines/envelope_from_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/message_ids_machine.rb +1570 -0
- data/lib/mail/parsers/ragel/ruby/machines/message_ids_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/mime_version_machine.rb +440 -0
- data/lib/mail/parsers/ragel/ruby/machines/mime_version_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/phrase_lists_machine.rb +564 -0
- data/lib/mail/parsers/ragel/ruby/machines/phrase_lists_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/machines/rb_actions.rl +51 -0
- data/lib/mail/parsers/ragel/ruby/machines/received_machine.rb +5144 -0
- data/lib/mail/parsers/ragel/ruby/machines/received_machine.rb.rl +37 -0
- data/lib/mail/parsers/ragel/ruby/parser.rb.rl.erb +37 -0
- data/lib/mail/parsers/received_parser.rb +47 -0
- data/lib/mail/parts_list.rb +4 -2
- data/lib/mail/patterns.rb +3 -1
- data/lib/mail/utilities.rb +3 -1
- data/lib/mail/version.rb +1 -1
- data/lib/mail/version_specific/ruby_1_8.rb +1 -1
- data/lib/mail/version_specific/ruby_1_9.rb +13 -1
- metadata +55 -51
- data/lib/VERSION +0 -4
- data/lib/load_parsers.rb +0 -35
- data/lib/mail/parsers/address_lists.rb +0 -64
- data/lib/mail/parsers/address_lists.treetop +0 -19
- data/lib/mail/parsers/content_disposition.rb +0 -535
- data/lib/mail/parsers/content_disposition.treetop +0 -46
- data/lib/mail/parsers/content_location.rb +0 -139
- data/lib/mail/parsers/content_location.treetop +0 -20
- data/lib/mail/parsers/content_transfer_encoding.rb +0 -201
- data/lib/mail/parsers/content_transfer_encoding.treetop +0 -18
- data/lib/mail/parsers/content_type.rb +0 -971
- data/lib/mail/parsers/content_type.treetop +0 -68
- data/lib/mail/parsers/date_time.rb +0 -114
- data/lib/mail/parsers/date_time.treetop +0 -11
- data/lib/mail/parsers/envelope_from.rb +0 -194
- data/lib/mail/parsers/envelope_from.treetop +0 -32
- data/lib/mail/parsers/message_ids.rb +0 -45
- data/lib/mail/parsers/message_ids.treetop +0 -15
- data/lib/mail/parsers/mime_version.rb +0 -144
- data/lib/mail/parsers/mime_version.treetop +0 -19
- data/lib/mail/parsers/phrase_lists.rb +0 -45
- data/lib/mail/parsers/phrase_lists.treetop +0 -15
- data/lib/mail/parsers/received.rb +0 -71
- data/lib/mail/parsers/received.treetop +0 -11
- data/lib/mail/parsers/rfc2045.rb +0 -421
- data/lib/mail/parsers/rfc2045.treetop +0 -35
- data/lib/mail/parsers/rfc2822.rb +0 -5397
- data/lib/mail/parsers/rfc2822.treetop +0 -408
- data/lib/mail/parsers/rfc2822_obsolete.rb +0 -3768
- data/lib/mail/parsers/rfc2822_obsolete.treetop +0 -241
- data/lib/tasks/corpus.rake +0 -125
- data/lib/tasks/treetop.rake +0 -10
@@ -1,241 +0,0 @@
|
|
1
|
-
module Mail
|
2
|
-
grammar RFC2822Obsolete
|
3
|
-
|
4
|
-
rule obs_qp
|
5
|
-
"\\" [\x00-\x7F]
|
6
|
-
end
|
7
|
-
|
8
|
-
rule obs_text
|
9
|
-
LF* CR* (obs_char LF* CR*)*
|
10
|
-
end
|
11
|
-
|
12
|
-
rule obs_char
|
13
|
-
[\x00-\x09] / # %d0-127 except CR and
|
14
|
-
[\x0B-\x0C] / # LF
|
15
|
-
[\x0E-\x7F]
|
16
|
-
end
|
17
|
-
|
18
|
-
rule obs_utext
|
19
|
-
obs_text
|
20
|
-
end
|
21
|
-
|
22
|
-
rule obs_phrase
|
23
|
-
(word / "." / "@")+
|
24
|
-
end
|
25
|
-
|
26
|
-
rule obs_phrase_list
|
27
|
-
phrase / (phrase? CFWS? "," CFWS?)+ phrase?
|
28
|
-
end
|
29
|
-
|
30
|
-
rule obs_FWS
|
31
|
-
WSP+ (CRLF WSP+)*
|
32
|
-
end
|
33
|
-
|
34
|
-
rule obs_day_of_week
|
35
|
-
CFWS? day_name CFWS?
|
36
|
-
end
|
37
|
-
|
38
|
-
rule obs_year
|
39
|
-
CFWS? (DIGIT DIGIT) CFWS?
|
40
|
-
end
|
41
|
-
|
42
|
-
rule obs_month
|
43
|
-
CFWS month_name CFWS
|
44
|
-
end
|
45
|
-
|
46
|
-
rule obs_day
|
47
|
-
CFWS? (DIGIT / (DIGIT DIGIT)) CFWS?
|
48
|
-
end
|
49
|
-
|
50
|
-
rule obs_hour
|
51
|
-
CFWS? (DIGIT DIGIT) CFWS?
|
52
|
-
end
|
53
|
-
|
54
|
-
rule obs_minute
|
55
|
-
CFWS? (DIGIT DIGIT) CFWS?
|
56
|
-
end
|
57
|
-
|
58
|
-
rule obs_second
|
59
|
-
CFWS? (DIGIT DIGIT) CFWS?
|
60
|
-
end
|
61
|
-
|
62
|
-
rule obs_zone
|
63
|
-
"UT" / "GMT" / # Universal Time
|
64
|
-
# North American UT
|
65
|
-
# offsets
|
66
|
-
"EST" / "EDT" / # Eastern: - 5/ - 4
|
67
|
-
"CST" / "CDT" / # Central: - 6/ - 5
|
68
|
-
"MST" / "MDT" / # Mountain: - 7/ - 6
|
69
|
-
"PST" / "PDT" / # Pacific: - 8/ - 7
|
70
|
-
#
|
71
|
-
[\x41-\x49] / # Military zones - "A"
|
72
|
-
[\x4B-\x5A] / # through "I" and "K"
|
73
|
-
[\x61-\x69] / # through "Z", both
|
74
|
-
[\x6B-\x7A] # upper and lower case
|
75
|
-
end
|
76
|
-
|
77
|
-
rule obs_angle_addr
|
78
|
-
CFWS? "<" obs_route? addr_spec ">" CFWS?
|
79
|
-
end
|
80
|
-
|
81
|
-
rule obs_route
|
82
|
-
CFWS? obs_domain_list ":" CFWS?
|
83
|
-
end
|
84
|
-
|
85
|
-
rule obs_domain_list
|
86
|
-
"@" domain (("," )* CFWS? "@" domain)*
|
87
|
-
end
|
88
|
-
|
89
|
-
rule obs_local_part
|
90
|
-
word ("." word)*
|
91
|
-
end
|
92
|
-
|
93
|
-
rule obs_domain
|
94
|
-
atom ("." atom)*
|
95
|
-
end
|
96
|
-
|
97
|
-
rule obs_mbox_list
|
98
|
-
(mailbox? CFWS? "," CFWS?)+ mailbox?
|
99
|
-
end
|
100
|
-
|
101
|
-
rule obs_addr_list
|
102
|
-
(address? CFWS? "," CFWS?)+ address?
|
103
|
-
end
|
104
|
-
|
105
|
-
rule obs_fields
|
106
|
-
(obs_return /
|
107
|
-
obs_received /
|
108
|
-
obs_orig_date /
|
109
|
-
obs_from /
|
110
|
-
obs_sender /
|
111
|
-
obs_reply_to /
|
112
|
-
obs_to /
|
113
|
-
obs_cc /
|
114
|
-
obs_bcc /
|
115
|
-
obs_message_id /
|
116
|
-
obs_in_reply_to /
|
117
|
-
obs_references /
|
118
|
-
obs_subject /
|
119
|
-
obs_comments /
|
120
|
-
obs_keywords /
|
121
|
-
obs_resent_date /
|
122
|
-
obs_resent_from /
|
123
|
-
obs_resent_send /
|
124
|
-
obs_resent_rply /
|
125
|
-
obs_resent_to /
|
126
|
-
obs_resent_cc /
|
127
|
-
obs_resent_bcc /
|
128
|
-
obs_resent_mid /
|
129
|
-
obs_optional)*
|
130
|
-
end
|
131
|
-
|
132
|
-
rule obs_orig_date
|
133
|
-
"Date" WSP* ":" date_time CRLF
|
134
|
-
end
|
135
|
-
|
136
|
-
rule obs_from
|
137
|
-
"From" WSP* ":" mailbox_list CRLF
|
138
|
-
end
|
139
|
-
|
140
|
-
rule obs_sender
|
141
|
-
"Sender" WSP* ":" mailbox CRLF
|
142
|
-
end
|
143
|
-
|
144
|
-
rule obs_reply_to
|
145
|
-
"Reply-To" WSP* ":" mailbox_list CRLF
|
146
|
-
end
|
147
|
-
|
148
|
-
|
149
|
-
rule obs_to
|
150
|
-
"To" WSP* ":" address_list CRLF
|
151
|
-
end
|
152
|
-
|
153
|
-
rule obs_cc
|
154
|
-
"Cc" WSP* ":" address_list CRLF
|
155
|
-
end
|
156
|
-
|
157
|
-
rule obs_bcc
|
158
|
-
"Bcc" WSP* ":" (address_list / CFWS?) CRLF
|
159
|
-
end
|
160
|
-
|
161
|
-
rule obs_message_id
|
162
|
-
"Message-ID" WSP* ":" msg_id CRLF
|
163
|
-
end
|
164
|
-
|
165
|
-
rule obs_in_reply_to
|
166
|
-
"In-Reply-To" WSP* ":" (phrase / msg_id)* CRLF
|
167
|
-
end
|
168
|
-
|
169
|
-
rule obs_references
|
170
|
-
"References" WSP* ":" (phrase / msg_id)* CRLF
|
171
|
-
end
|
172
|
-
|
173
|
-
rule obs_id_left
|
174
|
-
local_part
|
175
|
-
end
|
176
|
-
|
177
|
-
rule obs_id_right
|
178
|
-
domain
|
179
|
-
end
|
180
|
-
|
181
|
-
rule obs_subject
|
182
|
-
"Subject" WSP* ":" unstructured CRLF
|
183
|
-
end
|
184
|
-
|
185
|
-
rule obs_comments
|
186
|
-
"Comments" WSP* ":" unstructured CRLF
|
187
|
-
end
|
188
|
-
|
189
|
-
rule obs_keywords
|
190
|
-
"Keywords" WSP* ":" obs_phrase_list CRLF
|
191
|
-
end
|
192
|
-
|
193
|
-
rule obs_resent_from
|
194
|
-
"Resent-From" WSP* ":" mailbox_list CRLF
|
195
|
-
end
|
196
|
-
|
197
|
-
rule obs_resent_send
|
198
|
-
"Resent-Sender" WSP* ":" mailbox CRLF
|
199
|
-
end
|
200
|
-
|
201
|
-
rule obs_resent_date
|
202
|
-
"Resent-Date" WSP* ":" date_time CRLF
|
203
|
-
end
|
204
|
-
|
205
|
-
rule obs_resent_to
|
206
|
-
"Resent-To" WSP* ":" address_list CRLF
|
207
|
-
end
|
208
|
-
|
209
|
-
rule obs_resent_cc
|
210
|
-
"Resent-Cc" WSP* ":" address_list CRLF
|
211
|
-
end
|
212
|
-
|
213
|
-
rule obs_resent_bcc
|
214
|
-
"Resent-Bcc" WSP* ":" (address_list / CFWS?) CRLF
|
215
|
-
end
|
216
|
-
|
217
|
-
rule obs_resent_mid
|
218
|
-
"Resent-Message-ID" WSP* ":" msg_id CRLF
|
219
|
-
end
|
220
|
-
|
221
|
-
rule obs_resent_rply
|
222
|
-
"Resent-Reply-To" WSP* ":" address_list CRLF
|
223
|
-
end
|
224
|
-
|
225
|
-
rule obs_return
|
226
|
-
"Return-Path" WSP* ":" path CRLF
|
227
|
-
end
|
228
|
-
|
229
|
-
rule obs_received
|
230
|
-
"Received" WSP* ":" name_val_list CRLF
|
231
|
-
end
|
232
|
-
|
233
|
-
rule obs_path
|
234
|
-
obs_angle_addr
|
235
|
-
end
|
236
|
-
|
237
|
-
rule obs_optional
|
238
|
-
field_name WSP* ":" unstructured CRLF
|
239
|
-
end
|
240
|
-
end
|
241
|
-
end
|
data/lib/tasks/corpus.rake
DELETED
@@ -1,125 +0,0 @@
|
|
1
|
-
namespace :corpus do
|
2
|
-
|
3
|
-
task :load_mail do
|
4
|
-
require File.expand_path('../../../spec/environment')
|
5
|
-
require 'mail'
|
6
|
-
end
|
7
|
-
|
8
|
-
# Used to run parsing against an arbitrary corpus of email.
|
9
|
-
# For example: http://plg.uwaterloo.ca/~gvcormac/treccorpus/
|
10
|
-
desc "Provide a LOCATION=/some/dir to verify parsing in bulk, otherwise defaults"
|
11
|
-
task :verify_all => :load_mail do
|
12
|
-
|
13
|
-
root_of_corpus = ENV['LOCATION'] || 'corpus/spam'
|
14
|
-
@save_failures_to = ENV['SAVE_TO'] || 'spec/fixtures/emails/failed_emails'
|
15
|
-
@failed_emails = []
|
16
|
-
@checked_count = 0
|
17
|
-
|
18
|
-
if root_of_corpus
|
19
|
-
root_of_corpus = File.expand_path(root_of_corpus)
|
20
|
-
if not File.directory?(root_of_corpus)
|
21
|
-
raise "\n\tPath '#{root_of_corpus}' is not a directory.\n\n"
|
22
|
-
end
|
23
|
-
else
|
24
|
-
raise "\n\tSupply path to corpus: LOCATION=/path/to/corpus\n\n"
|
25
|
-
end
|
26
|
-
|
27
|
-
if @save_failures_to
|
28
|
-
if not File.directory?(@save_failures_to)
|
29
|
-
raise "\n\tPath '#{@save_failures_to}' is not a directory.\n\n"
|
30
|
-
end
|
31
|
-
@save_failures_to = File.expand_path(@save_failures_to)
|
32
|
-
puts "Mail which fails to parse will be saved in '#{@save_failures_to}'"
|
33
|
-
end
|
34
|
-
|
35
|
-
puts "Checking '#{root_of_corpus}' directory (recursively)"
|
36
|
-
|
37
|
-
# we're tracking all the errors separately, don't clutter terminal
|
38
|
-
$stderr_backup = $stderr.dup
|
39
|
-
$stderr.reopen("/dev/null", "w")
|
40
|
-
STDERR = $stderr
|
41
|
-
|
42
|
-
dir_node(root_of_corpus)
|
43
|
-
|
44
|
-
# put our toys back now that we're done with them
|
45
|
-
$stderr = $stderr_backup.dup
|
46
|
-
STDERR = $stderr
|
47
|
-
|
48
|
-
puts "\n\n"
|
49
|
-
|
50
|
-
if @failed_emails.any?
|
51
|
-
report_failures_to_stdout
|
52
|
-
end
|
53
|
-
puts "Out of Total: #{@checked_count}"
|
54
|
-
|
55
|
-
if @save_failures_to
|
56
|
-
puts "Add SAVE_TO=/some/dir to save failed emails to for review.,"
|
57
|
-
puts "May result in a lot of saved files. Do a dry run first!\n\n"
|
58
|
-
else
|
59
|
-
puts "There are no errors"
|
60
|
-
end
|
61
|
-
end
|
62
|
-
|
63
|
-
def dir_node(path)
|
64
|
-
puts "\n\n"
|
65
|
-
puts "Checking emails in '#{path}':"
|
66
|
-
|
67
|
-
entries = Dir.entries(path)
|
68
|
-
|
69
|
-
entries.each do |entry|
|
70
|
-
next if ['.', '..'].include?(entry)
|
71
|
-
full_path = File.join(path, entry)
|
72
|
-
|
73
|
-
if File.file?(full_path)
|
74
|
-
file_node(full_path)
|
75
|
-
elsif File.directory?(full_path)
|
76
|
-
dir_node(full_path)
|
77
|
-
end
|
78
|
-
end
|
79
|
-
end
|
80
|
-
|
81
|
-
def file_node(path)
|
82
|
-
verify(path)
|
83
|
-
end
|
84
|
-
|
85
|
-
def verify(path)
|
86
|
-
result, message = parse_as_mail(path)
|
87
|
-
if result
|
88
|
-
print '.'
|
89
|
-
$stdout.flush
|
90
|
-
else
|
91
|
-
save_failure(path, message)
|
92
|
-
print 'x'
|
93
|
-
end
|
94
|
-
end
|
95
|
-
|
96
|
-
def save_failure(path, message)
|
97
|
-
@failed_emails << [path, message]
|
98
|
-
if @save_failures_to
|
99
|
-
email_basename = File.basename(path)
|
100
|
-
failure_as_filename = message.gsub(/\W/, '_')
|
101
|
-
new_email_name = [failure_as_filename, email_basename].join("_")
|
102
|
-
File.open(File.join(@save_failures_to, new_email_name), 'w+') do |fh|
|
103
|
-
fh << File.read(path)
|
104
|
-
end
|
105
|
-
end
|
106
|
-
end
|
107
|
-
|
108
|
-
def parse_as_mail(path)
|
109
|
-
@checked_count += 1
|
110
|
-
begin
|
111
|
-
parsed_mail = Mail.read(path)
|
112
|
-
[true, nil]
|
113
|
-
rescue => e
|
114
|
-
[false, e.message]
|
115
|
-
end
|
116
|
-
end
|
117
|
-
|
118
|
-
def report_failures_to_stdout
|
119
|
-
@failed_emails.each do |failed|
|
120
|
-
puts "#{failed[0]} : #{failed[1]}"
|
121
|
-
end
|
122
|
-
puts "Failed: #{@failed_emails.size}"
|
123
|
-
end
|
124
|
-
|
125
|
-
end
|
data/lib/tasks/treetop.rake
DELETED