claude mail postfix puppet sre

Claude Code Skillでメール障害対応を実施

claude mail postfix puppet sre

こんにちは、技術部 技術基盤グループのkmsnです。

GMOペパボが運営するECサイト構築サービス「カラーミーショップ」で、Outlook/Hotmail/Live宛メールがブロックされる障害が発生しました。この記事では、Claude Code の Skill を活用して障害の初動対応を効率化した事例を紹介します。

結論:Skill で障害対応の初動が変わった

先に結論をお伝えします。今回の障害対応で最も効果的だったのは、Claude Code の Skill によって状況把握のスピードが大幅に上がったことです。

カラーミーショップのメールサーバーは数十台あります。従来であれば、障害発生時に1台ずつ SSH して sudo postqueue -p を叩き、キューの状態を目視で確認していく必要がありました。台数が多いため状況把握だけで時間がかかり、その間もメールは滞留し続けます。

今回は colorme-mailq Skill を使い、「メールキュー確認して」の一言で全台の状態を一括取得しました。

サーバー active deferred 合計
server-1 0 3,842 3,842
server-2 12 0 12

※ 上記は全数十台のうち抜粋

特定サーバーの deferred が突出して積み上がっていることが一目でわかり、対応する方針をすぐに決められました。従来の手動確認では状況把握に時間を要していた工程が、Skill によって数秒で完了し、対応方針の決定までの時間を大幅に短縮できました。

さらに、この Skill は社内のプライベートリポジトリに登録されているため、自分だけでなくチームの誰でも同じように使えます。個人のスクリプトではなく チーム共有の Skill として整備しておくことで、次に同様の障害が起きたときにも誰でも素早く初動に入れるという点が大きな価値です。

何が起きたか

カラーミーショップのユーザーが送信したメールが、Outlook/Hotmail/Live宛に届かずブロックされる事象が発生しました。Microsoft(Outlook.com)のような大手プロバイダーは、スパム判定によるブロック時に 5xx 系(主に 550)のエラーを返すことがあります。ただし、Postfix 側の設定や一時的なレスポンスにより deferred キューに滞留するケースもあり、今回はキューの滞留として顕在化しました。

ログを確認したところ、特定のショップドメインからの大量送信が引き金となり、送信を担うサーバーの IP が Microsoft(Outlook.com)側にブロックされたと判断しました。

Postfix transport で Outlook 宛の配送経路を変更する

Skill で状況を把握した後、ブロックされたサーバーを迂回する対応を取りました。これには Postfix の transport テーブルを使います。

transport テーブルは「特定ドメイン宛の配送を、どの経路で行うか」を定義するファイルです。Outlook 系ドメイン宛のメールを別の経路に切り替える設定を追加しました。

また /etc/postfix/transport を確認すると、以前のインシデント時に手動で投入された送信レート制御の設定が残っていました。今回は別の経路への切り替えで対処するため不要と判断し、削除した上で新しい設定を追加しました。

手動設定を Puppet でコード化する

ここで課題に当たりました。対象サーバーの /etc/postfix/transportPuppet で管理されておらず、手動設定のみの状態だったのです。

先ほどのレート制御の設定がまさにその典型で、何のためのものか、誰が投入したのかがすぐに追えない状況でした。手動設定が蓄積すると、こうした「経緯のわからない設定」が増えていきます。

別のメールサーバーでは hieradata/nodes/ 配下にノード専用の yaml が存在し、transport 設定が Puppet で管理されていました。一方、対象サーバーにはその yaml が存在しません。チームメンバーにアドバイスをもらいながら、以下の2択で検討しました。

  • A: 対象サーバーのノード yaml だけに書く → そのサーバーのみに適用。他サーバーへの影響なし
  • B: ロール共通の yaml に書く → 全メールサーバーに一律適用

既存実装を参考に、今回は A を選択。対象サーバー専用のノード yaml を新規作成し、このサーバーとしては初めて transport 設定を Puppet 管理に取り込みました。

チームメンバーのレビューを受けてマージし、--noop での dry-run で差分を確認してから本適用しました。

sudo puppet agent --test --noop  # dry-run で変更内容を事前確認
sudo puppet agent --test         # 本適用

経路の切り替えが正常に動作していることを確認し、復旧しました。

なお、transport による経路変更はあくまで暫定的な緩和措置であり、根本対処ではありません。これを恒久的な対処としてしまうと、迂回先のサーバーにも負荷が偏るなど新たな問題を招く可能性があります。並行して Microsoft への delist 申請や送信元ショップへの対応など、根本原因の解消に向けた対処を実施し、解消後に transport の設定を元に戻すところまでが一連の対応です。

その他の学び

カスタマーサポート(CS)への連携は「確定情報だけ」を素早く。

技術的な調査の完了を待たず、判明した情報(発生時刻・影響範囲・復旧時刻)をその都度 CS に共有するほうがユーザー影響を最小化できます。調査の過程をすべて流すのではなく、確定した情報だけをタイムリーに伝えるというシンプルな判断が、慣れないうちは意外と難しいと感じました。

手動設定は「なぜ入っているか」が追えなくなる。

今回 Puppet に設定を取り込んだことで、次の担当者が経緯を追いやすくなりました。障害のたびに手動で設定を足していくのではなく、コードに残す習慣が大切だと改めて感じました。

おわりに

今回の対応を通じて、障害対応の定型作業を Skill として整備しておくことの効果を実感しました。状況把握の速さは、そのまま復旧の速さにつながります。

この考え方はメール障害に限りません。たとえば Web サーバーのエラーレート急増時にログを集約する、データベースのスロークエリを一覧する、といった「障害発生直後にまず確認すること」は、どの領域にもあるはずです。こうした初動の定型作業を Skill として整備しておくことで、経験の浅いメンバーでも素早く状況把握に入れるようになり、経験豊富なメンバーは情報収集の手間を省いて判断や対応方針の策定に集中できます。

同様の取り組みを検討されている方の参考になれば幸いです。