2

I have developed simple Java Application which reads my Gmail inbox mails. I am able to read Email From and Subject. But, I am unable to read Email Contents.

When I try to read it, I get below exception:

Exception Msg: com.sun.mail.imap.IMAPInputStream cannot be cast to javax.mail.Multipart

Code:

import com.sun.mail.imap.IMAPFolder;
import com.sun.mail.imap.IMAPStore;

import javax.mail.Address;
import javax.mail.BodyPart;
import javax.mail.Message;
import javax.mail.MessagingException;
import javax.mail.Multipart;
import javax.mail.Session;

import java.io.IOException;
import java.util.List;
import java.util.Properties;


public class Read_Mail {

    static String from;

    public static void main(String args[])
    {
         Properties props = new Properties();
         props.setProperty("mail.store.protocol", "imaps");

         Session session = Session.getDefaultInstance(props,null);

         IMAPStore imapstore = null;

         try
         {
             imapstore = (IMAPStore) session.getStore("imaps");
             imapstore.connect("imap.gmail.com", "usernamexxxxx@gmail.com", "passwordxxx");

             final IMAPFolder folder = (IMAPFolder) imapstore.getFolder("Inbox");

             folder.open(IMAPFolder.READ_ONLY);

             Message[] messages = folder.getMessages();
                for (int i = 0; i < messages.length; i++) {
                    Message message = messages[i];
                    System.out.println("==============================");
                    System.out.println("Email #" + (i + 1));
                    System.out.println("Subject: " + message.getSubject());
                    System.out.println("From: " + message.getFrom()[0]);
//                  System.out.println("Text: " + message.getContent());

                    Object mp = (Object) message.getContent();

                    if (mp instanceof String)  
                    {  
                        String body = (String)mp;
                        System.out.println("MSG Body : " + body);
                    }  
                    else if (mp instanceof Multipart)  
                    {  
                        Multipart mpp = (Multipart)mp;
                        final BodyPart bp = mpp.getBodyPart(i);
                        System.out.println("Text: " +bp.getContent().toString());
                    } else {
                        System.out.println("Inside else");
                        Multipart mpp = (Multipart)mp;
                        final BodyPart bp = mpp.getBodyPart(i);
                        System.out.println("Text: " +bp.getContent().toString());
                    }

                }
         }
         catch(Exception e)
         {
            System.out.println("Exception Msg: " + e.getMessage()); 
         }
    }
}

It always goes inside else block and fires exception.

halfer
  • 19,824
  • 17
  • 99
  • 186
VVB
  • 7,363
  • 7
  • 49
  • 83

2 Answers2

1

Not sure what you're asking.

In the final else you're ignoring the fact that you've already determined it's not a Multipart (it failed instanceof Multipart) but go ahead and try and cast it to a Multipart anyway. Of course it's going to fail.

Now that you know ImapInputStream is a possibility, add an else-if specifically for that class (or, better, for InputStream) and process it like any other stream. Better yet, Java EE docs say that a stream is returned if it doesn't know what to do with the data type, so maybe that's your final else.

If you specifically check for a stream, then your final else should generate an error of some sort.

Arjan Tijms
  • 37,782
  • 12
  • 108
  • 140
Scott Sosna
  • 1,443
  • 1
  • 8
  • 8
  • You just re-explained my question instead of answering – VVB Apr 29 '15 at 08:30
  • No, I told you that you've written bad code. You asked why it threw an exception...it throws an exception because the code is incorrect. The API defines an InputStream as the return type of last resort and you don't handle it. Do you need me to write the code? – Scott Sosna Apr 29 '15 at 08:48
1

I have made a few changes n your code, hope it helps

 try {
     try {
         imapstore = (IMAPStore) session.getStore("imaps");
     } catch (NoSuchProviderException e1) {
         // TODO Auto-generated catch block
         e1.printStackTrace();
     }
     imapstore.connect("imap.gmail.com", "usernamexxxxx@gmail.com", "passwordxxx");

     IMAPFolder folder;
     folder = (IMAPFolder) imapstore.getFolder("Inbox");

     folder.open(IMAPFolder.READ_ONLY);

     Message[] messages;
     messages = folder.getMessages();
     for (int i = 0; i < messages.length; i++) {
         Message message = messages[i];
         System.out.println("==============================");
         System.out.println("Email #" + (i + 1));
         System.out.println("Subject: " + message.getSubject());
         System.out.println("From: " + message.getFrom()[0]);
         //                  System.out.println("Text: " + message.getContent());

         Object mp;
         try{
             mp = (Object) message.getContent();

             if (mp instanceof String) {  
                 String body = (String)mp;
                 System.out.println("MSG Body : " + body);
             }  else if (mp instanceof MimeMultipart) { 
                 MimeMultipart mpp = (MimeMultipart)mp;
                 for(int count =0;count<mpp.getCount();count++){
                     MimeBodyPart bp = (MimeBodyPart)mpp.getBodyPart(count);
                     InputStream fileNme = bp.getInputStream();
                     StringWriter writer = new StringWriter();
                     IOUtils.copy(fileNme, writer, "UTF-8");
                     String theString = writer.toString();
                     System.out.println("Text: " +theString);
                 }
             } else if (mp instanceof Multipart) {
                 Multipart mpp = (Multipart)mp;
                 for(int count =0;count<mpp.getCount();count++){
                     MimeBodyPart bp = (MimeBodyPart)mpp.getBodyPart(count);
                     InputStream fileNme = bp.getInputStream();
                     StringWriter writer = new StringWriter();
                     IOUtils.copy(fileNme, writer, "UTF-8");
                     String theString = writer.toString();
                     System.out.println("Text: " +theString);
                 }
             } 
         }catch (IOException e) {
             // TODO Auto-generated catch block
             e.printStackTrace();
         }
     }
 } catch (MessagingException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
 }

you would also need a jar containing IOUtils, which you can download from http://www.java2s.com/Code/Jar/o/Downloadorgapachecommonsiojar.htm

Saurabh Jhunjhunwala
  • 2,832
  • 3
  • 29
  • 57
  • Thanks for the reply. Let me check – VVB Apr 29 '15 at 10:09
  • I tried your solution but its not going into any of the if..else block. Simply, not reading email contents – VVB Apr 29 '15 at 10:13
  • add else System.out.println("Class ::: " + mp.getClass()); as the last block and please let me know the class name – Saurabh Jhunjhunwala Apr 29 '15 at 10:15
  • class com.sun.mail.util.BASE64DecoderStream & class com.sun.mail.imap.IMAPInputStream I am getting after putting above line. – VVB Apr 29 '15 at 10:20
  • write an else block and capture data using InputStream fileNme = bp.getInputStream(); StringWriter writer = new StringWriter(); IOUtils.copy(fileNme, writer, "UTF-8"); String theString = writer.toString(); System.out.println("Text: " +theString); – Saurabh Jhunjhunwala Apr 29 '15 at 10:29
  • But when I try to convert object into multipart objet then it throws exception then how above thing will work? – VVB Apr 29 '15 at 10:32
  • Still getting this exception after trying with MimeMultipart Exception in thread "main" java.lang.ClassCastException: com.sun.mail.imap.IMAPInputStream cannot be cast to javax.mail.internet.MimeMultipart – VVB Apr 29 '15 at 10:34
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/76528/discussion-between-saurabh-jhunjhunwala-and-vvb). – Saurabh Jhunjhunwala Apr 29 '15 at 10:40