Google PubSub / Gmail Webhook:发送电子邮件时始终从 PubSub 接收多个 POST 请求
Posted
技术标签:
【中文标题】Google PubSub / Gmail Webhook:发送电子邮件时始终从 PubSub 接收多个 POST 请求【英文标题】:Google PubSub / Gmail Webhook: Consistently Receiving Multiple POST Requests From PubSub When Sending An Email 【发布时间】:2019-05-06 06:23:52 【问题描述】:我设置了一个 webhook,它使用 Google Cloud PubSub API 和 Java 中的 Gmail API 监听和处理 Gmail 中我的 INBOX 和 SENT 文件夹中的更改。
我看到的问题是,当我向另一个用户发送消息时,PubSub 似乎 在一秒钟内两次推送到我的端点,history_id 和 message_id 略有不同,但订阅相同名称和用户电子邮件。
我了解 PubSub 保证至少一次交付,因此收到重复的消息并不少见,但因为它一直在发生并且 message_id 不同,我想可能会有基于以下 PubSub 文档的多个推送请求:
Cloud Pub/Sub 为每条消息分配一个唯一的
message_id
,可用于检测订阅者收到的重复消息。但是,这将不允许您检测因对同一数据的多个发布请求而产生的重复。
我尝试过的:
-
确保我的 Google Cloud 控制台上只有一个主题/订阅。
在 10 到 600 秒之间设置不同的 Ack 截止时间值。
致电
service.users().stop()
以确保我没有多次致电watch()
,然后再次开始watch()
。
我研究了 PubSubIO 以确保完全一次交付,但我认为如果我一直收到多条 PubSub 消息,那么我的设置方式肯定存在根本问题我的网络钩子。
编辑: 这是我必须观察我的 Gmail 帐户更改的代码。我正在使用具有域范围权限的服务帐户来访问整个域中的帐户
public static Map<String, String> watchInbox(Gmail service) throws IOException
Map<String, String> watchInboxResponse = new HashMap<>();
List<String> labelsToWatch = Arrays.asList("INBOX", "SENT");
String topicName = "projects/subscription-name/topics/topic-name";
WatchRequest request = new WatchRequest();
request.setLabelIds(labelsToWatch);
request.setTopicName(topicName);
WatchResponse response = service.users().watch("me", request).execute();
watchInboxResponse.put("historyId", response.getHistoryId().toString());
watchInboxResponse.put("expiration", response.getExpiration().toString());
return watchInboxResponse;
我将 historyid 和过期时间插入数据库并使用它来检查,在收到 webhook 调用后,如果自上次调用 watch
以来已经过去了超过 24 小时,我是否需要再次调用 watch()
(建议由谷歌)。
【问题讨论】:
您可以添加任何详细信息,例如:使用的代码,遇到的错误问题吗? How do I ask a good question?, How to create a Minimal, Complete, and Verifiable example 向社区展示你的尝试。 请增强您的代码。您所包含的示例非常少,对解决方案没有帮助。 您找到解决方案了吗?我也有类似的问题:***.com/questions/53619495/… 【参考方案1】:我在实现 Google 发布/订阅观看请求时也有类似的行为。
Gmail 在您撰写邮件时所做的是创建系统标签 “发送和草稿” 并不断使用新的 messageId 和标签“发送和草稿”保存到草稿,您订阅了“收件箱和发送”的任何更改,因此您的 webhook 将被点击两次或更长时间!
来自 Gmail 的邮件始终包含标签,您必须过滤具有标签草稿的邮件。
我的代码使用 Gmail .net SDK 并且必须处理
//Explicitly avoid further processing
bool isdraft = y.Message.LabelIds.Contains("DRAFT");
并过滤那些不管。
【讨论】:
以上是关于Google PubSub / Gmail Webhook:发送电子邮件时始终从 PubSub 接收多个 POST 请求的主要内容,如果未能解决你的问题,请参考以下文章
使用 Google Cloud PubSub 不断收到“向 Cloud PubSub 发送测试消息时出错...”
基于特定电子邮件 ID 的 Google Pubsub 订阅