概要
- Suga で新規ユーザーの不審なサインアップを発見
- Subscription bombing (サブスクリプションボミング)という攻撃手法の説明
- 攻撃の発見から調査、対応策の実施までの流れ
- Cloudflare Turnstile や認証フローの改善による対策
- 今後の教訓と再発防止策
Sugaで発生した不審な新規ユーザー登録
- 数週間前、 新規ユーザー が登録後に何も操作せず放置される事例を複数発見
- 通常は登録後すぐに 組織やプロジェクト作成 などのアクションがあるため、異常値として目立つ
- 新規ユーザー名が ランダム文字列 (例: PfVQXvYTXjwSbEeJBjXYy)で構成されていた
- Resend (メールサービス)で確認すると、実在するメールアドレス宛にウェルカムメールが正常に送信
- 怪しいと感じ、攻撃の可能性を調査開始
サブスクリプションボミングとは
- Subscription bombing は、ボットが被害者のメールアドレスを使い、無数のウェブサイトでサインアップを行う攻撃手法
- 目的はアカウント乗っ取りではなく、 被害者の受信箱を大量のノイズメールで埋め尽くすこと
- 攻撃者はその隙に、 銀行口座のパスワードリセット や クレジットカード申込 などを実行
- 本当に重要な通知メールがノイズに埋もれ、被害者が気づきにくくなる
- 大量のサイトが メールアドレス検証なしでメール送信 していることが原因
攻撃パターンと検知の経緯
- 3月12日に 最初の異常なサインアップ を検知、その後2日間でさらに2〜3件/日発生
- 当初は ペンテスト(脆弱性検証) の可能性を疑うも、同様のパターンが継続
- PostHog で「パスワードを忘れた」ページへのアクセスが異常に多いことを確認
- ボットは本物のメールアドレス+ランダム名で登録し、60秒以内にパスワードリセットを要求
- 被害者には「メールアドレス確認」「ウェルカム」「パスワードリセット」の3通が1分以内に届く
- ボットはフォーム入力時に 一文字ずつ不自然な間隔でタイプ、人間らしさを装うが挙動が均一
- アクセス元国と時間帯に相関がなく、 世界中から均等にアクセス されていた
サブスクリプションボミングの特徴
- 一度に大量リクエストやサーバー負荷増加はなし、 1〜2件/時の低頻度
- 国や時間帯の分布が不自然、通常ユーザーとは異なるトラフィックパターン
- レートリミット (一定時間あたりのリクエスト制限)が無効、しきい値以下で活動
- サイト運営者側への直接的な被害は少なく、 被害は主にメールアドレスの持ち主
被害の実態とサイト運営者の責任
- 被害者は 一晩で200通以上 の不要メールを受信し、重要な通知を見逃すリスク
- サインアップフォームが 未検証のメールアドレスにメールを送る仕様 は攻撃の温床
- サイト運営者が被害を認識しづらく、 対応が後回しになりがち
- 実際には ユーザーデータの汚染 や、サービスがハラスメントの片棒を担ぐことになる
実施した対策
- ファイアウォール強化 でボット検知を厳格化、ただしAPIの正規トラフィックも考慮し調整
- 6時間運用で2件のすり抜けを確認、 完全な防御には至らず
- Cloudflare Turnstile (CAPTCHA代替)を導入し、ユーザー体験を損なわずにボット排除
- Better Auth のCAPTCHAプラグインで簡単に実装
- サインアップ・サインイン・パスワードリセット全ページに @marsidev/react-turnstile を追加
- トークン取得まで送信ボタンを非活性化
- Turnstile導入後、 ボットのサインアップは完全に停止
- 今後のダメージ最小化のため、 メールは認証済みユーザーのみに送信
- 検証前は 確認メールのみ 送信、ウェルカムやアップデート通知は認証後
- GoogleやGitHub認証の場合は即時ウェルカムメール送信(メールアドレスが既に検証済み)
今後の教訓とまとめ
- 1〜2件/時の異常サインアップでも 見逃さず、迅速に対応
- 被害者への直接連絡は控え、 根本的な再発防止策 を優先
- 攻撃パターンの早期検知のためのレポート強化 を追加
- 今回の対応は妥当かつ迅速だったが、 初めから対策を講じるべきだった と反省
- サービス運営者は ユーザーの安全と信頼性 を最優先に考えるべき教訓