Veeam/Datto:メール日付が復元日時になる問題

1分で読めます

復元の翌朝、チケットが届く

Veeam Backup for Microsoft 365でメールボックスの復元が完了した直後のことです。作業は順調に終わり、データも揃い、フォルダも無事。ところが月曜の朝、ユーザーからこんな連絡が入ります。「メールが全部今日の日付になっています。何も探せません。」

メールが消えたわけではありません。ちゃんとそこにあります。ただ、表示されている日付が復元を実行した時刻になっており、実際に送受信された日付ではないのです。2021年1月のメールが、昨夜23時47分に受信したものとして表示される。会話のスレッドは崩れ、時系列はまったく追えません。

この現象はVeeam Backup for Microsoft 365、Datto SaaS Protection、Synology Active Backup for Microsoft 365、AvePoint Cloud Backupなど複数のツールで発生します。それぞれ仕組みは少し異なりますが、結果は同じです。

技術的な原因

間違った日付がどこから来るのかを理解するには、これらのツールがExchange OnlineやGoogle Workspaceにメールを再挿入する仕組みを見る必要があります。

バックアップツールがメッセージを復元する際、ローカルディスク上でファイルを移動するように「元の場所に戻す」ことはできません。そのため、ツールはIMAPプロトコル、またはプロバイダーのAPI(Microsoft側ではEWSやMicrosoft Graph、Google側ではGmail API)を経由して、メールボックスにメッセージの新しいコピーを書き込みます。そしてそのコピーとともに、そのメッセージがどの日付を持つのかをメールボックスに伝える必要があります。

ここから問題が始まります。(復元されたメールの生のヘッダーを見たことがある方なら、本文にたどり着く前にReceived:ヘッダーが20行以上並んでいるのを見たことがあるでしょう。)

IMAP APPENDとReceived:ヘッダー

IMAPプロトコルにはAPPENDというコマンドがあります。メールボックスにメッセージを挿入するためのコマンドです。復元ツールはまさにこれを使います。保存されていたメッセージを取り出し、IMAP APPEND経由で対象のメールボックスに挿入するわけです。

このコマンドを使うと、ツールはメッセージとともに日付を渡すことができます。ツールが元の日付を渡せば、メールボックスはその日付を保持します。Microsoft 365、Outlook.com、Gmailのいずれも同様です。何も渡さなかったり、復元時の日付を渡した場合は、メールボックスは復元した日にメールを記録します。また、メッセージを書き戻す方法によっては、先頭にもう一行、コピーした日付が入ったReceived:ヘッダーが追加されることがあります。Gmail自身のインポートAPIは、まさにこの動作をします。

追加される一行はこんな形になります。

Received: by gmailapi.google.com
  with HTTPREST; Mon, 14 Apr 2025 23:47:12 +0000

結果、元のメールは内部に無傷で残っています。元のDate:ヘッダー(例えば「3 Jan 2021 09:15:00」)も保持されています。しかし、その上に復元日時を持つ新しいReceived:ヘッダーが貼り付けられた状態になっています。

OutlookとGmailが日付を読み取る仕組み

OutlookやGmailのウェブインターフェースのようなメールクライアントは、メッセージ一覧に表示する日付を決める際、必ずしもDate:ヘッダーを参照するわけではありません。多くのクライアントは、IMAPプロトコルのINTERNALDATE(メッセージがメールボックスに追加された日時)や、最新のReceived:ヘッダーを使用します。

Windows版Outlookは2023年末のアップデート以降、この傾向が特に顕著です。ヘッダーチェーンの先頭に新しいReceived:ヘッダーがあると、それを表示日付として使います。元のDate:はメッセージのプロパティを開かない限り見えない「詳細情報」に追いやられてしまいます。

ユーザーが目にするのは、復元が行われた夜の日時で統一されたメッセージ一覧です。3年分のメール履歴が、一夜のうちに押しつぶされたように見えてしまうわけです。

移行とは異なる問題

これはIMAP移行後に日付がずれる一般的な問題とは区別して考える必要があります。移行の場合、ツールはサーバーAからサーバーBにメールを移動し、各メールが日付を保持するかどうかは、ツールが書き込み時にサーバーBに何を伝えるかによって決まります。仕組みは同じですが、文脈が違います。

ここで扱っているのは、バックアップからの復元です。メールは組織の外に出たことはなく、どこか(Azure Blob Storage、AWS S3、Dattoのアプライアンスなど)に安全に保管されていたものを再挿入しただけです。ユーザーからすれば「自分のメールが戻ってきた」はずなのに、という感覚があるため、問題の発覚はむしろ驚きとともに起こります。

技術的なメカニズムは移行と同じです。元の日付を伝えない再挿入は、同じアーティファクトを生み出します。そして修正方法も、同じ考え方に基づきます。

各ツールのINTERNALDATE対応状況

ツールによって細かい挙動は異なります。実は、ここが話の面白いところです。

Veeam Backup for Microsoft 365

VeeamはExchange OnlineへのリストアにEWS(Exchange Web Services)APIを使用します。EWSではDateTimeReceivedフィールドでメッセージの日付を指定できますが、この値がIMAPレベルのINTERNALDATEに必ずしも反映されるわけではありません。特に、元のメールボックスとは別のメールボックスへの粒度の細かい復元では、Outlookでの並び替え日付が元の日付とずれることがあります。

Datto SaaS Protection

