導入・背景
ある日突然、「サービスにアクセスできなくなった。」という報告をお客様から受けることがあると思います。
アラートのダッシュボードを見るとサーバが落ちているなどのアラートは上がっていませんが、確かにURLにアクセスすると繋がらない。。。そんな冷や汗が止まらないような状態がそこにはありました。
これは他人事ではなくて、実際に私の周りでも証明書の失効を起因としたサービス障害が発生しお客様への影響に至ったケースがありました。原因はシンプルで証明書の期限切れを監視しておらず、証明書が失効していたことです。
「AWSを使っているからACMが自動更新してくれるはず」という認識は半分正解で半分間違いで、自動更新が動くには一定の条件を満たしている必要があります。そもそも証明書が必ずしもACM発行とは限らないという点も見落とされやすいポイントだと感じています。
本記事は証明書失効のインシデントを踏まえて、同じ轍を踏まないための整理として書きました。
今後、サービス仕様の策定であったり基本設計の作成を行う方々の参考になれば幸いです。
想定読者
本記事は以下の読者を想定しています。
- AWSの基本的なサービス(ALB・CloudFront・Route 53など)を理解しているインフラエンジニア
- 構築後の運用設計も含めてシステムを担当している方
- 証明書やドメインの管理を引き継いだ、または整理したいと思っている方
※ ACMの発行操作やDNSの基本的な概念はある程度既知のものとして扱います。
証明書はACM発行だけじゃない
AWSでHTTPS通信を実現する手段としてACM(AWS Certificate Manager)の無料証明書が広く使われています。ただ現場ではいくつかのケースでACM以外の証明書が使われていることがあります。
- リフト&シフトでAWSに移行したシステム : 移行前から使っていたDigiCertなどの証明書をそのまま継続しているケース
- EC2上のNginx/Apacheに直接証明書を配置している : ACMはELBやCloudFrontなどのマネージドサービスにしか適用できないため手動で配置しているケース
- コンプライアンス要件でCAを指定されている : パブリックCAであればDigiCertなどを指定されるケースですね、プライベートCAであれば社内PKIやAWS Private CAを使うケースがあり管理フローが変わってきます
こういった証明書は更新が手動もしくは独自のフローになることが多く、メールや電話での認証が必要なケースもあります。そして証明書の更新作業自体が運用フローに組み込まれておらず気づいたら失効していたというパターンが一定数存在します。冒頭で触れたインシデントもこういった背景に近い状況でした。
ACM証明書の基礎 発行方式と検証方式
まずACM証明書の基本を整理しておきます。
発行方式
ACMでは以下の2種類の扱いがあります。
| 種別 | 概要 |
|---|---|
| ACMパブリック証明書 | AWSが無料で発行。ALB・CloudFront・API Gatewayなどに紐付けて使用 |
| インポート証明書 | DigiCertなどの外部CAで購入した証明書をACMにインポートして管理 |
インポート証明書はACMのコンソール上で一元管理できますが更新はACMが自動でやってくれません。ここが最初の落とし穴になりやすいです。冒頭のインシデントもサードパーティ証明書のインポート運用がベースになっており、更新が運用フローに組み込まれていなかったことが原因でした。
検証方式(ACMパブリック証明書の場合)
| 方式 | 概要 |
|---|---|
| DNS検証 | 指定されたCNAMEレコードをDNSに登録して検証 |
| メール検証 | ドメイン管理者メールアドレスに送られるメールを承認 |
新規で発行する場合はDNS検証を選んでおいた方がいいと思います。理由は後述しますが自動更新の信頼性という観点でDNS検証の方が圧倒的に安定しています。
ACMの自動更新が動く条件と失敗するパターン
ACMパブリック証明書は「自動更新される」という説明がありますが条件を満たさないと自動更新に失敗します。
自動更新が成功する条件
- 証明書が少なくとも1つのAWSリソース(ALBなど)に関連付けられている
- DNS検証の場合: 検証用CNAMEレコードがDNSに存在し続けている
- メール検証の場合: 更新メールに対して承認操作が行われる
失敗するパターン
1. DNSレコードが削除されている
Route 53でホストゾーンを再作成した、ドメインを別のレジストラに移管した、誰かが誤ってレコードを削除したなどの場合ですね。当然ですが、こういった場合に検証用CNAMEが消えて自動更新に失敗します。
# 検証用CNAMEの例
_abc123def456.example.com. CNAME _xyz789.acm-validations.aws.
このレコードが消えると、ACMは有効期限の45日前から開始する更新処理を正常に完了できなくなる可能性があります。DNS検証済み証明書の更新に失敗する主因は、検証用CNAMEレコードの欠落や不整合です。したがって、ホストゾーンの再作成やDNS移管時には、このCNAMEが引き継がれていることを必ず確認する必要があります。
2. メール検証で更新メールを誰も見ていない
メール検証の場合ACMは指定したメールアドレスに対してメールを送信します。
大体の案件の場合は運用・保守チーム向けのメーリスで管理をしているのではないでしょうか。
admin@example.comwebmaster@example.compostmaster@example.com
これらのアドレスを誰も監視していない、担当者が退職しているといったケースで承認漏れが発生します。サードパーティ証明書のメール・電話認証と構造は同じで、メール検証系の証明書は人に依存した更新フローになりやすいという点が共通の課題だと思っています。
3. ドメイン自体が失効している
証明書の前にドメインの有効期限が切れているというケースもあります。ドメインが失効するとDNS解決ができなくなるので証明書の自動更新どころかサービス全体が止まります。
4. インポート証明書は自動更新されない
再掲になりますが外部CAの証明書をACMにインポートしている場合、更新はすべて手動対応になります。ACMはコンソール上での管理はしてくれますが更新作業はしてくれません。
失効を防ぐためにやっておくこと
CloudFront用の証明書はus-east-1で発行する
CloudFrontに紐付ける証明書はus-east-1(バージニア北部)で発行したものしか使えません。CloudFrontがグローバルサービスであるためリージョンの制約があります。ALB向けに東京リージョンで発行した証明書をそのままCloudFrontに使い回そうとして詰まるケースが割とあるので覚えておくといいと思います。
DNS検証に統一する
新規に証明書を発行する場合はDNS検証を選んでおくのが無難です。メール検証との違いをまとめると以下の通りです。
| DNS検証 | メール検証 | |
|---|---|---|
| 自動更新 | CNAMEが残っていれば自動更新される | 毎回メールへの承認操作が必要 |
| 運用負荷 | 低い | 高い(担当者依存) |
| ドメイン移管時 | CNAMEの引き継ぎに注意が必要 | 比較的影響が少ない |
なおRoute 53をDNSとして使っている場合は証明書作成後の検証ステップで Create records in Route 53 というボタンが表示されます。これをクリックするとCNAMEレコードを自動追加してくれるので手動でレコードを登録する手間が省けます。
EventBridgeで期限切れを検知して通知する
ACMはデフォルトでCloudWatchメトリクスを公開していませんがAWS HealthイベントとEventBridgeを組み合わせることで証明書の期限切れ前に通知を受け取れます。
{
"source": ["aws.acm"],
"detail-type": ["ACM Certificate Approaching Expiration"]
}
このイベントはパブリック証明書では有効期限30日前から毎日、インポート証明書・プライベート証明書では45日前から毎日発火します。なお、この通知開始タイミングは ACM のアカウント設定で変更できます。SNSと組み合わせてSlackやメールに通知を流すのが定番の構成です。(参考:Supported AWS Certificate Manager events - AWS Certificate Manager)
EventBridge Rule
└─ ACM Certificate Approaching Expiration
↓
SNS Topic
↓
Lambda(Slack通知)or メール
インポート証明書にも同じ期限接近イベントが発火します。外部CAの証明書をACMにインポートしておくと、証明書監視の仕組みをACM管理の証明書とある程度統一しやすくなります。
ドメイン管理台帳を整備する
証明書の前にドメインが失効してしまうと元も子もないのでドメインの管理状況も整理しておく必要があります。
Route 53でドメインを管理している場合
- 自動更新が有効になっているかを確認する(デフォルトは有効)
-
Route 53 > Registered domainsから設定を確認できます
外部レジストラで管理している場合
- 自動更新設定の有無を確認する
- クレジットカードの有効期限切れで自動更新が失敗するパターンも割とあります
こういった情報をスプレッドシートでもいいので台帳として持っておくと担当者変更時の引き継ぎがスムーズになります。
| ドメイン | レジストラ | 有効期限 | 自動更新 | 証明書CA | 証明書期限 | 担当者 |
|---|---|---|---|---|---|---|
| example.com | Route 53 | 2026-09-01 | 有効 | ACM | 自動更新 | 山田 |
| legacy.example.jp | お名前.com | 2025-12-31 | 無効 | DigiCert | 2025-11-30 | 佐藤 |
定期的に棚卸しする
以下のコマンドでアカウント内の全証明書と更新ステータスを一覧確認できます。
# 証明書一覧の確認
aws acm list-certificates \
--query 'CertificateSummaryList[*].[DomainName,CertificateArn,Status]' \
--output table
# 有効期限・更新ステータスも含めて確認(jq使用)
aws acm list-certificates | \
jq -r '.CertificateSummaryList[].CertificateArn' | \
xargs -I{} aws acm describe-certificate --certificate-arn {} | \
jq -r '.Certificate | [.DomainName, .NotAfter, .RenewalSummary.RenewalStatus // "N/A"] | @tsv'
四半期に一度でも棚卸しをしておくと失効リスクのある証明書を事前に発見できます。
失効してしまったときのリカバリ
それでも失効してしまったときのために対応の流れを押さえておきます。
ACMパブリック証明書が失効した場合
- ACMコンソールから新規に証明書を発行する(既存の証明書を「更新」する概念はない点に注意)
- DNS検証の場合はCNAMEレコードを追加して検証を完了させる
- ALB/CloudFrontなどのリソースに新しい証明書を紐付け直す
- 古い失効証明書を削除する
ACMには基本的に失効した証明書に対してコンソール上から手動で延命更新するような運用はできません。そのため、失効後の復旧は新しい証明書の発行とリソース差し替えが基本になります。
インポート証明書(DigiCert等)が失効した場合
- CAのコンソールまたはサポートに連絡して新しい証明書を発行してもらう
- 発行された証明書をACMにインポートし直す
- リソースへの紐付けを確認する
サードパーティCAは再発行に時間がかかる場合があるので失効してから動き始めると復旧に数日かかることもあります。これが監視を事前に入れておく最大の動機だと思っています。
まとめ
証明書管理の要点は以下の3つだと思っています。
- 棚卸しをする ─ ACMコンソールで確認するとインポート証明書が混在していることがあります。どの証明書が誰によってどう管理されているかを把握するところから始めるのがいいと思います
- 自動更新に寄せる ─ 可能な限りACMパブリック証明書+DNS検証に統一することで人が介在しなくても更新が回る仕組みにしておく。ドメイン側の自動更新も忘れずに確認しておく
- 監視を入れる ─ EventBridgeのACM期限切れイベントで失効の前に気づける状態を作っておく。インポート証明書もACMに取り込んでおくと監視を一本化できる
加えてもう1点。サードパーティ証明書の更新にはお客様側の承認フロー(メール・電話認証など)が必要なケースがあります。そういった場合に万が一更新が間に合わなかったときのために、緊急時はACMパブリック証明書を一時的に適用してサービスを復旧させるという対応を事前にお客様と合意しておくことを強くおすすめします。失効してから承認フローを回し始めると復旧までに時間がかかりお客様影響が長引くリスクがあるため、こういった緊急対応の取り決めを運用設計の段階で盛り込んでおくと安心です。
これはあくまでも緊急時の対応ですので、新しいサードパーティ製の証明書が届いた場合にはすぐに置換することをお勧めいたします。
証明書の失効は「まさか自分のところには関係ない」と思っているときに起きると思っています。本記事が証明書管理の見直しをするきっかけになれば幸いです。