🚀

Gmailのmessage.getId()のIDが重複して困った話

に公開

TL;DR

Google Apps Script(GAS)でGmailのメールのIDを取得するなら message.getHeader('Message-ID') を使った方が良いという話

message.getId()は使わない方が良いです

本文

背景

当方は生成AIのコンサルタントです。GASを使ってGmailのメールを生成AIで処理させるプログラムを組んでいました

ただ、定期的に処理を行う上ではメールの重複処理を避ける必要性があります。そこでGmailのメッセージIDを使用して処理済メールを特定することにしました

問題と解決策

message.getId()ではメールが重複し得る

多くの記事では以下で取得できるIDを使用し、メールの重複判定をしていました

const messageId = message.getId();

しかしこの方法ではメールが重複し得ます
なぜならこのIDは「アカウント内で一意」 だからです。つまりGASの実行者(アカウント)が変わるとIDも変わります
結果として、同じメールでも実行者Aと実行者Bで別のIDとみなされ、同じメッセージの重複処理が発生します

thread.getId()で取れるメールのスレッドのIDも同様です。GASの実行者が変わるとIDが変わります

message.getHeader('Message-ID')はメールによって一意

最終的に

  • message.getHeader('Message-ID')

を使うことにしました

この値はメール本体に埋め込まれた標準ヘッダーの値であり、GASの実行者が違っても同じ値を取ります

メールのスレッドについては、

  • thread.getPermalink()

を使えばスレッドごとに一意な値を取得できます(他に良い方法があるかもしれません)

メールの重複処理を避けたい場合はこれらの値を使用することをオススメします

鵜呑みせずにしっかりテストする

今回結構苦労したので記事を書きました
多くに記事でmessage.getId()が使われており、それで一意になると思ってしまっていました
鵜呑みせずにしっかりテストすることは大事だと感じます

というか各メールのIDとも言えるはずのmessage.getId()がまさか重複するとは…
そうなるとこのメソッドそもそも要らないのでは。なんで作ったのかが謎
皆さんもお気を付けください

Discussion