【问题标题】:Downloading attachments from unseen messages从看不见的邮件中下载附件
【发布时间】:2020-09-12 00:19:01
【问题描述】:

我在 java 中从事大学项目。我必须使用 GMAIL API 从新电子邮件中下载附件。

我使用 OAuth 2.0 授权成功连接到 gmail 帐户。

private static final List<String> SCOPES = Collections.singletonList(GmailScopes.GMAIL_READONLY);

我尝试使用

获取看不见的邮件
ListMessagesResponse listMessageResponse = service.users().messages().list(user).setQ("is:unseen").execute();

listMessageResponse 不是 null 但是当我调用方法 .getResultSizeEstimate() 它返回 0 我还尝试使用

listMessageResponse 转换为 List (我想这更有用)
List<Message> list = listMessageResponse.getMessages();

但是 list 会启动 NullPointerException

然后尝试获取每个附件

for(Message m : list) {
            List<MessagePart> part = m.getPayload().getParts();
            for(MessagePart p: part) {
                if(p.getFilename()!=null && p.getFilename().length()>0) {
                    System.out.println(p.getFilename()); // Just to check attachment filename
                }
            }
        }

我的方法是否正确(如果不是如何解决)以及我应该如何下载这些附件。

编辑 1:

修复了q参数,我误写了is:unseen而不是is:unread。 现在应用程序成功到达未读邮件。 (例如有两封未读邮件,都成功到达,我可以轻松获取他们的 ID)。

现在这部分出现 NullPointerException

List<MessagePart> part = m.getPayload().getParts();

两封邮件都有附件,并且 m 不是 null(我通过 .getID() 获得 ID)

任何想法如何克服这个问题并下载附件?

编辑 2:

附件下载部分

for(MessagePart p : parts) {

            if ((p.getFilename() != null && p.getFilename().length() > 0)) {
                String filename = p.getFilename();
                String attId = p.getBody().getAttachmentId();
                MessagePartBody attachPart;
                FileOutputStream fileOutFile = null;
                try { 
                   attachPart = service.users().messages().attachments().get("me", p.getPartId(), attId).execute();
                   byte[] fileByteArray = Base64.decodeBase64(attachPart.getData());


                   fileOutFile = new FileOutputStream(filename); // Or any other dir
                   fileOutFile.write(fileByteArray);
                   fileOutFile.close();
                }catch (IOException e) {
                    System.out.println("IO Exception processing attachment: " + filename);
                } finally {
                   if (fileOutFile != null) {
                      try {
                         fileOutFile.close();
                      } catch (IOException e) {
                         // probably doesn't matter
                      }
                   }
                }
            }
        }

下载使用不同类型电子邮件的测试应用程序。 唯一剩下的就是将未读消息的标签(由应用程序到达)更改为阅读。有什么技巧吗?

还有一个小问题: 我希望这个应用程序使用 TimerTask 抽象类每 10 分钟获取一次邮件。是否需要手动“关闭”与 gmail 的连接,或者在 run() 方法迭代结束后自动完成?

 @Override
 public void run(){

 // Some fancy code

 service.close(); // Something like that if even exists
 }

【问题讨论】:

  • 您有一个名为 unseen 的自定义标签?记住 Response 不会为空,它总是会返回一个响应对象。听起来您的自定义标签没有结果。
  • 我犯了一个愚蠢的错误,我想写未读但写得看不见。
  • @BogosavCvetkovic 我相应地更新了我的答案,请告诉我这是否适合你。
  • @BogosavCvetkovic 既然您的原始问题得到了解决,我建议针对您当前的问题发布一个新问题,并请考虑接受我提供的答案,因为这是在 SO 中的用户之间共享知识的基础.另外,当然,在发布新问题之前,请先对更改标签的主题进行一些研究,只有在遇到无法解决的问题时才发布问题。
  • Users.messages: modifyClass Gmail.Users.Messages.Modify 可能是您开始研究标签更改的好地方。

标签: java google-api gmail gmail-api google-api-java-client


【解决方案1】:

我认为ListMessagesResponse 永远不会变为空。即使没有与您的查询匹配的消息,至少resultSizeEstimate 将被填充到结果响应中:请参阅Users.messages: list > Response

我认为您使用了正确的方法,只是没有与您的查询匹配的消息。实际上,我以前从未见过is:unseen。你的意思是is:unread 吗?

更新:

使用Users.messages: list 时,仅填充每条消息的idthreadId,因此您无法访问消息payload。为了获得完整的消息资源,您必须改用Users.messages: get,正如您在引用的链接中看到的那样:

注意每个消息资源只包含一个id和一个threadId。可以使用messages.get 方法获取其他消息详细信息。

所以在这种情况下,在获取消息列表后,您必须遍历列表,并对列表中的每条消息执行以下操作:

  • 通过m.getId() 获取消息id
  • 检索到消息id 后,使用它调用Gmail.Users.Messages.Get 并获取完整的消息资源。检索到的消息应填充所有字段,包括有效负载,并且您应该能够访问相应的附件。

代码示例:

List<Message> list = listMessageResponse.getMessages();
for(Message m : list) {
  Message message = service.users().messages().get(user, m.getId()).execute();
  List<MessagePart> part = message.getPayload().getParts();
  // Rest of code
}

参考:

【讨论】:

  • 你说得对,我把 is:unseen 弄错了。我将使用更多新细节编辑问题。
  • 终于完成了,现在只剩下将消息标签从未读更改为已读(不想多次阅读同一条消息)。使用最新信息编辑的问题。
猜你喜欢
  • 2014-05-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-08-20
  • 2010-09-14
  • 1970-01-01
  • 2018-08-18
相关资源
最近更新 更多