38

我正在尝试访问我的 gmail 帐户并从中检索所有未读电子邮件的信息。

在参考了许多链接后,我已经编写了我的代码。我提供了一些链接供参考。

使用 Java 通过 GMail 帐户发送和接收电子邮件

使用 JavaMailAPI 接收邮件的 Java 代码

为了测试我的代码,我创建了一个 Gmail 帐户。所以我收到了来自 Gmail 的 4 条消息。我在检查邮件数量后运行我的应用程序。这显示了正确的结果。4 封未读邮件。正在显示所有信息(例如日期、发件人、内容、主题等)

然后我登录到我的新帐户,阅读其中一封电子邮件并重新运行我的应用程序。现在未读消息的计数应该是 3,但它显示“未读消息数:0”

我在这里复制代码。

public class MailReader

{

    Folder inbox;

    // Constructor of the calss.

    public MailReader() {
        System.out.println("Inside MailReader()...");
        final String SSL_FACTORY = "javax.net.ssl.SSLSocketFactory";

        /* Set the mail properties */

        Properties props = System.getProperties();
        // Set manual Properties
        props.setProperty("mail.pop3.socketFactory.class", SSL_FACTORY);
        props.setProperty("mail.pop3.socketFactory.fallback", "false");
        props.setProperty("mail.pop3.port", "995");
        props.setProperty("mail.pop3.socketFactory.port", "995");
        props.put("mail.pop3.host", "pop.gmail.com");

        try

        {

            /* Create the session and get the store for read the mail. */

            Session session = Session.getDefaultInstance(
                    System.getProperties(), null);

            Store store = session.getStore("pop3");

            store.connect("pop.gmail.com", 995, "abc@gmail.com",
                    "paasword");

            /* Mention the folder name which you want to read. */

            // inbox = store.getDefaultFolder();
            // inbox = inbox.getFolder("INBOX");
            inbox = store.getFolder("INBOX");

            /* Open the inbox using store. */

            inbox.open(Folder.READ_ONLY);

            /* Get the messages which is unread in the Inbox */

            Message messages[] = inbox.search(new FlagTerm(new Flags(
                    Flags.Flag.SEEN), false));
            System.out.println("No. of Unread Messages : " + messages.length);

            /* Use a suitable FetchProfile */
            FetchProfile fp = new FetchProfile();
            fp.add(FetchProfile.Item.ENVELOPE);

            fp.add(FetchProfile.Item.CONTENT_INFO);

            inbox.fetch(messages, fp);

            try

            {

                printAllMessages(messages);

                inbox.close(true);
                store.close();

            }

            catch (Exception ex)

            {
                System.out.println("Exception arise at the time of read mail");

                ex.printStackTrace();

            }

        }

        catch (MessagingException e)
        {
            System.out.println("Exception while connecting to server: "
                    + e.getLocalizedMessage());
            e.printStackTrace();
            System.exit(2);
        }

    }

    public void printAllMessages(Message[] msgs) throws Exception
    {
        for (int i = 0; i < msgs.length; i++)
        {

            System.out.println("MESSAGE #" + (i + 1) + ":");

            printEnvelope(msgs[i]);
        }

    }

    public void printEnvelope(Message message) throws Exception

    {

        Address[] a;

        // FROM

        if ((a = message.getFrom()) != null) {
            for (int j = 0; j < a.length; j++) {
                System.out.println("FROM: " + a[j].toString());
            }
        }
        // TO
        if ((a = message.getRecipients(Message.RecipientType.TO)) != null) {
            for (int j = 0; j < a.length; j++) {
                System.out.println("TO: " + a[j].toString());
            }
        }
        String subject = message.getSubject();

        Date receivedDate = message.getReceivedDate();
        Date sentDate = message.getSentDate(); // receivedDate is returning
                                                // null. So used getSentDate()

        String content = message.getContent().toString();
        System.out.println("Subject : " + subject);
        if (receivedDate != null) {
            System.out.println("Received Date : " + receivedDate.toString());
        }
        System.out.println("Sent Date : " + sentDate.toString());
        System.out.println("Content : " + content);

        getContent(message);

    }

