タグアーカイブ メール配信

Mail Mintのワンクリック解除リンクでデータベースエラーが出る時の対処

Mail Mintのワンクリック解除リンクでデータベースエラーが出る時の対処

Mail Mint で配信したメールのワンクリック解除リンクをクリックすると、WordPress のデータベースエラー「Column ‘mint_email_id’ cannot be null」がログに出力される問題は、プラグインのバージョンが古いことが主な原因だ。最新版(バージョン 1.30.0 以降)にアップデートすることで、このエラーは発生しなくなる。

なぜワンクリック解除でデータベースエラーが発生するのか

なぜワンクリック解除でデータベースエラーが発生するのか

Mail Mint のワンクリック解除機能は、メール内のリンクに埋め込まれたハッシュ値から、どの配信(ブロードキャスト)からの解除なのかを特定する。しかし、古いバージョン(1.24.4 以下など)では、ハッシュ値が無効な場合や、該当する配信が存在しない場合に、ブロードキャスト ID を取得する関数が null を返していた。

その結果、購読解除ステータスの更新自体は正常に行われるものの、その後にブロードキャストごとのメタ情報(is_unsubscribe)を記録する際、データベースの mint_email_id カラムに null が INSERT されようとして、WordPress のデータベースエラーが発生していた。

このエラーは、購読解除の処理自体を妨げるものではなく、あくまでログに記録されるだけだが、大量に発生するとサーバーのエラーログが肥大化するなどの影響が出る。

Mail Mint を最新版にアップデートしてエラーを解消する

Mail Mint を最新版にアップデートしてエラーを解消する

開発元はこの問題を認識し、バージョン 1.30.0 で修正をリリースしている。そのため、まずは管理画面からプラグインを最新版に更新しよう。

STEP 1 管理画面の「プラグイン」→「インストール済みプラグイン」を開く
↓
STEP 2 Mail Mint の「更新」リンクが表示されていればクリック
↓
STEP 3 バージョン 1.30.0 以上に更新されていることを確認する

プラグインの自動更新が有効な場合はすでに適用されている可能性もあるが、念のためバージョン表示を確認しておこう。

更新後にエラーが止まったか確認する

更新が完了したら、メールマーケティングのワンクリック解除リンクを実際にテストするか、サーバーのエラーログに同じメッセージが出なくなったことを確認する。WordPress のデバッグモードを有効にしている場合は wp-content/debug.log もチェックする。

Before WordPressデータベースエラー Column ‘mint_email_id’ cannot be null がログに記録される
↓
After エラーは発生せず、静かに購読解除メタが保存される
■ エラー状態 ■ 修正後

どうしてもアップデートできない場合の一時的な対処

どうしてもアップデートできない場合の一時的な対処

何らかの理由でプラグインをすぐに更新できない場合、以下のコード修正を適用することでエラーを回避できる。ただし、この修正はプラグインの本体ファイルを直接変更するため、次回のアップデートで上書きされる。あくまで緊急措置として理解しておこう。

修正するファイルは app/Internal/Optin/UnsubscribeConfirmation.php だ。process_one_click_confirmation メソッド内の、$broadcast_email_id を取得した直後の処理を対象にする。

修正前(エラーが発生するコード)

$broadcast_email_id = EmailModel::get_broadcast_email_by_hash( $hash );
// ... 中略 ...
EmailModel::insert_or_update_email_meta( 'is_unsubscribe', 1, $broadcast_email_id );

修正後

$broadcast_email_id = EmailModel::get_broadcast_email_by_hash( $hash );
// ... 中略 ...
if ( ! empty( $broadcast_email_id ) ) {
    EmailModel::insert_or_update_email_meta( 'is_unsubscribe', 1, $broadcast_email_id );
}

このガードを追加することで、ハッシュが無効でブロードキャスト ID が null のままでも、データベースエラーが発生しなくなる。購読解除ステータスの更新は問題なく行われるため、最低限の動作は保たれる。

データベースエラーが解消したか確認する方法

データベースエラーが解消したか確認する方法

エラーログを監視して、同じメッセージが出力されなくなったかを確認する。WordPress のデバッグモードが有効な場合は、wp-content/debug.log を直接確認するか、管理画面からデバッグログを表示するプラグインを使うと手軽だ。サーバーのエラーログ(エラーログファイルや php-fpm のログ)にも同様のエントリがないかチェックする。

また、テスト用のメールを送信し、そのワンクリック解除リンクを実際にクリックして、エラーログに新たな記録が発生しないことを確かめるのが確実だ。

よくある質問

