Amazon Web Services ブログ
Application Load Balancer での mTLS 導入について
本稿は、2024年5月21日に Networking & Content Delivery で公開された “Introducing mTLS for Application Load Balancer” を翻訳したものです。
AWS は 2023年11月26日、Application Load Balancer (ALB) で X509 証明書を使用したクライアントの相互認証機能をサポートすると発表しました。この記事では、この新機能を実装するためのオプションと、実装時に考慮すべき点について説明します。
ALB はアプリケーション層 (OSI モデルの第7層) で動作し、バックエンドターゲットに着信する HTTP/HTTPS リクエストのロードバランシングを行います。ALB は一般的に、スケーラブルで安全な Web アプリケーションを作成するために使用され、ホスト名、完全パス、または HTTP ヘッダー条件に基づいてルーティングできる高度なルーティングルールをサポートしています。詳細については、Application Load Balancer のドキュメントを参照してください。
セキュリティの観点から、ALB では HTTPS リスナーを作成できます。HTTPS リスナーを使用すると、ALB はクライアントとの TLS セッションを終端します。ALB には、AWS WAF とのネイティブ統合機能があり、Web アプリケーション用のルールを作成し、ALB の背後で実行されているアプリケーションを保護できます。
mTLS コンセプト
相互トランスポート層セキュリティ (mTLS) は、ネットワーク通信を保護するために使用される TLS プロトコルを拡張したものです。TLS は通常、インターネット上の安全な接続を確立するために使用され、認証、データの機密性、および整合性を確保します。ただし、従来の TLS では、認証は一方向であり、サーバーがクライアントに対して自身を認証しますが、クライアントの身元は検証されません。
これに対し、mTLS では、サーバーとクライアントの両方が相互に認証することが求められるため、「相互」または「双方向」TLS と呼ばれています。mTLS に関連する概念として以下のようなものがあります:
- 認証局 (CA): 企業にTLS証明書を提供する組織や団体のことです。認証局は、TLS 証明書を発行する前に、ドメイン名と所有者の詳細を確認します。
- TLS 証明書: システム (Web クライアントなど) が別のシステム (Web サーバーなど) の身元を検証できるようにする、デジタルオブジェクトです。TLS 証明書に含まれる詳細情報により、クライアントはサーバーとの暗号化された接続を確立できます。
- サーバー証明書: サーバーの身元を証明する TLS 証明書です。
- クライアント証明書: クライアントの身元を証明する TLS 証明書です。
- 証明書信頼チェーン: TLS 証明書の順序付きリストです。チェーンは (クライアント/サーバーの TLS 証明書である) リーフ証明書から始まり、ルート証明書で終わります。リーフ証明書とルート証明書の間の証明書は中間証明書と呼ばれます。チェーンの各証明書は、次の証明書で識別された組織/団体によって署名されています。これは図1に示されています。
- TLS ハンドシェイク: クライアントとサーバーが相互に TLS 証明書を使って認証を行い、暗号化の標準に合意し、データを安全に転送するための secure チャネルを作成するプロセスです。詳細については、TLS のドキュメントを参照してください。クライアントは、TLS ハンドシェイク中に TLS 証明書をサーバーと共有します。これにより、サーバーはクライアントを認証できます。
- 証明書失効リスト (CRL): 信頼されるべきではないブロックリストに載せられた証明書のリストです。
mTLS プロセスは、スマートデバイス、API、マイクロサービス間の通信を保護したり、規制要件を満たすために相互の身元を確認する必要がある状況で一般的に使用されます。また、VPN (仮想プライベートネットワーク) や組織内部の通信を保護するためにも使用されています。
mTLS を実装するには、サーバーとクライアントの両方が信頼できる CA によって発行された電子証明書を持っている必要があります。これらの証明書は同じ CA または異なる CA によって生成することができ、ハンドシェイク過程で相手の信頼性を証明するために使用されます。
Application Load Balancerで mTLS クライアント認証を使用する
Application Load Balancer は、クライアントの証明書チェーンの深さと大きさが一定の範囲内にある場合、mTLSをサポートしています。現在サポートされている最大サイズと深さについては、Application Load Balancer のクォータをご確認ください。ClientCertExceedsDepthLimit および ClientCertExceedsSizeLimit の各 Amazon CloudWatch メトリクスを使用すると、これらの制限を超えた要求を追跡できます。
Application Load Balancer は、mTLSで以下の2つの動作モードをサポートしています:
- mTLS 検証モード
- mTLS パススルーモード
mTLS 検証モード
Application Load Balancer で mTLS検証モードを使用するには、トラストストアを作成する必要があります。トラストストアには、クライアント証明書を検証するために使用される1つの CA 証明書バンドルがあります。自分の証明書を持参するか、AWS Certificate Manager(ACM) を使用して証明書を生成できます。ALB の mTLS 検証モードには、AWS 管理の CA を使用できます。AWS Private Certificate Authority は、高可用性の管理CA サービスで、組織がプライベート証明書を使用してアプリケーションとデバイスを保護するのに役立ちます。証明書の発行と管理の詳細については、ACMのドキュメントを参照してください。
信頼しないクライアント証明書を指定するには、1つ以上の証明書失効リスト (CRL) をトラストストアに関連付けます。失効リストを S3 バケットにアップロードし、そのバケットをトラストストアで指定します。ALB は S3 から CRL をインポートし、CRL チェックは ALB によって行われるため、毎回 S3 から CRL をフェッチする必要がなくなります。これにより、ALB は CRL を使用したクライアント認証時に遅延を生じません。CRL 構成の詳細については、ドキュメントの「Application Load BalancerでのTLSによる相互認証」のページをご覧ください。
この検証モードでは、ALB がトラストストアを使用してクライアント証明書を検証します。これにより、有効な証明書で認証されたクライアントのみがバックエンドターゲットと通信できます。ALB は、認証されていないユーザーからのリクエストをブロックします。これにより、mTLS 認証に必要な計算負荷の大きな処理を ALB にオフロードし、バックエンドターゲットの処理リソースをアプリケーションサービスの提供に使用できます。図2は、検証モードのアーキテクチャを示しています。
ALB の mTLS 検証モードは以下のステップで検証されます。
[1] CA 証明書バンドルを Amazon S3 にアップロードし、必要に応じて CRL もアップロードします。
[2] トラストストアを作成し、CA 証明書バンドルの Amazon S3 パスを指定します。必要に応じて CRL の Amazon S3 パスも指定します。
[3] クライアントが ALB との TLS セッションを開始します。TLS ハンドシェイク中に、クライアントは TLS 証明書を提示します。
[4] TLS セッションが ALB で終了します。TLS ハンドシェイク中に、ALB はサーバー側の証明書を提示し、クライアントの証明書を受け取ります。
[5] ALB は トラストストアを参照し、証明書を検証します。信頼できない CA によって署名された証明書、証明書失効リスト (CRL) に記載された証明書、有効期限切れの証明書の場合、クライアント認証は失敗します。クライアント認証が失敗する可能性のあるシナリオの完全なリストについては、ドキュメントの「Application Load BalancerでのTLSによる相互認証」のページを参照してください。クライアント認証に失敗した場合、ALB は TLS 接続を拒否します。ただし、必要に応じて期限切れの証明書を許可するようALBを設定することができます。
[6] クライアントと ALB 間で TLS セッションが正常に確立されます。
[7] ALB はバックエンドのターゲットとは別のセッションを作成します。
ALB が TLS セッションを終端するため、バックエンドターゲットへのトラフィックの負荷分散には、ALB のルーティングアルゴリズムを使用できます。例えば、重み付きラウンドロビンルールを使用して、Web アプリケーションのブルーグリーンデプロイメントを作成できます。
クライアント認証を実行するほか、ALB は次の証明書メタデータをバックエンドターゲットに送信します。
X-Amzn-Mtls-Clientcert-Serial-Number – リーフ証明書の16進数表記、クライアント証明書のシリアル番号。例: 0ABC1234。
X-Amzn-Mtls-Clientcert-Issuer – XN_FLAG_RFC2253 フラグを使って X509_NAME_print_ex で印刷された発行者の識別名(DN)
X-Amzn-Mtls-Clientcert-Subject – XN_FLAG_RFC2253 フラグを使って X509_NAME_print_ex で印刷された件名 DN
X-Amzn-Mtls-Clientcert-Validity – notBefore と notAfter 日付の ISO8601 形式、例: NotBefore=2023-09-21T01:50:17Z; NotAfter=2024-09-20T01:50:17Z
X-Amzn-Mtls-Clientcert-Leaf – URLエンコーディングされたPEM形式のリーフ証明書
この情報を使用すると、バックエンドターゲットでこれらのメタデータフィールドに基づいてロジックを実装できます。例えば、X-Amzn-Mtls-Clientcert-Leaf フィールドを解析して証明書の有効期限を取得し、証明書の有効期限が近づいている場合にクライアントにカスタムメッセージを送信できます。
mTLS パススルーモード
このモードでは、ALB はクライアント認証のために HTTP ヘッダー AMZN-MTLS-CLIENT-CERT でバックエンドターゲットに証明書チェーン全体を転送します。ALB は、リーフ証明書を含む証明書チェーン全体を、URL エンコーディングされた PEM 形式で、+、=、/ を安全な文字として挿入します。AMZN-MTLS-CLIENT-CERT ヘッダーの例を次に示します。
X-Amzn-Mtls-Clientcert:
`-----BEGIN%20CERTIFICATE-----%0AMIID<...reduced<br />...>do0g%3D%3D%0A-----END%20CERTIFICATE-----%0A-----BEGIN%20CERTIFICAT<br />E-----%0AMIID1<...reduced...>3eZlyKA%3D%3D%0A-----END%20CERTIFICATE---<br />--%0A`
バックエンドのターゲットは、この HTTP ヘッダーを解析し、証明書を抽出して、クライアント認証を実行できる必要があります。クライアント認証プロセスを制御したい場合は、このモードを使用します。図3がパススルーモードのアーキテクチャです。
ALB の mTLS パススルーモードは以下のステップで検証されます:
[1] クライアントが ALB と TLS セッションを開始します。 TLS ハンドシェイク中に、クライアントは TLS 証明書を提示します。
[2] TLS セッションは ALB で終了します。 TLS ハンドシェイク中に、ALB はサーバー側の証明書を提示し、クライアントの証明書を受け取ります。
[3] ALB はバックエンドターゲットとの新しいセッションを作成します。このセッションは HTTP または HTTPS のいずれかになり、ユーザー構成に基づきます。 ALB は、AMZN-MTLS-CLIENT-CERT という HTTP ヘッダーに完全な証明書チェーンを含めます。
[4] バックエンドターゲットはクライアント証明書を受け取り、AMZN-MTLS-CLIENT-CERT HTTP ヘッダーからクライアント証明書チェーンを解析するロジックを実装する必要があります。また、ターゲットはクライアント認証を実行するロジックを実装する必要があります。
mTLS パススルーモードが有効な場合、クライアント証明書が存在しないと、ALB は HTTP ヘッダーを追加しません。バックエンドターゲットは、クライアント証明書のない要求を処理するロジックを実装する必要があります。
バックエンドターゲットでクライアント認証に失敗した場合、ターゲットは HTTP エラーコードを ALB に送り返す必要があります。ALB はこのエラーコードをクライアントに転送します。
HTTPS リスナーの場合、バックエンドターゲットはクライアントの証明書に基づいてクライアントを認証し、ALB はクライアントとの間の TLS 接続を終端し、ターゲットとの別の TLS セッションを開きます。ALB とバックエンドターゲットの間の TLS セッションは、ターゲットにインストールした証明書を使って作成されます。
ALB が TLS 接続を終端するため、バックエンドターゲットへのトラフィックの負荷分散には ALB のルーティングアルゴリズムを使用できます。
スマートカーが一時的にインターネット接続を失うなど、一部のスマートデバイスは長期間オフラインになる可能性があります。このような場合、バックエンドターゲットには期限切れの TLS 証明書を処理するロジックを実装する必要があります。
パススルーモードを実装するもう1つのユースケースは、アプリケーションベースのクッキー (Cookie) の実装です。この場合、バックエンドターゲットが認証済みクライアントにクッキーを発行し、クライアントはこのクッキーを通信に使用します。これにより、バックエンドターゲットが各要求の証明書チェーン全体を処理する必要がなくなります。オープンソースライブラリを使ってバックエンドターゲットにクッキーを実装し、クッキーに基づいてクライアントの認証ステータスを追跡するロジックを実装できます。
モニタリング
ALB は、ロードバランサーに送信されたすべてのリクエストについて、接続ログを提供します。これらのログはAmazon Simple Storage Service(Amazon S3)バケットに送信され、クライアントの IP アドレス、TLS 暗号化の詳細、リクエストが拒否された場合のエラーコードなどの詳細が含まれます。詳細については、「Application Load Balancer の接続ログ」を参照してください。
ALB の mTLS サポートに関する CloudWatch メトリクスの完全なリストは、「Application Load Balancer の CloudWatch メトリクス」で確認できます。
ALB の mTLS モードと Network Load Balancer (NLB) の比較
HTTPS アプリケーションをお持ちの場合、アプリケーションレベルのルーティングを行いたい場合は、ALB の検討をお勧めします。例えば、HTTPS リクエストに対して重み付きラウンドロビンの負荷分散を実行することで、ブルー/グリーンのようなデプロイメントを作成できます。ALB を使用すると、TLS/mTLS 操作をオフロードすることもできます。ただし、ALB がクライアントの TLS セッションを終了するため、ALB 用の証明書をアップロードする必要があります。
一方、NLB はトランスポート層 (OSIモデルのレイヤー4) で動作し、TCP/UDP コネクションの低レイテンシー負荷分散を提供します。HTTPS アプリケーションの場合、特定のセキュリティコンプライアンスルールによりサーバーがクライアントのTLS 接続を終了する必要がある場合は、Network Load Balancer (NLB) の使用をお勧めします。
表1は、ALB と NLB のパススルーモードと検証モードのサポートを比較し、各オプションの考慮事項を示しています。
ALB + mTLS検証モード | ALB + mTLS パススルーモード | NLB | |
---|---|---|---|
クライアント認証 | ALB で実行、AWS が管理 | バックエンドターゲットで実行、お客様が管理 | バックエンドターゲットで実行、お客様が管理 |
クライアントのSSL/TLSセッション終了 | ALB で実行、AWS が管理 | ALB で実行、AWS が管理 | バックエンドターゲットで実行、お客様が管理 |
ルーティングルール機能 | ALB のL7 ルーティングルール | ALB のL7 ルーティングルール | NLB のポートとプロトコルによるルーティングルール |
Conclusion
この投稿では、Application Load Balancer (ALB) の mTLS 検証モードとパススルーモードについて説明し、各モードを使用する際の考慮事項を議論しました。クライアント認証に ALB を使用したい場合は、ALB で mTLS 検証モードを使用します。バックエンドターゲットでクライアント認証を制御したい場合は、mTLS パススルーモードが最適です。トラストストアを使用するには追加料金がかかり、mTLS を有効にする際には Application Load Balancer の価格を考慮する必要があります。詳細については、Elastic Load Balancing の価格ページをご覧ください。
この機能は 2023年11月26日にリリースされましたので、ぜひお試しいただき、ご質問やコメントがあれば、AWS サポートまでお問い合わせください。
本記事は、Introducing mTLS for Application Load Balancerを翻訳したものです。翻訳は Solutions Architect の 中本 が担当しました。