diff --git a/emailcommon/src/com/android/emailcommon/internet/Rfc822Output.java b/emailcommon/src/com/android/emailcommon/internet/Rfc822Output.java index 6aa70d334..36b72c5db 100644 --- a/emailcommon/src/com/android/emailcommon/internet/Rfc822Output.java +++ b/emailcommon/src/com/android/emailcommon/internet/Rfc822Output.java @@ -29,6 +29,7 @@ import android.content.Context; import android.database.Cursor; import android.net.Uri; import android.text.Html; +import android.text.TextUtils; import android.util.Base64; import android.util.Base64OutputStream; @@ -88,17 +89,21 @@ public class Rfc822Output { /** * Returns an HTML encoded message alternate */ - private static String getHtmlAlternate(Body body) { + /*package*/ static String getHtmlAlternate(Body body, boolean useSmartReply) { if (body.mHtmlReply == null) { return null; } StringBuffer altMessage = new StringBuffer(); - altMessage.append(body.mTextContent.replaceAll("\\r?\\n", "
")); + String htmlContent = TextUtils.htmlEncode(body.mTextContent); // Escape HTML reserved chars + altMessage.append(htmlContent.replaceAll("\\r?\\n", "
")); if (body.mIntroText != null) { - altMessage.append(body.mIntroText.replaceAll("\\r?\\n", "
")); + String htmlIntro = TextUtils.htmlEncode(body.mIntroText); + altMessage.append(htmlIntro.replaceAll("\\r?\\n", "
")); + } + if (!useSmartReply) { + String htmlBody = getHtmlBody(body.mHtmlReply); + altMessage.append(htmlBody); } - String htmlBody = getHtmlBody(body.mHtmlReply); - altMessage.append(htmlBody); return altMessage.toString(); } @@ -156,7 +161,7 @@ public class Rfc822Output { } } messageBody[TEXT_BODY_IDX] = text; - messageBody[HTML_BODY_IDX] = getHtmlAlternate(body); + messageBody[HTML_BODY_IDX] = getHtmlAlternate(body, useSmartReply); return messageBody; } @@ -167,13 +172,7 @@ public class Rfc822Output { * @param context system context for accessing the provider * @param messageId the message to write out * @param out the output stream to write the message to -<<<<<<< HEAD:emailcommon/src/com/android/emailcommon/internet/Rfc822Output.java - * @param useSmartReply whether or not quoted text is appended to a reply/forward - * - * TODO alternative parts (e.g. text+html) are not supported here. -======= * @param useSmartReply whether or not to append quoted text if this is a reply/forward ->>>>>>> 5912e7c... Attach original HTML message on forward/reply:src/com/android/emailcommon/internet/Rfc822Output.java */ public static void writeTo(Context context, long messageId, OutputStream out, boolean useSmartReply, boolean sendBcc) throws IOException, MessagingException { diff --git a/tests/src/com/android/emailcommon/internet/Rfc822OutputTests.java b/tests/src/com/android/emailcommon/internet/Rfc822OutputTests.java index dc5999292..07570f32e 100644 --- a/tests/src/com/android/emailcommon/internet/Rfc822OutputTests.java +++ b/tests/src/com/android/emailcommon/internet/Rfc822OutputTests.java @@ -22,6 +22,7 @@ import com.android.emailcommon.internet.Rfc822Output; import com.android.emailcommon.mail.MessagingException; import com.android.emailcommon.provider.EmailContent; import com.android.emailcommon.provider.EmailContent.Attachment; +import com.android.emailcommon.provider.EmailContent.Body; import com.android.emailcommon.provider.EmailContent.Message; import org.apache.james.mime4j.field.Field; @@ -52,8 +53,15 @@ public class Rfc822OutputTests extends ProviderTestCase2 { private static final String RECIPIENT_CC = "recipient-cc@android.com"; private static final String SUBJECT = "This is the subject"; private static final String BODY = "This is the body. This is also the body."; + private static final String REPLY_TEXT_BODY = "This is the body. This is also the body."; + /** HTML reply body */ + private static final String BODY_HTML_REPLY = + "This is the body.
This is also the body."; private static final String TEXT = "Here is some new text."; + private static String REPLY_INTRO_TEXT = "\n\n" + SENDER + " wrote:\n\n"; + private static String REPLY_INTRO_HTML = "

" + SENDER + " wrote:

"; + private Context mMockContext; private String mForwardIntro; private String mReplyIntro; @@ -77,6 +85,25 @@ public class Rfc822OutputTests extends ProviderTestCase2 { // TODO Write test that ensures that bcc is handled properly (i.e. sent/not send depending // on the flag passed to writeTo + private Message createTestMessage(String text, boolean save) { + Message message = new Message(); + message.mText = text; + message.mFrom = SENDER; + message.mFlags = Message.FLAG_TYPE_REPLY; + message.mTextReply = REPLY_TEXT_BODY; + message.mHtmlReply = BODY_HTML_REPLY; + message.mIntroText = REPLY_INTRO_TEXT; + if (save) { + message.save(mMockContext); + } + return message; + } + + private Body createTestBody(Message message) { + Body body = Body.restoreBodyWithMessageId(mMockContext, message.mId); + return body; + } + /** * Test for buildBodyText(). * Compare with expected values. @@ -288,6 +315,52 @@ public class Rfc822OutputTests extends ProviderTestCase2 { assertEquals(BODY_RESULT3, actual); } + /** + * Tests that the entire HTML alternate string is valid for text entered by + * the user. We don't test all permutations of forwarded HTML here because + * that is verified by testGetHtmlBody(). + */ + public void testGetHtmlAlternate() { + Message message = createTestMessage(TEXT, true); + Body body = createTestBody(message); + String html; + + // Generic case + html = Rfc822Output.getHtmlAlternate(body, false); + assertEquals(TEXT + REPLY_INTRO_HTML + BODY_HTML_REPLY, html); + + // "smart reply" enabled; html body should not be added + html = Rfc822Output.getHtmlAlternate(body, true); + assertEquals(TEXT + REPLY_INTRO_HTML, html); + + // HTML special characters; dependent upon TextUtils#htmlEncode() + message.mId = -1; // Changing the message; need to reset the id + message.mText = "<>&'\""; + message.save(mMockContext); + body = createTestBody(message); + + html = Rfc822Output.getHtmlAlternate(body, false); + assertEquals("<>&'"" + REPLY_INTRO_HTML + BODY_HTML_REPLY, html); + + // Newlines in user text + message.mId = -1; // Changing the message; need to reset the id + message.mText = "dos\r\nunix\nthree\r\n\n\n"; + message.save(mMockContext); + body = createTestBody(message); + + html = Rfc822Output.getHtmlAlternate(body, false); + assertEquals("dos
unix
three


" + REPLY_INTRO_HTML + BODY_HTML_REPLY, html); + + // Null HTML reply + message.mId = -1; // Changing the message; need to reset the id + message.mHtmlReply = null; + message.save(mMockContext); + body = createTestBody(message); + + html = Rfc822Output.getHtmlAlternate(body, false); + assertNull(html); + } + /** * Confirm that the constructed message includes "MIME-VERSION: 1.0" */