mailparser 0.4.22a

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,1130 @@
1
+ # -*- coding: utf-8 -*-
2
+ # Copyright (C) 2007-2010 TOMITA Masahiro
3
+ # mailto:tommy@tmtm.org
4
+
5
+ require "mailparser"
6
+ require "test/unit"
7
+
8
+ class TC_Message < Test::Unit::TestCase
9
+ def setup()
10
+ end
11
+ def teardown()
12
+ end
13
+
14
+ def test_from()
15
+ msg = StringIO.new(<<EOS)
16
+ From: TOMITA Masahiro <tommy@tmtm.org>
17
+
18
+ EOS
19
+ m = MailParser::Message.new(msg)
20
+ assert_equal("tommy", m.from.addr_spec.local_part)
21
+ assert_equal("tmtm.org", m.from.addr_spec.domain)
22
+ assert_equal("TOMITA Masahiro", m.from.display_name)
23
+ assert_equal([], m.from.comments)
24
+ end
25
+
26
+ def test_from_mime()
27
+ msg = StringIO.new(<<EOS)
28
+ From: =?us-ascii?q?TOMITA_Masahiro?= <tommy@tmtm.org>
29
+
30
+ EOS
31
+ m = MailParser::Message.new(msg)
32
+ assert_equal("tommy", m.from.addr_spec.local_part)
33
+ assert_equal("tmtm.org", m.from.addr_spec.domain)
34
+ assert_equal("=?us-ascii?q?TOMITA_Masahiro?=", m.from.display_name)
35
+ assert_equal([], m.from.comments)
36
+ end
37
+
38
+ def test_from_mime_decode()
39
+ msg = StringIO.new(<<EOS)
40
+ From: =?us-ascii?q?TOMITA_Masahiro?= <tommy@tmtm.org>
41
+
42
+ EOS
43
+ m = MailParser::Message.new(msg, :decode_mime_header=>true)
44
+ assert_equal("tommy", m.from.addr_spec.local_part)
45
+ assert_equal("tmtm.org", m.from.addr_spec.domain)
46
+ assert_equal("TOMITA Masahiro", m.from.display_name)
47
+ assert_equal([], m.from.comments)
48
+ end
49
+
50
+ def test_from_none()
51
+ msg = StringIO.new(<<EOS)
52
+ Sender: TOMITA Masahiro <tommy@tmtm.org>
53
+
54
+ EOS
55
+ m = MailParser::Message.new(msg)
56
+ assert_nil(m.from)
57
+ end
58
+
59
+ def test_from_multi()
60
+ msg = StringIO.new(<<EOS)
61
+ From: TOMITA Masahiro <tommy@tmtm.org>, hoge@example.com
62
+
63
+ EOS
64
+ m = MailParser::Message.new(msg)
65
+ assert_equal("tommy", m.from.addr_spec.local_part)
66
+ assert_equal("tmtm.org", m.from.addr_spec.domain)
67
+ assert_equal("TOMITA Masahiro", m.from.display_name)
68
+ assert_equal([], m.from.comments)
69
+ end
70
+
71
+ def test_from_comment()
72
+ msg = StringIO.new(<<EOS)
73
+ From: TOMITA Masahiro <tommy@tmtm.org> (hoge hoge)
74
+
75
+ EOS
76
+ m = MailParser::Message.new(msg)
77
+ assert_equal("tommy", m.from.addr_spec.local_part)
78
+ assert_equal("tmtm.org", m.from.addr_spec.domain)
79
+ assert_equal("TOMITA Masahiro", m.from.display_name)
80
+ assert_equal(["(hoge hoge)"], m.from.comments)
81
+ end
82
+
83
+ def test_to()
84
+ msg = StringIO.new(<<EOS)
85
+ To: TOMITA Masahiro <tommy@tmtm.org>
86
+
87
+ EOS
88
+ m = MailParser::Message.new(msg)
89
+ assert_equal(1, m.to.size)
90
+ assert_equal("tommy", m.to[0].addr_spec.local_part)
91
+ assert_equal("tmtm.org", m.to[0].addr_spec.domain)
92
+ assert_equal("TOMITA Masahiro", m.to[0].display_name)
93
+ assert_equal([], m.to[0].comments)
94
+ end
95
+
96
+ def test_to_none()
97
+ msg = StringIO.new(<<EOS)
98
+ From: TOMITA Masahiro <tommy@tmtm.org>
99
+
100
+ EOS
101
+ m = MailParser::Message.new(msg)
102
+ assert_equal([], m.to)
103
+ end
104
+
105
+ def test_to_multi()
106
+ msg = StringIO.new(<<EOS)
107
+ To: TOMITA Masahiro <tommy@tmtm.org>, hoge@example.com
108
+
109
+ EOS
110
+ m = MailParser::Message.new(msg)
111
+ assert_equal(2, m.to.size)
112
+ assert_equal("tommy", m.to[0].addr_spec.local_part)
113
+ assert_equal("tmtm.org", m.to[0].addr_spec.domain)
114
+ assert_equal("TOMITA Masahiro", m.to[0].display_name)
115
+ assert_equal([], m.to[0].comments)
116
+ assert_equal("hoge", m.to[1].addr_spec.local_part)
117
+ assert_equal("example.com", m.to[1].addr_spec.domain)
118
+ assert_equal("", m.to[1].display_name)
119
+ assert_equal([], m.to[1].comments)
120
+ end
121
+
122
+ def test_to_multi_header()
123
+ msg = StringIO.new(<<EOS)
124
+ To: TOMITA Masahiro <tommy@tmtm.org>, hoge@example.com
125
+ To: fuga@example.jp
126
+
127
+ EOS
128
+ m = MailParser::Message.new(msg)
129
+ assert_equal(3, m.to.size)
130
+ assert_equal("tommy", m.to[0].addr_spec.local_part)
131
+ assert_equal("tmtm.org", m.to[0].addr_spec.domain)
132
+ assert_equal("TOMITA Masahiro", m.to[0].display_name)
133
+ assert_equal([], m.to[0].comments)
134
+ assert_equal("hoge", m.to[1].addr_spec.local_part)
135
+ assert_equal("example.com", m.to[1].addr_spec.domain)
136
+ assert_equal("", m.to[1].display_name)
137
+ assert_equal([], m.to[1].comments)
138
+ assert_equal("fuga", m.to[2].addr_spec.local_part)
139
+ assert_equal("example.jp", m.to[2].addr_spec.domain)
140
+ assert_equal("", m.to[2].display_name)
141
+ assert_equal([], m.to[2].comments)
142
+ end
143
+
144
+ def test_to_comment()
145
+ msg = StringIO.new(<<EOS)
146
+ To: TOMITA Masahiro <tommy@tmtm.org> (foo), hoge@example.com (bar)
147
+
148
+ EOS
149
+ m = MailParser::Message.new(msg)
150
+ assert_equal(2, m.to.size)
151
+ assert_equal("tommy", m.to[0].addr_spec.local_part)
152
+ assert_equal("tmtm.org", m.to[0].addr_spec.domain)
153
+ assert_equal("TOMITA Masahiro", m.to[0].display_name)
154
+ assert_equal(["(foo)"], m.to[0].comments)
155
+ assert_equal("hoge", m.to[1].addr_spec.local_part)
156
+ assert_equal("example.com", m.to[1].addr_spec.domain)
157
+ assert_equal("", m.to[1].display_name)
158
+ assert_equal(["(bar)"], m.to[1].comments)
159
+ end
160
+
161
+ def test_cc()
162
+ msg = StringIO.new(<<EOS)
163
+ Cc: TOMITA Masahiro <tommy@tmtm.org>
164
+
165
+ EOS
166
+ m = MailParser::Message.new(msg)
167
+ assert_equal(1, m.cc.size)
168
+ assert_equal("tommy", m.cc[0].addr_spec.local_part)
169
+ assert_equal("tmtm.org", m.cc[0].addr_spec.domain)
170
+ assert_equal("TOMITA Masahiro", m.cc[0].display_name)
171
+ assert_equal([], m.cc[0].comments)
172
+ end
173
+
174
+ def test_cc_none()
175
+ msg = StringIO.new(<<EOS)
176
+ From: TOMITA Masahiro <tommy@tmtm.org>
177
+
178
+ EOS
179
+ m = MailParser::Message.new(msg)
180
+ assert_equal([], m.cc)
181
+ end
182
+
183
+ def test_cc_multi()
184
+ msg = StringIO.new(<<EOS)
185
+ Cc: TOMITA Masahiro <tommy@tmtm.org>, hoge@example.com
186
+
187
+ EOS
188
+ m = MailParser::Message.new(msg)
189
+ assert_equal(2, m.cc.size)
190
+ assert_equal("tommy", m.cc[0].addr_spec.local_part)
191
+ assert_equal("tmtm.org", m.cc[0].addr_spec.domain)
192
+ assert_equal("TOMITA Masahiro", m.cc[0].display_name)
193
+ assert_equal([], m.cc[0].comments)
194
+ assert_equal("hoge", m.cc[1].addr_spec.local_part)
195
+ assert_equal("example.com", m.cc[1].addr_spec.domain)
196
+ assert_equal("", m.cc[1].display_name)
197
+ assert_equal([], m.cc[1].comments)
198
+ end
199
+
200
+ def test_cc_multi_header()
201
+ msg = StringIO.new(<<EOS)
202
+ Cc: TOMITA Masahiro <tommy@tmtm.org>, hoge@example.com
203
+ Cc: fuga@example.jp
204
+
205
+ EOS
206
+ m = MailParser::Message.new(msg)
207
+ assert_equal(3, m.cc.size)
208
+ assert_equal("tommy", m.cc[0].addr_spec.local_part)
209
+ assert_equal("tmtm.org", m.cc[0].addr_spec.domain)
210
+ assert_equal("TOMITA Masahiro", m.cc[0].display_name)
211
+ assert_equal([], m.cc[0].comments)
212
+ assert_equal("hoge", m.cc[1].addr_spec.local_part)
213
+ assert_equal("example.com", m.cc[1].addr_spec.domain)
214
+ assert_equal("", m.cc[1].display_name)
215
+ assert_equal([], m.cc[1].comments)
216
+ assert_equal("fuga", m.cc[2].addr_spec.local_part)
217
+ assert_equal("example.jp", m.cc[2].addr_spec.domain)
218
+ assert_equal("", m.cc[2].display_name)
219
+ assert_equal([], m.cc[2].comments)
220
+ end
221
+
222
+ def test_cc_comment()
223
+ msg = StringIO.new(<<EOS)
224
+ Cc: TOMITA Masahiro <tommy@tmtm.org> (foo), hoge@example.com (bar)
225
+
226
+ EOS
227
+ m = MailParser::Message.new(msg)
228
+ assert_equal(2, m.cc.size)
229
+ assert_equal("tommy", m.cc[0].addr_spec.local_part)
230
+ assert_equal("tmtm.org", m.cc[0].addr_spec.domain)
231
+ assert_equal("TOMITA Masahiro", m.cc[0].display_name)
232
+ assert_equal(["(foo)"], m.cc[0].comments)
233
+ assert_equal("hoge", m.cc[1].addr_spec.local_part)
234
+ assert_equal("example.com", m.cc[1].addr_spec.domain)
235
+ assert_equal("", m.cc[1].display_name)
236
+ assert_equal(["(bar)"], m.cc[1].comments)
237
+ end
238
+
239
+ def test_subject()
240
+ msg = StringIO.new(<<EOS)
241
+ Subject: This is a pen.
242
+
243
+ EOS
244
+ m = MailParser::Message.new(msg)
245
+ assert_equal("This is a pen.", m.subject)
246
+ end
247
+
248
+ def test_subject_none()
249
+ msg = StringIO.new(<<EOS)
250
+ X-Subject: This is a pen.
251
+
252
+ EOS
253
+ m = MailParser::Message.new(msg)
254
+ assert_equal("", m.subject)
255
+ end
256
+
257
+ def test_subject_multi_line()
258
+ msg = StringIO.new(<<EOS)
259
+ Subject: This is a pen.
260
+ Is this a pen?
261
+
262
+ EOS
263
+ m = MailParser::Message.new(msg)
264
+ assert_equal("This is a pen. Is this a pen?", m.subject)
265
+ end
266
+
267
+ def test_subject_multi_header()
268
+ msg = StringIO.new(<<EOS)
269
+ Subject: This is a pen.
270
+ Subject: Is this a pen?
271
+
272
+ EOS
273
+ m = MailParser::Message.new(msg)
274
+ assert_equal("This is a pen. Is this a pen?", m.subject)
275
+ end
276
+
277
+ def test_subject_mime()
278
+ msg = StringIO.new(<<EOS)
279
+ Subject: =?us-ascii?q?This_is_a_pen.?=
280
+
281
+ EOS
282
+ m = MailParser::Message.new(msg)
283
+ assert_equal("=?us-ascii?q?This_is_a_pen.?=", m.subject)
284
+ end
285
+
286
+ def test_subject_mime_decode()
287
+ msg = StringIO.new(<<EOS)
288
+ Subject: =?us-ascii?q?This_is_a_pen.?=
289
+
290
+ EOS
291
+ m = MailParser::Message.new(msg, :decode_mime_header=>true)
292
+ assert_equal("This is a pen.", m.subject)
293
+ end
294
+
295
+ def test_subject_mime_decode_charset()
296
+ msg = StringIO.new(<<EOS)
297
+ Subject: =?iso-2022-jp?b?GyRCJCIkJCQmJCgkKhsoQg==?=
298
+
299
+ EOS
300
+ m = MailParser::Message.new(msg, :decode_mime_header=>true, :output_charset=>"utf-8")
301
+ assert_equal("あいうえお", m.subject)
302
+ end
303
+
304
+ def test_subject_mime_decode_unknown_charset()
305
+ msg = StringIO.new(<<EOS)
306
+ Subject: =?xxx?b?GyRCJCIkJCQmJCgkKhsoQg==?=
307
+
308
+ EOS
309
+ m = MailParser::Message.new(msg, :decode_mime_header=>true, :output_charset=>"utf-8")
310
+ assert_equal("=?xxx?b?GyRCJCIkJCQmJCgkKhsoQg==?=", m.subject)
311
+ end
312
+
313
+ def test_subject_mime_decode_charset_converter()
314
+ msg = StringIO.new(<<EOS)
315
+ Subject: =?iso-2022-jp?b?GyRCJCIkJCQmJCgkKhsoQg==?=
316
+
317
+ EOS
318
+ cv = proc{|f,t,s| "abcdefg"}
319
+ m = MailParser::Message.new(msg, :decode_mime_header=>true, :output_charset=>"utf-8", :charset_converter=>cv)
320
+ assert_equal("abcdefg", m.subject)
321
+ end
322
+
323
+ def test_content_type()
324
+ msg = StringIO.new(<<EOS)
325
+ Content-Type: text/plain; charset=us-ascii
326
+
327
+ EOS
328
+ m = MailParser::Message.new(msg)
329
+ assert_equal("text", m.type)
330
+ assert_equal("plain", m.subtype)
331
+ assert_equal("us-ascii", m.charset)
332
+ end
333
+
334
+ def test_content_type_miss()
335
+ msg = StringIO.new(<<EOS)
336
+ Content-Type: text
337
+
338
+ EOS
339
+ m = MailParser::Message.new(msg)
340
+ assert_equal("text", m.type)
341
+ assert_equal("plain", m.subtype)
342
+ assert_equal(nil, m.charset)
343
+ end
344
+
345
+ def test_content_type_none()
346
+ msg = StringIO.new(<<EOS)
347
+
348
+ EOS
349
+ m = MailParser::Message.new(msg)
350
+ assert_equal("text", m.type)
351
+ assert_equal("plain", m.subtype)
352
+ assert_equal(nil, m.charset)
353
+ end
354
+
355
+ def test_content_type_other()
356
+ msg = StringIO.new(<<EOS)
357
+ Content-Type: other
358
+ EOS
359
+ m = MailParser::Message.new(msg)
360
+ assert_equal("other", m.type)
361
+ assert_equal("", m.subtype)
362
+ assert_equal(nil, m.charset)
363
+ end
364
+
365
+ def test_body()
366
+ msg = StringIO.new(<<EOS)
367
+ From: TOMITA Masahiro <tommy@tmtm.org>
368
+ Content-Type: text/plain; charset=us-ascii
369
+
370
+ Test message.
371
+ EOS
372
+ m = MailParser::Message.new(msg)
373
+ assert_equal("Test message.\n", m.body)
374
+ end
375
+
376
+ def test_body_iso2022jp()
377
+ msg = StringIO.new(<<EOS)
378
+ From: TOMITA Masahiro <tommy@tmtm.org>
379
+ Content-Type: text/plain; charset=iso-2022-jp
380
+
381
+ \e\$B\$\"\$\$\$\&\$\(\$\*\e(B
382
+ EOS
383
+ m = MailParser::Message.new(msg)
384
+ assert_equal("\e\$B\$\"\$\$\$\&\$\(\$\*\e(B\n", m.body)
385
+ end
386
+
387
+ def test_body_iso2022jp_charset()
388
+ msg = StringIO.new(<<EOS)
389
+ From: TOMITA Masahiro <tommy@tmtm.org>
390
+ Content-Type: text/plain; charset=iso-2022-jp
391
+
392
+ \e\$B\$\"\$\$\$\&\$\(\$\*\e(B
393
+ EOS
394
+ m = MailParser::Message.new(msg, :output_charset=>"utf8")
395
+ assert_equal("あいうえお\n", m.body)
396
+ end
397
+
398
+ def test_body_with_charset_but_not_text_type()
399
+ msg = StringIO.new(<<EOS)
400
+ From: TOMITA Masahiro <tommy@tmtm.org>
401
+ Content-Type: application/octet-stream; charset=iso-2022-jp
402
+
403
+ \e\$B\$\"\$\$\$\&\$\(\$\*\e(B
404
+ EOS
405
+ m = MailParser::Message.new(msg, :output_charset=>"utf8")
406
+ assert_equal("\e\$B\$\"\$\$\$\&\$\(\$\*\e(B\n", m.body)
407
+ end
408
+
409
+ def test_body_no_charset()
410
+ msg = StringIO.new(<<EOS)
411
+ From: TOMITA Masahiro <tommy@tmtm.org>
412
+ Content-Type: text/plain
413
+
414
+ abcdefg
415
+ EOS
416
+ m = MailParser::Message.new(msg, :output_charset=>"utf8")
417
+ assert_equal("abcdefg\n", m.body)
418
+ end
419
+
420
+ def test_body_preconv
421
+ m = MailParser::Message.new(<<EOS, :output_charset=>"utf8")
422
+ From: TOMITA Masahiro <tommy@tmtm.org>
423
+ Content-Type: text/plain; charset=iso-2022-jp
424
+
425
+ \e$B$3$l$OK\\J8$G$9\e(B
426
+ EOS
427
+ assert_equal "これは本文です\n", m.body
428
+ assert_equal "\e$B$3$l$OK\\J8$G$9\e(B\n", m.body_preconv
429
+ end
430
+
431
+ def test_body_charset_converter
432
+ m = MailParser::Message.new(<<EOS, :output_charset=>"utf8", :charset_converter=>proc{|f,t,s| "abcdefg"})
433
+ From: TOMITA Masahiro <tommy@tmtm.org>
434
+ Content-Type: text/plain; charset=iso-2022-jp
435
+
436
+ \e$B$3$l$OK\\J8$G$9\e(B
437
+ EOS
438
+ assert_equal "abcdefg", m.body
439
+ end
440
+
441
+ def test_body_use_file
442
+ m = MailParser::Message.new(<<EOS, :output_charset=>"utf8", :use_file=>1)
443
+ From: TOMITA Masahiro <tommy@tmtm.org>
444
+ Content-Type: text/plain; charset=iso-2022-jp
445
+
446
+ \e$B$3$l$OK\\J8$G$9\e(B
447
+ EOS
448
+ assert_equal "これは本文です\n", m.body
449
+ assert_equal "\e$B$3$l$OK\\J8$G$9\e(B\n", m.body_preconv
450
+ end
451
+
452
+ def test_filename()
453
+ msg = StringIO.new(<<EOS)
454
+ Content-Type: text/plain; name="filename.txt"
455
+
456
+ EOS
457
+ m = MailParser::Message.new(msg)
458
+ assert_equal("filename.txt", m.filename)
459
+ end
460
+
461
+ def test_filename2()
462
+ msg = StringIO.new(<<EOS)
463
+ Content-Disposition: attachment; filename="filename.txt"
464
+
465
+ EOS
466
+ m = MailParser::Message.new(msg)
467
+ assert_equal("filename.txt", m.filename)
468
+ end
469
+
470
+ def test_filename3()
471
+ msg = StringIO.new(<<EOS)
472
+ Content-Type: text/plain; name="ctype.txt"
473
+ Content-Disposition: attachment; filename="cdisp.txt"
474
+
475
+ EOS
476
+ m = MailParser::Message.new(msg)
477
+ assert_equal("cdisp.txt", m.filename)
478
+ end
479
+
480
+ def test_filename_rfc2231()
481
+ msg = StringIO.new(<<EOS)
482
+ Content-Disposition: attachment; filename*=us-ascii'en'filename.txt
483
+
484
+ EOS
485
+ m = MailParser::Message.new(msg)
486
+ assert_equal("filename.txt", m.filename)
487
+ end
488
+
489
+ def test_filename_rfc2231_charset()
490
+ msg = StringIO.new(<<EOS)
491
+ Content-Disposition: attachment; filename*=iso-2022-jp''%1B$B$%22$$$&$%28$%2A%1B%28B.txt
492
+
493
+ EOS
494
+ m = MailParser::Message.new(msg, :output_charset=>"utf-8")
495
+ assert_equal("あいうえお.txt", m.filename)
496
+ end
497
+
498
+ def test_filename_rfc2231_unknown_charset()
499
+ msg = StringIO.new(<<EOS)
500
+ Content-Disposition: attachment; filename*=xxxx''%1B$B$%22$$$&$%28$%2A%1B%28B.txt
501
+
502
+ EOS
503
+ m = MailParser::Message.new(msg, :output_charset=>"utf-8")
504
+ assert_equal("\e$B$\"$$$&$($*\e(B.txt", m.filename)
505
+ end
506
+
507
+ def test_filename_mime()
508
+ msg = StringIO.new(<<EOS)
509
+ Content-Disposition: attachment; filename="=?us-ascii?q?filename.txt?="
510
+
511
+ EOS
512
+ m = MailParser::Message.new(msg)
513
+ assert_equal("=?us-ascii?q?filename.txt?=", m.filename)
514
+ end
515
+
516
+ def test_filename_mime_decode()
517
+ msg = StringIO.new(<<EOS)
518
+ Content-Disposition: attachment; filename="=?us-ascii?q?filename.txt?="
519
+
520
+ EOS
521
+ m = MailParser::Message.new(msg, :decode_mime_filename=>true)
522
+ assert_equal("filename.txt", m.filename)
523
+ end
524
+
525
+ def test_filename_mime_decode_nofilename()
526
+ msg = StringIO.new(<<EOS)
527
+ Content-Type: text/plain
528
+ EOS
529
+ m = MailParser::Message.new(msg, :decode_mime_filename=>true)
530
+ assert_nil m.filename
531
+ end
532
+
533
+ def test_filename_mime_charset()
534
+ msg = StringIO.new(<<EOS)
535
+ Content-Disposition: attachment; filename="=?iso-2022-jp?q?=1B$B$=22$$$&$=28$=2A=1B=28B.txt?="
536
+
537
+ EOS
538
+ m = MailParser::Message.new(msg, :decode_mime_filename=>true, :output_charset=>"utf-8")
539
+ assert_equal("あいうえお.txt", m.filename)
540
+ end
541
+
542
+ def test_filename_mime_charset_converter()
543
+ msg = StringIO.new(<<EOS)
544
+ Content-Disposition: attachment; filename="=?iso-2022-jp?q?=1B$B$=22$$$&$=28$=2A=1B=28B.txt?="
545
+
546
+ EOS
547
+ cv = proc{|f,t,s| "abcdefg"}
548
+ m = MailParser::Message.new(msg, :decode_mime_filename=>true, :output_charset=>"utf-8", :charset_converter=>cv)
549
+ assert_equal("abcdefg", m.filename)
550
+ end
551
+
552
+ def test_filename_mime_unknown_charset()
553
+ msg = StringIO.new(<<EOS)
554
+ Content-Disposition: attachment; filename="=?xxx?q?=1B$B$=22$$$&$=28$=2A=1B=28B.txt?="
555
+
556
+ EOS
557
+ m = MailParser::Message.new(msg, :decode_mime_filename=>true, :output_charset=>"utf-8")
558
+ assert_equal("=?xxx?q?=1B$B$=22$$$&$=28$=2A=1B=28B.txt?=", m.filename)
559
+ end
560
+
561
+ def test_filename_invalid_crlf()
562
+ msg = StringIO.new(<<EOS)
563
+ Content-Disposition: attachment; filename="aaaa
564
+ bbb"
565
+
566
+ EOS
567
+ m = MailParser::Message.new(msg)
568
+ assert_equal("aaaa bbb", m.filename)
569
+ end
570
+
571
+ def test_extract_message_type()
572
+ msg = StringIO.new(<<EOS)
573
+ From: from1@example.com
574
+ Content-Type: multipart/mixed; boundary="xxxx"
575
+
576
+ --xxxx
577
+ Content-Type: text/plain
578
+
579
+ body1
580
+
581
+ --xxxx
582
+ Content-Type: message/rfc822
583
+
584
+ From: from2@example.com
585
+ Content-Type: text/plain
586
+
587
+ body2
588
+ --xxxx--
589
+ EOS
590
+ m = MailParser::Message.new(msg, :extract_message_type=>true)
591
+ assert_equal("<from1@example.com>", m.from.to_s)
592
+ assert_equal(2, m.part.size)
593
+ assert_equal("text", m.part[0].type)
594
+ assert_equal("body1\n", m.part[0].body)
595
+ assert_equal("message", m.part[1].type)
596
+ assert_equal("<from2@example.com>", m.part[1].message.from.to_s)
597
+ assert_equal("body2", m.part[1].message.body)
598
+ end
599
+
600
+ def test_extract_message_type_header_only
601
+ msg = StringIO.new(<<EOS)
602
+ From: from1@example.com
603
+ Content-Type: multipart/mixed; boundary="xxxx"
604
+
605
+ --xxxx
606
+ Content-Type: text/plain
607
+
608
+ body1
609
+
610
+ --xxxx
611
+ Content-Type: message/rfc822
612
+
613
+ From: from2@example.com
614
+ Content-Type: text/plain
615
+ --xxxx--
616
+ EOS
617
+ m = MailParser::Message.new(msg, :extract_message_type=>true)
618
+ assert_equal("<from1@example.com>", m.from.to_s)
619
+ assert_equal(2, m.part.size)
620
+ assert_equal("text", m.part[0].type)
621
+ assert_equal("body1\n", m.part[0].body)
622
+ assert_equal("message", m.part[1].type)
623
+ assert_equal("<from2@example.com>", m.part[1].message.from.to_s)
624
+ assert_equal("", m.part[1].message.body)
625
+ end
626
+
627
+ def test_extract_message_type_skip_body()
628
+ msg = StringIO.new(<<EOS)
629
+ From: from1@example.com
630
+ Content-Type: multipart/mixed; boundary="xxxx"
631
+
632
+ --xxxx
633
+ Content-Type: text/plain
634
+
635
+ body1
636
+
637
+ --xxxx
638
+ Content-Type: message/rfc822
639
+
640
+ From: from2@example.com
641
+ Content-Type: text/plain
642
+
643
+ body2
644
+ --xxxx--
645
+ EOS
646
+ m = MailParser::Message.new(msg, :extract_message_type=>true, :skip_body=>true)
647
+ assert_equal("<from1@example.com>", m.from.to_s)
648
+ assert_equal(2, m.part.size)
649
+ assert_equal("text", m.part[0].type)
650
+ assert_equal("", m.part[0].body)
651
+ assert_equal("message", m.part[1].type)
652
+ assert_equal("<from2@example.com>", m.part[1].message.from.to_s)
653
+ assert_equal("", m.part[1].message.body)
654
+ end
655
+
656
+ def test_extract_message_type_text_body_only()
657
+ msg = StringIO.new(<<EOS)
658
+ From: from1@example.com
659
+ Content-Type: multipart/mixed; boundary="xxxx"
660
+
661
+ --xxxx
662
+ Content-Type: text/plain
663
+
664
+ body1
665
+
666
+ --xxxx
667
+ Content-Type: message/rfc822
668
+
669
+ From: from2@example.com
670
+ Content-Type: text/plain
671
+
672
+ body2
673
+
674
+ --xxxx--
675
+ EOS
676
+ m = MailParser::Message.new(msg, :extract_message_type=>true, :text_body_only=>true)
677
+ assert_equal("<from1@example.com>", m.from.to_s)
678
+ assert_equal(2, m.part.size)
679
+ assert_equal("text", m.part[0].type)
680
+ assert_equal("body1\n", m.part[0].body)
681
+ assert_equal("message", m.part[1].type)
682
+ assert_equal("<from2@example.com>", m.part[1].message.from.to_s)
683
+ assert_equal("body2\n", m.part[1].message.body)
684
+ end
685
+
686
+ def test_extract_multipart_alternative_attach()
687
+ msg = StringIO.new(<<EOS)
688
+ From: from1@example.com
689
+ Content-Type: multipart/mixed; boundary="xxxx"
690
+
691
+ --xxxx
692
+ Content-Type: multipart/alternative;
693
+ boundary="yyyy"
694
+
695
+ --yyyy
696
+ Content-Type: text/plain; charset=iso-2022-jp
697
+
698
+ hoge
699
+
700
+ --yyyy
701
+ Content-Type: text/html; charset=iso-2022-jp
702
+
703
+ fuga html
704
+
705
+ --yyyy--
706
+
707
+ --xxxx
708
+ Content-Type: application/octet-stream; name="attach.txt"
709
+ Content-Disposition: attachment; filename="attach.txt"
710
+
711
+ attached file
712
+ --xxxx--
713
+ EOS
714
+ m = MailParser::Message.new(msg)
715
+ assert_equal(2, m.part.size)
716
+ assert_equal(2, m.part[0].part.size)
717
+ assert_equal("hoge\n", m.part[0].part[0].body)
718
+ assert_equal("fuga html\n", m.part[0].part[1].body)
719
+ assert_equal("attached file", m.part[1].body)
720
+ end
721
+
722
+ def test_extract_no_boundary()
723
+ msg = StringIO.new(<<EOS)
724
+ From: from@example.com
725
+ Content-Type: multipart/mixed; boundary="xxx"
726
+
727
+ hoge
728
+ hoge
729
+ EOS
730
+ m = MailParser::Message.new(msg)
731
+ assert_equal("", m.body)
732
+ assert_equal([], m.part)
733
+ end
734
+
735
+ def test_extract_no_end_boundary()
736
+ msg = StringIO.new(<<EOS)
737
+ From: from@example.com
738
+ Content-Type: multipart/mixed; boundary="xxx"
739
+
740
+ --xxx
741
+ Content-Type: text/plain
742
+
743
+ hoge
744
+ hoge
745
+ EOS
746
+ m = MailParser::Message.new(msg)
747
+ assert_equal(1, m.part.size)
748
+ assert_equal("hoge\nhoge\n", m.part[0].body)
749
+ end
750
+
751
+ def test_extract_no_end_boundary_nest()
752
+ msg = StringIO.new(<<EOS)
753
+ From: from@example.com
754
+ Content-Type: multipart/mixed; boundary="xxx"
755
+
756
+ --xxx
757
+ Content-Type: multipart/mixed; boundary="yyy"
758
+
759
+ --yyy
760
+ Content-Type: text/plain
761
+
762
+ hoge
763
+ hoge
764
+
765
+ --xxx
766
+ Content-Type: text/plain
767
+
768
+ fuga
769
+
770
+ --xxx--
771
+ EOS
772
+ m = MailParser::Message.new(msg)
773
+ assert_equal(2, m.part.size)
774
+ assert_equal(1, m.part[0].part.size)
775
+ assert_equal("hoge\nhoge\n", m.part[0].part[0].body)
776
+ assert_equal("fuga\n", m.part[1].body)
777
+ end
778
+
779
+ def test_parse_no_header_delimiter()
780
+ msg = StringIO.new <<EOS
781
+ Subject: hoge
782
+ hogehoge
783
+ EOS
784
+ m = MailParser::Message.new msg
785
+ assert_equal "hoge", m.subject
786
+ assert_equal "hogehoge\n", m.body
787
+ end
788
+
789
+ def test_parse_header_only_part()
790
+ msg = StringIO.new <<EOS
791
+ Content-Type: multipart/mixed; boundary=abcdefg
792
+
793
+ --abcdefg
794
+ Content-Type: text/plain
795
+ --abcdefg
796
+ Content-Type: text/plain
797
+
798
+ hoge
799
+
800
+ --abcdefg--
801
+ EOS
802
+ m = MailParser::Message.new msg
803
+ assert_equal 2, m.part.size
804
+ assert_equal "", m.part[0].body
805
+ assert_equal "hoge\n", m.part[1].body
806
+ end
807
+
808
+ def test_parse_header_only_part2()
809
+ msg = StringIO.new <<EOS
810
+ Content-Type: multipart/mixed; boundary=abcdefg
811
+
812
+ --abcdefg
813
+ Content-Type: multipart/mixed; boundary=xyz
814
+ --abcdefg
815
+ Content-Type: text/plain
816
+
817
+ hoge
818
+
819
+ --abcdefg--
820
+ EOS
821
+ m = MailParser::Message.new msg
822
+ assert_equal 2, m.part.size
823
+ assert_equal "", m.part[0].body
824
+ assert_equal "hoge\n", m.part[1].body
825
+ end
826
+
827
+ def test_parse_last_crlf
828
+ msg = StringIO.new <<EOS
829
+ Content-Type: multipart/mixed; boundary=abcdefg
830
+
831
+ --abcdefg
832
+ Content-Type: multipart/mixed; boundary=xyz
833
+ --abcdefg
834
+ Content-Type: text/plain
835
+ Content-Transfer-Encoding: base64
836
+
837
+ aG9nZQo=
838
+ --abcdefg--
839
+ EOS
840
+ m = MailParser::Message.new msg
841
+ assert_equal 2, m.part.size
842
+ assert_equal "", m.part[0].body
843
+ assert_equal "hoge\n", m.part[1].body
844
+ end
845
+
846
+ def test_raw_single_part
847
+ msg = StringIO.new(<<EOS)
848
+ From: from@example.com
849
+ Content-Type: text/plain
850
+
851
+ hogehoge
852
+
853
+ fugafuga
854
+ EOS
855
+ m = MailParser::Message.new msg, :keep_raw=>true
856
+ assert_equal msg.string, m.raw
857
+ end
858
+
859
+ def test_raw_multi_part_nest
860
+ msg = StringIO.new(<<EOS)
861
+ From: from@example.com
862
+ Content-Type: multipart/mixed; boundary="xxx"
863
+
864
+ --xxx
865
+ Content-Type: multipart/mixed; boundary="yyy"
866
+
867
+ --yyy
868
+ Content-Type: text/plain
869
+
870
+ hoge
871
+ hoge
872
+ --yyy
873
+ Content-Type: text/plain
874
+
875
+ hoge
876
+ hoge
877
+ --yyy--
878
+
879
+ --xxx
880
+ Content-Type: text/plain
881
+
882
+ fuga
883
+ --xxx--
884
+ EOS
885
+ m = MailParser::Message.new msg, :keep_raw=>true
886
+ assert_equal msg.string, m.raw
887
+ assert_equal <<EOS, m.part[0].part[0].raw
888
+ Content-Type: text/plain
889
+
890
+ hoge
891
+ hoge
892
+ EOS
893
+ assert_equal <<EOS, m.part[1].raw
894
+ Content-Type: text/plain
895
+
896
+ fuga
897
+ EOS
898
+ end
899
+
900
+ def test_raw_message_part
901
+ msg = StringIO.new(<<EOS)
902
+ From: from1@example.com
903
+ Content-Type: multipart/mixed; boundary="xxxx"
904
+
905
+ --xxxx
906
+ Content-Type: text/plain
907
+
908
+ body1
909
+
910
+ --xxxx
911
+ Content-Type: message/rfc822
912
+
913
+ From: from2@example.com
914
+ Content-Type: text/plain
915
+
916
+ body2
917
+ --xxxx--
918
+ EOS
919
+ m = MailParser::Message.new msg, :keep_raw=>true
920
+ assert_equal msg.string, m.raw
921
+ assert_equal <<EOS, m.part[0].raw
922
+ Content-Type: text/plain
923
+
924
+ body1
925
+
926
+ EOS
927
+ assert_equal <<EOS, m.part[1].raw
928
+ Content-Type: message/rfc822
929
+
930
+ From: from2@example.com
931
+ Content-Type: text/plain
932
+
933
+ body2
934
+ EOS
935
+ end
936
+
937
+ def test_raw_message_part_header_only
938
+ msg = StringIO.new(<<EOS)
939
+ From: from1@example.com
940
+ Content-Type: multipart/mixed; boundary="xxxx"
941
+
942
+ --xxxx
943
+ Content-Type: text/plain
944
+
945
+ body1
946
+
947
+ --xxxx
948
+ Content-Type: message/rfc822
949
+
950
+ From: from2@example.com
951
+ Content-Type: text/plain
952
+ --xxxx--
953
+ EOS
954
+ m = MailParser::Message.new msg, :keep_raw=>true
955
+ assert_equal msg.string, m.raw
956
+ assert_equal <<EOS, m.part[0].raw
957
+ Content-Type: text/plain
958
+
959
+ body1
960
+
961
+ EOS
962
+ assert_equal <<EOS, m.part[1].raw
963
+ Content-Type: message/rfc822
964
+
965
+ From: from2@example.com
966
+ Content-Type: text/plain
967
+ EOS
968
+ end
969
+
970
+ def test_raw_with_continuous_header
971
+ msg = StringIO.new(<<EOS)
972
+ From: from1@example.com
973
+ Subject: hogehoge
974
+ fugafuga
975
+
976
+ body1
977
+ EOS
978
+ m = MailParser::Message.new msg, :keep_raw=>true
979
+ assert_equal <<EOS, m.raw
980
+ From: from1@example.com
981
+ Subject: hogehoge
982
+ fugafuga
983
+
984
+ body1
985
+ EOS
986
+ end
987
+
988
+ def test_raw_and_use_file
989
+ msg = StringIO.new(<<EOS)
990
+ From: from@example.com
991
+ Content-Type: text/plain
992
+
993
+ hogehoge
994
+
995
+ fugafuga
996
+ EOS
997
+ m = MailParser::Message.new msg, :keep_raw=>true, :use_file=>1
998
+ assert_equal msg.string, m.raw
999
+ end
1000
+ end
1001
+
1002
+ class TC_DelimIO < Test::Unit::TestCase
1003
+ include MailParser
1004
+ def setup()
1005
+ end
1006
+ def teardown()
1007
+ end
1008
+
1009
+ def test_gets
1010
+ s = StringIO.new <<EOS
1011
+ aaaa
1012
+ bbbb
1013
+ cccc
1014
+ dddd
1015
+ EOS
1016
+ dio = DelimIO.new(DelimIO.new(s), ["cccc"])
1017
+ assert_equal "aaaa\n", dio.gets
1018
+ assert_equal "bbbb\n", dio.gets
1019
+ assert_equal nil, dio.gets
1020
+ assert_equal true, dio.eof?
1021
+ dio.ungets
1022
+ assert_equal false, dio.eof?
1023
+ assert_equal "bbbb\n", dio.gets
1024
+ assert_equal nil, dio.gets
1025
+ assert_equal true, dio.eof?
1026
+ end
1027
+
1028
+ def test_each_line
1029
+ s = StringIO.new <<EOS
1030
+ aaaa
1031
+ bbbb
1032
+ cccc
1033
+ dddd
1034
+ EOS
1035
+ dio = DelimIO.new(DelimIO.new(s))
1036
+ ret = []
1037
+ dio.each_line do |line|
1038
+ ret << line
1039
+ end
1040
+ assert_equal ["aaaa\n","bbbb\n","cccc\n","dddd\n"], ret
1041
+ assert_equal true, dio.eof?
1042
+ end
1043
+
1044
+ def test_each_line_delim
1045
+ s = StringIO.new <<EOS
1046
+ aaaa
1047
+ bbbb
1048
+ cccc
1049
+ dddd
1050
+ EOS
1051
+ dio = DelimIO.new(DelimIO.new(s), ["cccc"])
1052
+ ret = []
1053
+ dio.each_line do |line|
1054
+ ret << line
1055
+ end
1056
+ assert_equal ["aaaa\n","bbbb\n"], ret
1057
+ assert_equal true, dio.eof?
1058
+ end
1059
+
1060
+ def test_ungets
1061
+ s = StringIO.new <<EOS
1062
+ aaaa
1063
+ bbbb
1064
+ cccc
1065
+ dddd
1066
+ EOS
1067
+ dio = DelimIO.new(DelimIO.new(s), ["cccc"])
1068
+ ret = []
1069
+ dio.each_line do |line|
1070
+ ret << line
1071
+ end
1072
+ assert_equal ["aaaa\n","bbbb\n"], ret
1073
+ assert_equal true, dio.eof?
1074
+ dio.ungets
1075
+ assert_equal false, dio.eof?
1076
+ assert_equal "bbbb\n", dio.gets
1077
+ end
1078
+
1079
+ def test_base64_body
1080
+ msg = <<EOS
1081
+ Content-Transfer-Encoding: base64
1082
+
1083
+ QUJDREVGR0hJSktMTU4=
1084
+ EOS
1085
+ mp = MailParser::Message.new msg
1086
+ assert_equal "ABCDEFGHIJKLMN", mp.body
1087
+ end
1088
+
1089
+ def test_quoted_printable_body
1090
+ msg = <<EOS
1091
+ Content-Transfer-Encoding: quoted-printable
1092
+
1093
+ =41=42=43=44=45=46=47=48=49=4A=4B=4C=4D=4E=
1094
+ EOS
1095
+ mp = MailParser::Message.new msg
1096
+ assert_equal "ABCDEFGHIJKLMN", mp.body
1097
+ end
1098
+
1099
+ def test_uuencode_body
1100
+ msg = <<EOS
1101
+ Content-Transfer-Encoding: x-uuencode
1102
+
1103
+ begin 644 hoge
1104
+ M04)#1$5&1TA)2DM,34Y/4%%24U155E=865HP,3(S-#4V-S@Y86)C9&5F9VAI
1105
+ 1:FML;6YO<'%R<W1U=G=X>7H`
1106
+ `
1107
+ end
1108
+ EOS
1109
+ mp = MailParser::Message.new msg
1110
+ assert_equal "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrstuvwxyz", mp.body
1111
+ end
1112
+
1113
+ end
1114
+
1115
+ class TC_DataBuffer < Test::Unit::TestCase
1116
+ def test_string
1117
+ b = MailParser::DataBuffer.new(nil)
1118
+ assert_equal '', b.str
1119
+ b << 'hogehoge'
1120
+ b << 'fugafuga'
1121
+ assert_equal 'hogehogefugafuga', b.str
1122
+ end
1123
+ def test_file
1124
+ b = MailParser::DataBuffer.new(1)
1125
+ assert_equal '', b.str
1126
+ b << 'hogehoge'
1127
+ b << 'fugafuga'
1128
+ assert_equal 'hogehogefugafuga', b.str
1129
+ end
1130
+ end