Dattoは設定によってMicrosoft Graph APIまたはIMAPを使って復元します。どちらの場合も、メールボックスに表示される日付は、復元時に各メッセージの元の日付が渡されるかどうかによって決まります。DattoをクライアントのためにMSPが使用している場合、この問題はかなり頻繁に発生します。特にランサムウェアのインシデント後に数百のメールボックスを一斉に復元するような緊急対応時には、日付がすべて狂っていることに後から気づく、という展開になりがちです。

AvePointとSynology Active Backup

AvePoint Cloud BackupとSynology Active Backup for Microsoft 365も同様の仕組みで動作します。AvePointはこの挙動をナレッジベースで文書化しており(「メッセージは復元日時を受信日として復元される」)、ネイティブな修正手段は提供していません。Synologyも同じ問題を抱えており、復元インターフェース上で「メッセージの日付」と「復元日時」が明確に区別されていないため、問題がより分かりにくくなっています。

朗報:元の日付は消えていない

救いがあるとすれば、メッセージ元来のDate:ヘッダーは変更されていないという点です。復元されたすべてのメールの中に、元の日付は無傷のまま存在しています。復元処理はメールボックスが記録する日付を変え、場合によっては先頭にReceived:行を追加しましたが、メッセージ本体には手をつけていません。

これはMIMEフォーマット(RFC 2822)の特性です。メッセージの内部構造は不変であり、Received:ヘッダーは層を重ねるように先頭に積み上がっていきますが、元の情報はその下にきちんと残っています。

つまり、情報は失われていません。再挿入によるアーティファクトに隠されているだけです。

復元をやり直しても解決しない理由

最初に思いつくのは「復元したメールを削除してもう一度やり直せば、今度は日付が正しくなるかもしれない」というアイデアです。これは得策ではありません。理由がいくつかあります。

まず、復元ツールは2回目も同じ動作をします。同じツール、同じ設定であれば、メールは元の日付を持たないまま同じように書き戻されるからです。まったく同じ結果になります。

次に、本番環境のメールボックスで復元をやり直すということは、時間と帯域幅とリスクを伴う作業です。20,000件のメッセージを持つメールボックスが50個あれば、数時間の作業になり、APIを占有し、MicrosoftやGoogle側でレート制限が発動することもあります(バッチ処理中の深夜2時に429 Too Many Requestsが返ってくる、あの状況です)。

復元は成功しています。データはそこにあります。修正が必要なのは日付のアーティファクトであって、復元処理そのものではありません。

自力で修正する場合の現実的なリスク

問題を理解することと、80,000件のメールを一件も失わずに修正することは、まったく別の話です。

IMAPでメッセージを走査して日付を修正するPythonスクリプトは、作れそうに思えます。テスト用の50件なら問題なく動くでしょう。本番環境では違います。エッジケースが次々と出てきます。S/MIME署名済みメール(ヘッダーを変更すると暗号署名が無効になる)、PGP暗号化メッセージ、非標準のMIME境界を持つmultipart構造、RFC 2047エンコードされた非ASCIIヘッダー、スクリプトのメモリを溢れさせる40MBの添付ファイル。さらに、複数のReceived:ヘッダーが追加されているメール(復元が途中から再実行された場合など)は、より精緻な検出ロジックが必要です。

正直に言うと、本当のリスクはスクリプトがクラッシュすることではありません。エラーなく動作しているように見えながら、壊れたメッセージを生成してしまうことです。スレッドが崩れ、重複が発生し、添付ファイルが切り離される。それに気づくのは、ユーザーが重要なメールを探し始めた数週間後かもしれません。

修正後のすべてのメールが本当に無傷かどうか、どうやって検証しますか?自作スクリプトにそのような仕組みはほとんどありません。

リデイト(Redate.io)のアプローチ

Redate.ioは各メールのヘッダーチェーンを解析し、Veeamによる復元、BitTitanによる移行、手動インポートを問わず、再挿入によるアーティファクトを特定します。独自の修正エンジンは、どのツールが原因かを知る必要さえありません。表示されている日付が元の日付と一致しないメールを探し出すため、聞いたことのないツールが使われた場合でも見つけ出せます。

修正を実行する前に、Redate.ioはメールボックス全体をスキャンしてレポートを生成します。影響を受けているメールの件数、誤った日付、検出された元の日付が一覧で確認できます。このスキャンは無料です。対応を決める前に、問題の全体像を把握できます。

修正後は各メールを個別に検証します。元のメッセージは表示可能なバックアップフォルダに保持され、削除するまで残るため、万一の際の安全網が確保されています。

Redate.ioでは、利用者が自分自身のMicrosoftアカウントまたはGoogleアカウントでサインインし、Redate.ioはそのサインインで許可された範囲内で該当のメールボックスだけを開きます。メールが中間サーバーを経由することはありません。修正はメールボックスの中で直接行われ、エクスポートや再インポートは発生しません。

複数のクライアントが同時に影響を受けているMSPの方は、MSP向けのページをご確認ください。Redate.ioは単一のインターフェースから複数のメールボックスを並行処理できます。

バックアップツールからの復元だけが原因ではありません。同じ日付アーティファクトは他の状況でも発生します。

いずれのケースも根本的な仕組みは同じです。元の日付を伝えない再挿入(先頭に新しいReceived:ヘッダーが追加される場合もあります)が起こり、メールクライアントがその新しい日付を基準として表示します。

メールはそこにあります。元の日付は各メッセージの中に保存されています。 Redate.ioで無料スキャンを実行して、メールボックスの中で何件が影響を受けているかを正確に確認してから、修正を実行するかどうか判断してください。

関連記事