    public void getContent(Message msg)

    {
        try {
            String contentType = msg.getContentType();
            System.out.println("Content Type : " + contentType);
            Multipart mp = (Multipart) msg.getContent();
            int count = mp.getCount();
            for (int i = 0; i < count; i++) {
                dumpPart(mp.getBodyPart(i));
            }
        } catch (Exception ex) {
            System.out.println("Exception arise at get Content");
            ex.printStackTrace();
        }
    }

    public void dumpPart(Part p) throws Exception {
        // Dump input stream ..
        InputStream is = p.getInputStream();
        // If "is" is not already buffered, wrap a BufferedInputStream
        // around it.
        if (!(is instanceof BufferedInputStream)) {
            is = new BufferedInputStream(is);
        }
        int c;
        System.out.println("Message : ");
        while ((c = is.read()) != -1) {
            System.out.write(c);
        }
    }

    public static void main(String args[]) {
        new MailReader();
    }
}

我在谷歌上搜索,但我发现你应该使用 Flags.Flag.SEEN 来阅读未读的电子邮件。但这在我的情况下没有显示正确的结果。

有人可以指出我可能在哪里做错了吗?

如果您需要完整的代码,我可以编辑我的帖子。

注意:我编辑了我的问题以包含整个代码,而不是我之前发布的代码片段。

4

6 回答 6

15

Your code should work. You can also use the Folder.getUnreadMessageCount() method if all you want is the count.

JavaMail can only tell you what Gmail tells it. Perhaps Gmail thinks that all those messages have been read? Perhaps the Gmail web interface is marking those messages read? Perhaps you have another application monitoring the folder for new messages?

Try reading an unread message with JavaMail and see if the count changes.

You might find it useful to turn on session debugging so you can see the actual IMAP responses that Gmail is returning; see the JavaMail FAQ.

于 2012-10-30T18:33:24.017 回答
11

您无法使用 POP3 获取未读邮件。来自JavaMail API

POP3 不支持永久标志(请参阅 Folder.getPermanentFlags())。特别是,永远不会为 POP3 消息设置 Flags.Flag.RECENT 标志。由应用程序来确定 POP3 邮箱中的哪些邮件是“新的”。

您可以使用 IMAP 协议并使用 SEEN 标志,如下所示:

public Message[] fetchMessages(String host, String user, String password, boolean read) {
    Properties properties = new Properties();
    properties.put("mail.store.protocol", "imaps");

    Session emailSession = Session.getDefaultInstance(properties);
    Store store = emailSession.getStore();
    store.connect(host, user, password);

    Folder emailFolder = store.getFolder("INBOX");
    // use READ_ONLY if you don't wish the messages
    // to be marked as read after retrieving its content
    emailFolder.open(Folder.READ_WRITE);

    // search for all "unseen" messages
    Flags seen = new Flags(Flags.Flag.SEEN);
    FlagTerm unseenFlagTerm = new FlagTerm(seen, read);
    return emailFolder.search(unseenFlagTerm);
}

要注意的另一件事是 POP3 不处理文件夹。IMAP 获取文件夹,POP3 只获取收件箱。更多信息:如何使用 POP3 检索 gmail 子文件夹/标签?

于 2015-07-26T14:50:03.980 回答
8

更改inbox.open(Folder.READ_ONLY);inbox.open(Folder.READ_WRITE); 它将更改您在收件箱中阅读的邮件。

于 2013-07-29T05:51:26.220 回答
4
Flags seen = new Flags(Flags.Flag.RECENT);
FlagTerm unseenFlagTerm = new FlagTerm(seen, false);
messages = inbox.search(unseenFlagTerm);
于 2014-07-22T14:42:09.497 回答
1

要使用的正确标志是

Flags.Flag.RECENT
于 2014-06-05T18:47:32.123 回答
-1

请使用此方法获取未读邮件

getNewMessageCount()

请参考以下链接:

https://javamail.java.net/nonav/docs/api/com/sun/mail/imap/IMAPFolder.html

于 2014-12-22T05:25:35.950 回答