diff --git a/MessageBuilder.cs b/MessageBuilder.cs
index 31e367f..14395e6 100644
--- a/MessageBuilder.cs
+++ b/MessageBuilder.cs
@@ -352,21 +352,25 @@ internal static void AddBodypart(this MailMessage message, Bodypart part, string
// Attachments collection.
bool hasName = part.Parameters.ContainsKey("name");
+ // Check for alternative view.
+ string ContentType = ParseMIMEField(message.Headers["Content-Type"])["value"];
+ bool preferAlternative = string.Compare(ContentType, "multipart/alternative", true) == 0;
+
// If the MailMessage's Body fields haven't been initialized yet, put it there. Some weird
// (i.e. spam) mails like to omit content-types so we don't check for that here and just
// assume it's text.
if (String.IsNullOrEmpty(message.Body) &&
- part.Disposition.Type != ContentDispositionType.Attachment) {
+ !(part.Disposition.Type == ContentDispositionType.Attachment ||
+ (part.Disposition.Type == ContentDispositionType.Unknown &&
+ preferAlternative == false && hasName))) {
+ //if (String.IsNullOrEmpty(message.Body) &&
+ // !(part.Disposition.Type == ContentDispositionType.Attachment)) {
message.Body = encoding.GetString(bytes);
message.BodyEncoding = encoding;
message.IsBodyHtml = part.Subtype.ToLower() == "html";
return;
}
- // Check for alternative view.
- string ContentType = ParseMIMEField(message.Headers["Content-Type"])["value"];
- bool preferAlternative = string.Compare(ContentType, "multipart/alternative", true) == 0;
-
// Many attachments are missing the disposition-type. If it's not defined as alternative
// and it has a name attribute, assume it is Attachment rather than an AlternateView.
if (part.Disposition.Type == ContentDispositionType.Attachment ||
diff --git a/Tests/MessageBuilderTest.cs b/Tests/MessageBuilderTest.cs
index de3b4fc..067ab27 100644
--- a/Tests/MessageBuilderTest.cs
+++ b/Tests/MessageBuilderTest.cs
@@ -1,4 +1,5 @@
-using Microsoft.VisualStudio.TestTools.UnitTesting;
+using System;
+using Microsoft.VisualStudio.TestTools.UnitTesting;
using System.IO;
using System.Linq;
using System.Net.Mail;
@@ -128,6 +129,40 @@ public void MessageWithMultipartMixedAttachment() {
"Attachment name missmatch.");
}
+ ///
+ /// Creates a MailMessage instance from an RFC822/MIME string containing an attachment without
+ /// a disposition and an empty body.
+ ///
+ [TestMethod]
+ [TestCategory("BuildMessageFromMIME822")]
+ public void MessageWithMultipartMixedAttachmentAndEmptyBody()
+ {
+ // The multiparts is manipulated base64 data and not the real files.
+ MailMessage m = MessageBuilder.FromMIME822(Properties.Resources.MailWithoutDispositionEmptyBody);
+
+ // Check the From header.
+ Assert.AreEqual("", m.From.DisplayName, "Expected no From displayname.");
+ Assert.AreEqual("invxxxxx@xxxxx.com", m.From.Address, "Unexpected From address.");
+ // Check the To header.
+ Assert.AreEqual(1, m.To.Count, "Unexpected To address count.");
+ Assert.AreEqual("", m.To[0].DisplayName, "Expected no To displayname.");
+ Assert.AreEqual("faktxxx@xxxxxx.se", m.To[0].Address, "Unexpected To address.");
+ Assert.AreEqual("Fakt__xxxx___xxxx___07_02_2013", m.Subject, "Unexpected Subject.");
+ Assert.AreEqual(
+ "multipart/mixed;\tboundary=\"--boundary_0_6cb33448-390c-4f02-b75a-2738f1d6dd45\"",
+ m.Headers["Content-Type"], "Unexpected Content-Type");
+ Assert.IsFalse(m.IsBodyHtml, "Expected non HTML body");
+ // Ensure that the body encoding is null, since there is no body.
+ Assert.AreEqual(null, m.BodyEncoding, "Expected null Body Encoding.");
+ // Ensure that the body is empty.
+ Assert.AreEqual(String.Empty, m.Body);
+ Assert.AreEqual(0, m.AlternateViews.Count, "AlternateViews count missmatch.");
+ // Ensure that the attachment is treated correctly as an attachment.
+ Assert.AreEqual(1, m.Attachments.Count, "Attachment count missmatch.");
+ Assert.AreEqual("Fakt_fil_xxxx_20130207.pdf", m.Attachments[0].Name,
+ "Attachment name missmatch.");
+ }
+
///
/// Ensures a malformed, invalid or missing From header is handled properly. See issue #50.
///
diff --git a/Tests/Properties/Resources.Designer.cs b/Tests/Properties/Resources.Designer.cs
index 22fab27..2c9a820 100644
--- a/Tests/Properties/Resources.Designer.cs
+++ b/Tests/Properties/Resources.Designer.cs
@@ -1,7 +1,7 @@
//------------------------------------------------------------------------------
//
// This code was generated by a tool.
-// Runtime Version:4.0.30319.18408
+// Runtime Version:4.0.30319.34209
//
// Changes to this file may cause incorrect behavior and will be lost if
// the code is regenerated.
@@ -257,6 +257,27 @@ internal static string MailWithoutDisposition {
}
}
+ ///
+ /// Looks up a localized string similar to Received: from xxx.xxxxx.com (xx.xxxx.com [123.45.67.89])
+ /// by xxxx.asxxx.se (Postfix) with ESMTP id E357F2CCC6A
+ /// for <faktxxx@xxxxxx.se>; Thu, 7 Feb 2013 17:12:05 +0100 (CET)
+ ///MIME-Version: 1.0
+ ///From: <invxxxxx@xxxxx.com>
+ ///To: <faktxxx@xxxxxx.se>
+ ///Date: Thu, 7 Feb 2013 17:12:02 +0100
+ ///Subject: Fakt__xxxx___xxxx___07_02_2013
+ ///Content-Type: multipart/mixed;
+ /// boundary="--boundary_0_6cb33448-390c-4f02-b75a-2738f1d6dd45"
+ ///Message-ID: <44967f46-57cc-47c4-ab9f-1c450e1d87bb@XXXXI0123.xx.xxxx.com>
+ ///
+ ///----boundar [rest of string was truncated]";.
+ ///
+ internal static string MailWithoutDispositionEmptyBody {
+ get {
+ return ResourceManager.GetString("MailWithoutDispositionEmptyBody", resourceCulture);
+ }
+ }
+
///
/// Looks up a localized string similar to Return-Path: <xxxxxxx@canon.no>
///Received: from mail-gtw.canon.no (mail.canon.no [194.248.71.4])
@@ -289,7 +310,7 @@ internal static string MailWithQuotedPrintables {
///X-Mailer: tie-bomber
///Date: Sat, 04 Sep 1999 18:26:50 +0900
///Message-ID: <19990904092850.5963.foo@example.org>
- ///Content-Type: multipart/mixed; boun [rest of string was truncated]";.
+ ///Content-Type: multipart [rest of string was truncated]";.
///
internal static string MailWithRfc2231Headers {
get {
@@ -310,7 +331,7 @@ internal static string MailWithRfc2231Headers {
///X-Mailer: tie-bomber
///Date: Sat, 04 Sep 1999 18:26:50 +0900
///Message-ID: <19990904092850.5963.foo@example.org>
- ///Content-Type: multipart/mixed; boun [rest of string was truncated]";.
+ ///Content-Type: multipart [rest of string was truncated]";.
///
internal static string MailWithRfc2231Headers2 {
get {
diff --git a/Tests/Properties/Resources.resx b/Tests/Properties/Resources.resx
index 1e07a20..55ee4b7 100644
--- a/Tests/Properties/Resources.resx
+++ b/Tests/Properties/Resources.resx
@@ -161,6 +161,9 @@ X-MimeOLE: Produced By Microsoft MimeOLE V6.0.6002.18463
..\Resources\MailWithoutDisposition.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;Windows-1252
+
+ ..\Resources\MailWithoutDispositionEmptyBody.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;Windows-1252
+
..\Resources\MailWithQuotedPrintables.txt;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;Windows-1252
diff --git a/Tests/Resources/MailWithoutDispositionEmptyBody.txt b/Tests/Resources/MailWithoutDispositionEmptyBody.txt
new file mode 100644
index 0000000..a35f00a
--- /dev/null
+++ b/Tests/Resources/MailWithoutDispositionEmptyBody.txt
@@ -0,0 +1,26 @@
+Received: from xxx.xxxxx.com (xx.xxxx.com [123.45.67.89])
+ by xxxx.asxxx.se (Postfix) with ESMTP id E357F2CCC6A
+ for ; Thu, 7 Feb 2013 17:12:05 +0100 (CET)
+MIME-Version: 1.0
+From:
+To:
+Date: Thu, 7 Feb 2013 17:12:02 +0100
+Subject: Fakt__xxxx___xxxx___07_02_2013
+Content-Type: multipart/mixed;
+ boundary="--boundary_0_6cb33448-390c-4f02-b75a-2738f1d6dd45"
+Message-ID: <44967f46-57cc-47c4-ab9f-1c450e1d87bb@XXXXI0123.xx.xxxx.com>
+
+----boundary_0_6cb33448-390c-4f02-b75a-2738f1d6dd45
+Content-Type: text/plain; charset="utf-8"
+Content-Transfer-Encoding: base64
+
+----boundary_0_6cb33448-390c-4f02-b75a-2738f1d6dd45
+Content-Type: application/octet-stream; name="Fakt_fil_xxxx_20130207.pdf"
+Content-Transfer-Encoding: base64
+
+JVBERi0xLjMNCiX15Pb8DQoNCjcgMCBvYmogPDwgL1R5cGUgL1hPYmplY3QNCi9TdWJ0eXBl
+IC9JbWFnZQ0KL05hbWUgL0kxDQovV2lkdGggNDYxDQovSGVpZ2h0IDExMA0KL0JpdHNQZXJD
+b21wb25lbnQgOA0KL0NvbG9yU3BhY2UgL0RldmljZUdyYXkNCi9MZW5ndGggOTUyOCAvRmls
+dGVyIFsgL0FTQ0lJODVEZWNvZGUgL0ZsYXRlRGVjb2RlIF0gPj4NCnN0cmVhbQ0KR2IiLyxN
+NDU0MFtKcD8/V14uckZCMXQuLUBjRVxBclFMVkgzJW1iWWR0bEpcRkVdO21faT==
+----boundary_0_6cb33448-390c-4f02-b75a-2738f1d6dd45--
diff --git a/Tests/Tests.csproj b/Tests/Tests.csproj
index fda401f..f4bd213 100644
--- a/Tests/Tests.csproj
+++ b/Tests/Tests.csproj
@@ -85,6 +85,7 @@
ResXFileCodeGenerator
Resources.Designer.cs
+ Designer
@@ -111,6 +112,9 @@
+
+
+