アップデートしてもエラーが続く場合は?

キャッシュ系プラグインやサーバーキャッシュが古いバージョンのファイルを保持しているケースがある。全キャッシュをクリアし、ブラウザのキャッシュも削除してから再度確認する。また、他のプラグインとの競合も考えられるため、標準テーマに切り替え、Mail Mint 以外のプラグインを一時的に無効化して切り分けを試みる。

一度発生したエラーログは削除したほうがよい?

特に削除する必要はないが、ログが肥大化してディスク容量を圧迫している場合は、ファイルを空にしたり、ログローテーションを設定したりするのが現実的だ。WordPress の debug.log は管理画面から直接内容を確認できるツールを使うのも手だ。

購読解除のメタ情報が記録されないとどんな問題が起きる?

ブロードキャスト単位での解除率や効果測定の集計が正しく取れなくなる可能性がある。ただし、購読解除そのものは正常に処理されているため、配信停止自体は問題なく行われている。レポートの精度を気にする場合は、エラー解消後に過去分のメタ情報を補完することを検討してもよい。

この記事のポイント

  • Mail Mint のワンクリック解除リンクでデータベースエラーが発生するのはプラグインの古いバグが原因
  • バージョン 1.30.0 以上への更新で根本的に解決する
  • 更新できない場合は null チェックを追加する一時パッチで回避可能
  • エラーは購読解除の処理自体を止めるものではないが、ログの肥大化に注意
  • 修正後はテストメールで解除リンクをクリックし、エラーログを確認する
大量メール配信の落とし穴、800,000通で自社サイトがダウンした理由

大量メール配信の落とし穴、800,000通で自社サイトがダウンした理由

2026年、WooCommerce.comが約80万の購読者に向けてニュースレターを一斉配信したところ、わずか数分でサイトがダウンするという思わぬトラブルが発生した。原因は攻撃でもリリースミスでもなく、メール配信そのものだった。配信先に企業向けメールシステムが多く含まれていたため、メールセキュリティスキャナーが一斉にリンク先を自動クロールし、膨大なトラフィックを引き起こしたのである。

この出来事は、当該チームに「大量メール配信はインフラの負荷テストと同義である」という教訓を残した。本記事では、この障害の経緯と原因、そして再発防止策を紹介する。メールマーケティング施策を運営するすべての企業にとって、無視できない警鐘だ。

800,000通のメールで自社サイトがダウン、その経緯

800,000通のメールで自社サイトがダウン、その経緯

ある日の午前9時15分(UTC)、WooCommerceのチームは約80万人に向けたニュースレター配信を実行した。配信開始からわずか3分後の9時18分、同僚からの「サイトが落ちている」という一報が届く。監視アラートが作動したのはその4分後(9時22分)であり、人が気づく方が先だった。

状況をさらに混乱させたのは、その朝には一切のデプロイがなく、攻撃の痕跡も皆無だった点だ。にもかかわらず、エッジレベルでのリクエスト総数は平時の約25万から急増し、ピーク時には約53万を記録した。実際のダウンタイムは3〜4分程度にとどまった。この短い間に、一部のユーザーには「429 Too Many Requests」が返され、ごく一部で5xx系エラーも発生したが、大多数のリクエストは正常な200応答を返し続けている。つまり「短時間の部分的な停止」であり、それでも立派なインシデントだった。

補足すると、当初のトラフィックグラフでは合計リクエスト数が実際の2倍に表示されるというダッシュボードの不具合が見つかった。後に修正されたが、正しい数字はステータス別の線であり、ピークは約53万、平常時が約25万。いつも通りの約2倍のトラフィックが数分間だけ発生したことに変わりはない。

原因はメールセキュリティスキャナーだった

原因はメールセキュリティスキャナーだった

まず疑ったのは当日のリリースや攻撃の兆候だが、どれも該当しなかった。しかしアクセスログには二つの異様な痕跡が残されていた。

一つは、トラフィック元の大半がデータセンターやVPNのIPアドレスで、実際のショッピング利用者が使うような一般ISPからではなかった点だ。もう一つは「JavaScript ChunkLoadError」の大量発生である。ChunkLoadErrorとは、HTMLだけを取得し、ページのJavaScript(JS)をダウンロードする前に接続が切断された場合に起こるエラーだ。数千回のこのエラーが数秒のうちに集中した。

この断片的な情報をつなぎ合わせると、犯人像が見えてくる。企業向けメールシステム(Office 365やMimecastなど)は、メールが受信トレイに届いた瞬間に、本文中のすべてのリンクを自動的にたどり、マルウェアチェックを行う。受信者がメールを開封する以前に、セキュリティスキャナーがリンク先を叩くのだ。

