We are experiencing an issue while parsing meetings/appointments.
Description:
-
We created an meeting invite using outlook with different special characters. (Sample_Meeting_For_JIRA.eml)
-
On parsing this eml file using the below code we were able to generate a .pst file, which had all the special characters improper.(Sample meeting With Forced RTF false.eml, .eml extracted from the .pst)
-
On commenting the line mapiConversionOption.setForcedRtfBodyForAppointment(false); from the below code and generating a .pst, we found the error was no longer observed. But we cannot afford to comment this line as it breaks the html formatting for the mail. (Sample meeting With Forced RTF as default.eml)
Please refer to the uploaded .zip file for the mentioned .eml files. SampleEmails.zip (11.2 KB)
Below is a sample test case that is failing:
import static org.junit.Assert.assertTrue;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.Charset;
import java.util.Date;
import java.util.Enumeration;
import java.util.Map;
import java.util.Properties;
import javax.mail.BodyPart;
import javax.mail.Header;
import javax.mail.MessagingException;
import javax.mail.Multipart;
import javax.mail.Session;
import javax.mail.internet.MimeMessage;
import javax.mail.util.SharedByteArrayInputStream;import org.apache.commons.io.IOUtils;
import org.junit.Test;import com.aspose.email.AlternateView;
import com.aspose.email.Appointment;
import com.aspose.email.AppointmentLoadOptions;
import com.aspose.email.HeaderCollection;
import com.aspose.email.MailMessage;
import com.aspose.email.MapiConversionOptions;
import com.aspose.email.MapiMessage;
import com.google.common.collect.ImmutableMap;public class EmailReaderTest {
static String sourcePath="/Sample_Meeting_For_JIRA.eml"; @Test public void testEmailParser() throws IOException, MessagingException { try (InputStream is = new FileInputStream(new File(sourcePath))) { MapiConversionOptions mapiConversionOption = new MapiConversionOptions(); mapiConversionOption.setPreserveOriginalAddresses(true); mapiConversionOption.setPreserveOriginalDates(true); mapiConversionOption.setPreserveSignature(true); mapiConversionOption.setUseBodyCompression(true); mapiConversionOption.setFormat(MapiConversionOptions.getUnicodeFormat().getFormat()); mapiConversionOption.setPreserveEmbeddedMessageFormat(false); mapiConversionOption.setForcedRtfBodyForAppointment(false); MailMessage message = new MailMessage(); message.setBodyEncoding(Charset.forName("UTF-8")); SharedByteArrayInputStream sh = new SharedByteArrayInputStream(IOUtils.toByteArray(is)); Properties sessionProps = new Properties(); sessionProps.setProperty( "mail.mime.address.strict", "false"); Session session = Session.getInstance(sessionProps); MimeMessage mm = new MimeMessage(session, sh); Multipart multipart = (Multipart) mm.getContent(); Map<String, Boolean> HEADER_NAMES_ADDRESSES = ImmutableMap.<String, Boolean>builder() .put("from", false) .put("sender", false) .put("to", true) .put("cc", true) .put("bcc", true) .put("reply-to", true) .build(); mm.removeHeader("Content-Transfer-Encoding"); message.setDate(new Date()); message.setTimeZoneOffset(0); message.setSubjectEncoding(Charset.forName("UTF-8")); HeaderCollection hc = message.getHeaders(); Enumeration<Header> headers = mm.getAllHeaders(); while(headers.hasMoreElements()) { Header header = headers.nextElement(); hc.add(header.getName(),header.getValue()); } for (int i = 0; i < multipart.getCount(); i++) { BodyPart part = multipart.getBodyPart(i); //System.out.println( "Content-type:"+part.getContentType()); String contentString = new String(IOUtils.toByteArray(part.getInputStream()),Charset.forName("UTF-8")); if(part.getContentType().toLowerCase().startsWith("text/html")){ AlternateView view = AlternateView.createAlternateViewFromString(contentString, Charset.forName("UTF-8"), "text/html"); message.isBodyHtml(true); message.getAlternateViews().addItem(view); // System.out.println(" view: "+ new String(IOUtils.toByteArray(view.getContentStream()), Charset.forName("UTF-8"))); } else if(part.getContentType().toLowerCase().startsWith("text/calendar")){ AppointmentLoadOptions appointmentLoadOptions = new AppointmentLoadOptions(); appointmentLoadOptions.setApplyLocalTZ(false); appointmentLoadOptions.setIgnoreSmtpAddressCheck(true); byte[] contentBytes = contentString.getBytes(Charset.forName("UTF-8")); Appointment appointment = Appointment.load(new ByteArrayInputStream(contentBytes), appointmentLoadOptions); message.getAlternateViews().addItem(appointment.requestApointment()); }else if(part.getContentType().toLowerCase().startsWith("text/plain")){ AlternateView view = AlternateView.createAlternateViewFromString(contentString, Charset.forName("UTF-8"), "text/plain"); message.getAlternateViews().addItem(view); } } MapiMessage mapiMsg = MapiMessage.fromMailMessage(message, mapiConversionOption); //System.out.println("Mapi msg: "+mapiMsg.getBodyHtml()); assertTrue(mapiMsg.getBodyHtml().contains("→")); } }
}