为什么迭代所有java邮件用户的文件夹非常慢?

时间:2016-06-23 12:00:36

标签: java performance javamail imap dovecot

   Properties props = System.getProperties();
   props.put("mail.imap.connectiontimeout",5000);
   Session session = Session.getInstance(props);
   Store store = session.getStore("imap");
   for(50K users){

        //login,password changed in loop  
        String[] folders = {"inbox", "f1", "f2", "f3", "spam"};
        store.connect(serverAddress, login + emailSuffix, password);
        for (int i = 0; i < folders.length; i++) {
                    Folder x = store.getFolder(folders[i]);
                    x.open(Folder.READ_ONLY);
                    System.out.println("folder " + folders[i] + " of " + login);
                    x.getUnreadMessageCount();
                    x.close(false);
        }
        store.close();
    }

我为所有连接使用相同的商店,根据this answer更改了UWP app icon on taskbar中的service_count以改善imap-dovecot性能,但我只看到第一次迭代,然后代码挂起或经过很长时间后,下一次system.out

实际上,我需要抓取所有用户的所有旧消息+计算所有未读消息,因为我想从纯Java Mail迁移到某种自定义格式。我甚至没有管理每个用户的所有用户和文件夹,因为即使是简单的store.connect在第一次迭代后也会挂起!

我个人认为瓶颈是我的dovecot配置,但它使用默认限制(1000个连接)看起来不错。

我以某种方式改善了我的鸽舍,或者只为所有用户连接我的商店一次,或以某种方式以其他方式获取所有用户的所有消息和所有用户的unreadMessagesCount?

PS。编程方式的唯一替代方法是maildir中的一些bash脚本,它会从文件系统读取每条消息并将其传递给一些转换为我的自定义格式的其余部分)但它比Java更难解析smptp太难了,从文件名中解析seen个标志,等等。

更新

我发现apache commons net imapclient非常快。

<dependency>
    <groupId>commons-net</groupId>
    <artifactId>commons-net</artifactId>
    <version>3.3</version>
</dependency>

我的代码如下

IMAPClient client = new IMAPClient();
client.connect("localhost");
for(50K users){
    client.login(login + emailSuffix, password);
    for (int i = 0; i < folders.length; i++) {
        System.out.println(client.select("INBOX"); //prints true, it's ok
    }
}
  1. 看起来它比java mailapi更快地连接,因为它可能 连接一次到主机,然后登录每个用户。我可以在JavaMail API中以某种方式重复这种行为吗?
  2. 我如何使用apache commons客户端获取消息?所有方法都返回boolean或void,所以它看起来就像服务器检查库我是对的吗?有可能以某种方式从imapclient获得有用的信息吗?

1 个答案:

答案 0 :(得分:0)

最后通过简单的迭代文件系统解决了我的问题(我有maildir格式)。

我想Java Mail API会为store.connect中的每个用户创建新的dovecot auth,而它应该只连接一次(使用dovecot auth)并在每次用户登录后使用(使用dovecot imap-login)。 这就是为什么我每次迭代等待1分钟 - 它在dovecot配置中为auth进程闲置了。我不确定,但看起来如此。

Apache lib works fast但它只是测试库用于ping服务器,检查连接和其他imap操作。它返回有关操作的布尔结果,但不返回有用的信息(