WooCommerceのニュースレターはストアオーナー向けだったため、送信先には企業ドメインが非常に多かった。80万通を一斉に配信すると、それら企業メールシステムのスキャナー群もほぼ同時に作動し、一瞬のうちに大量のリクエストが殺到した。これがスパイクの正体である。もし同じ配信をGmailが中心の一般消費者向けに行っていれば、このような急増は起きなかっただろう。

なぜ同じ規模の前回は耐えられたのか

なぜ同じ規模の前回は耐えられたのか

実はその1週間前にも、さらに大規模な配信を実施していた。その際にも今回とほぼ同じボットトラフィックのスパイクが発生していたが、誰も気づかないままインフラは何事もなく耐え抜いた。だから今回も「配信量が特に多すぎた」わけではない。

問題は配信のサイズではなく、タイミングだった。前回の配信では偶発的に、ボットの同時接続数がわずかに抑えられたり、キャッシュの状態が良好だったりした可能性がある。今回はほんのわずかな違いが、耐えられる負荷と許容限界との差になった。正確な理由を断定するのは難しいが、一瞬の集中がすべてを変えたことは確かだ。

オートスケーリングが追いつかなかった瞬間

オートスケーリングが追いつかなかった瞬間

WooCommerce.comはWordPress VIPのホスティング上で稼働しており、オートスケーリングは正常に動作していた。もしトラフィックが徐々に増加するパターンであれば、新しいリソースが立ち上がるまでの数分間で対応できたはずである。実際に追加されたキャパシティが整った頃には、スパイクはすでに通過し、被害も収束していた。

しかし今回の攻撃(自爆攻撃とも言える)は、段階的な増加ではなく「ステップ関数」のような瞬間的な跳ね上がりだった。スケーリングが反応するための傾斜が存在しないため、自動化の仕組みは事実上役に立たなかった。問題はサーバーに到達する前、配信の仕組みそのものにあったのだ。

一斉配信の場合(Before)
時間 →
秒単位で急上昇し、インフラが反応する前にピークが過ぎる
↓
バッチ配信(After)
時間 →
なだらかな増加でオートスケーリングが追随できる

トラフィックが瞬間的に跳ね上がる一斉配信と、分散されて緩やかな山になるバッチ配信の比較を示した。今回の対策では、後者の方式を採用することでスパイクを回避した。

対策〜バッチ配信でスパイクを防ぐ

対策〜バッチ配信でスパイクを防ぐ

次のキャンペーンは、たまたま1週間後のブラックフライデーに予定されていた。チームは全リストを一気に送信するのではなく、数時間かけて小分けにバッチ配信する方式に変更した。利用しているメール配信プラットフォームがこの機能をサポートしているかを事前に確認した上での判断である。

結果は明確だった。バッチ配信へ切り替えた後は、あのスパイクは一切発生しなくなった。追加のサーバーキャパシティは投入しておらず、今後も増強予定はない。オートスケーリングは自然な成長や季節変動を十分に吸収できるが、自ら招く瞬間的な高負荷には対応しきれないからだ。

大規模なマーケティングメールの配信は「インフラに関わるイベント」として認識し、特に最大規模の配信の前にはサーバー運用チームと連携することが推奨される。

大量メール配信は負荷テストである、という教訓

大量メール配信は負荷テストである、という教訓

企業向けのメールアドレスを含む大規模リストに一斉配信を行うと、受信者が何もしなくても、配信開始と同時にメールセキュリティスキャナーがすべてのリンクを叩く。これは結果として、自社サイトに対して意図しない大規模な負荷テストを実施しているのと同じだ。

重要なのは、配信停止やメールマーケティングの否定ではない。適切に管理すればニュースレターは強力なチャネルである。ただし、送信ボタンを押す前に「ボットによる一斉アクセスが起こりうる」と想定しておくことが不可欠だ。配信のタイミングを分散するだけでも、今回のような障害は回避できる。

この記事のポイント

  • 80万通のメール一斉配信で自社サイトが3〜4分ダウンした
  • 原因は企業向けメールセキュリティスキャナーの一斉リンクチェックだった
  • 同じ規模の前回は偶然耐えられたが、タイミング次第で失敗しうる
  • オートスケーリングは段階的な増加には強いが、瞬間的なスパイクには無力
  • 対策として配信を時間差バッチに変更し、再発を防止した
  • 大量メール配信は意図しない負荷テストとなりうる、分散配信が鍵