[アップデート] Amazon CloudFrontのセットアップが一部簡略化および自動化されました! #AWSreInforce

[アップデート] Amazon CloudFrontのセットアップが一部簡略化および自動化されました! #AWSreInforce

Clock Icon2025.06.18

こんにちは、コンサルティング部の神野です。

本日、re:Inforce 2025でAWSからAmazon CloudFrontのセットアップが一部簡略化および自動化するアップデートが発表されました。

image (10)

https://aws.amazon.com/about-aws/whats-new/2025/06/amazon-cloudfront-streamlines-cdn-setup-smart-defaults-automation/

この新しいエクスペリエンスでは、Amazon Route 53 を使用して DNS レコードを、AWS Certificate Manager (ACM) を使用して TLS 証明書を自動的にプロビジョニングおよび管理します。

ディストリビューションを作成する際、CloudFront は特定のオリジンタイプに基づいて最適化された設定を自動的に適用するようになりました

まとめると2点大きな変更点がありました。

  • CloudFrontのディストリビューション作成時にコンソール上からACMとシームレスに連携してTLS証明書を作成およびプロビジョニングを行う
  • Amazon S3 から静的ウェブサイトを作成場合、バケットへの直接アクセスを防ぐためにCloudFront はオリジンアクセスコントロール(OAC)を自動的に設定する

早速コンソール上から触ってみて記事にしました!!

やってみた

S3でホスティングしている静的ウェブサイトをCloudFront経由で配信する設定をしてみます。

前提

  • Route53にパブリックホストゾーンが作成済みであること
  • 使用するドメインのネームサーバーがRoute53に向いていること

事前準備

今回は静的ファイルを配信する用のS3バケットを作成します。
任意の名前を入れてパブリックアクセスブロックを有効にしてバケットを作成します。

CleanShot 2025-06-18 at 01.25.02@2x

下記HTMLファイルをindex.htmlとして作成したS3バケットに配置します。

index.html
index.html
<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>CloudFront配信テストページ</title>
    <style>
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }

        body {
            font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, Cantarell, sans-serif;
            line-height: 1.6;
            color: #333;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            min-height: 100vh;
            display: flex;
            align-items: center;
            justify-content: center;
            padding: 20px;
        }

        .container {
            background: rgba(255, 255, 255, 0.95);
            border-radius: 20px;
            box-shadow: 0 20px 40px rgba(0, 0, 0, 0.1);
            padding: 40px;
            max-width: 800px;
            width: 100%;
            text-align: center;
            backdrop-filter: blur(10px);
        }

        h1 {
            color: #667eea;
            font-size: 2.5em;
            margin-bottom: 20px;
            animation: fadeInDown 1s ease-out;
        }

        .cloudfront-icon {
            width: 100px;
            height: 100px;
            margin: 0 auto 30px;
            background: linear-gradient(45deg, #ff6b6b, #f06595);
            border-radius: 50%;
            display: flex;
            align-items: center;
            justify-content: center;
            animation: pulse 2s infinite;
        }

        .cloudfront-icon::before {
            content: "☁️";
            font-size: 50px;
        }

        .status {
            background: #e6fffa;
            border: 2px solid #4fd1c5;
            border-radius: 10px;
            padding: 20px;
            margin: 30px 0;
            animation: fadeIn 1.5s ease-out;
        }

        .status h2 {
            color: #319795;
            margin-bottom: 10px;
        }

        .info-grid {
            display: grid;
            grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
            gap: 20px;
            margin: 30px 0;
        }

        .info-card {
            background: #f7fafc;
            padding: 20px;
            border-radius: 10px;
            box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);
            transition: transform 0.3s ease;
            animation: fadeInUp 1s ease-out;
            animation-fill-mode: both;
        }

        .info-card:nth-child(1) { animation-delay: 0.1s; }
        .info-card:nth-child(2) { animation-delay: 0.2s; }
        .info-card:nth-child(3) { animation-delay: 0.3s; }

        .info-card:hover {
            transform: translateY(-5px);
            box-shadow: 0 8px 12px rgba(0, 0, 0, 0.15);
        }

        .info-card h3 {
            color: #764ba2;
            margin-bottom: 10px;
        }

        .info-card p {
            color: #718096;
            font-size: 0.9em;
        }

        .test-image {
            width: 200px;
            height: 150px;
            background: linear-gradient(45deg, #667eea, #764ba2);
            border-radius: 10px;
            margin: 20px auto;
            display: flex;
            align-items: center;
            justify-content: center;
            color: white;
            font-weight: bold;
            animation: slideIn 1s ease-out;
        }

        .footer {
            margin-top: 40px;
            padding-top: 20px;
            border-top: 1px solid #e2e8f0;
            color: #718096;
            font-size: 0.9em;
        }

        .timestamp {
            font-family: 'Courier New', monospace;
            background: #f7fafc;
            padding: 5px 10px;
            border-radius: 5px;
            display: inline-block;
            margin-top: 10px;
        }

        @keyframes fadeInDown {
            from {
                opacity: 0;
                transform: translateY(-30px);
            }
            to {
                opacity: 1;
                transform: translateY(0);
            }
        }

        @keyframes fadeIn {
            from { opacity: 0; }
            to { opacity: 1; }
        }

        @keyframes fadeInUp {
            from {
                opacity: 0;
                transform: translateY(30px);
            }
            to {
                opacity: 1;
                transform: translateY(0);
            }
        }

        @keyframes pulse {
            0% { transform: scale(1); }
            50% { transform: scale(1.05); }
            100% { transform: scale(1); }
        }

        @keyframes slideIn {
            from {
                opacity: 0;
                transform: translateX(-50px);
            }
            to {
                opacity: 1;
                transform: translateX(0);
            }
        }

        @media (max-width: 768px) {
            h1 { font-size: 2em; }
            .container { padding: 30px 20px; }
            .info-grid { grid-template-columns: 1fr; }
        }
    </style>
</head>
<body>
    <div class="container">
        <div class="cloudfront-icon"></div>
        <h1>CloudFront 配信テスト</h1>

        <div class="status">
            <h2>✅ 配信ステータス: 正常</h2>
            <p>このページはAmazon CloudFrontを通じて配信されています</p>
        </div>

        <div class="info-grid">
            <div class="info-card">
                <h3>🚀 高速配信</h3>
                <p>世界中のエッジロケーションから最も近い場所からコンテンツを配信</p>
            </div>
            <div class="info-card">
                <h3>🔒 セキュア</h3>
                <p>HTTPS配信とAWS WAFによる保護でセキュアな配信を実現</p>
            </div>
            <div class="info-card">
                <h3>📊 スケーラブル</h3>
                <p>トラフィックの増減に自動的に対応し、常に安定した配信を提供</p>
            </div>
        </div>

        <div class="test-image">
            テスト画像
        </div>

        <p style="margin: 20px 0;">
            このページは、CloudFrontの動作確認用のサンプルページです。<br>
            キャッシュの動作確認やヘッダー情報の確認にご利用ください。
        </p>

        <div class="footer">
            <p>Amazon CloudFront Sample Page</p>
            <div class="timestamp" id="timestamp"></div>
        </div>
    </div>

    <script>
        // ページ読み込み時刻を表示
        document.getElementById('timestamp').textContent = 
            'ページ読み込み時刻: ' + new Date().toLocaleString('ja-JP');

        // CloudFrontのレスポンスヘッダーを確認(デベロッパーツールで確認可能)
        console.log('CloudFront配信テストページが読み込まれました');
        console.log('デベロッパーツールのNetworkタブで以下のヘッダーを確認できます:');
        console.log('- X-Cache (CloudFrontのキャッシュヒット/ミス)');
        console.log('- X-Amz-Cf-Id (CloudFrontのリクエストID)');
        console.log('- X-Amz-Cf-Pop (配信元のエッジロケーション)');
    </script>
</body>
</html>

CleanShot 2025-06-18 at 01.28.07@2x

アップデートが完了したらCloudFrontでディストリビューションを作成します。

ディストリビューションの作成開始

CloudFrontのコンソール画面にアクセスして、
ディストリビューションを作成ボタンを選択します。
CleanShot 2025-06-18 at 01.13.05@2x

すると表示が今までとは異なっていて、下記バナーメッセージが表示されて、体験をより良くしたよと書いてありますね。

  • We've streamlined the process of creating a CloudFront distribution. Continue here and let us know what you think. Or go to the previous Create Distribution page.

CleanShot 2025-06-18 at 01.19.24@2x

ディストリビューション名など基本的な情報を入力します。
事前にドメインを入力しておくことで、ACMの署名書発行およびドメイン検証もシームレスに出来るようになるので入力しておきます。入力してCheck domainを選択して問題がなければDomain managed by Route53と表示されます。

CleanShot 2025-06-18 at 01.59.01@2x

オリジンの設定

オリジンタイプとして「Amazon S3」を選択し、対象のS3バケットを指定します。

注目すべきは、「Grant CloudFront access to origin」オプションです。これがデフォルトで有効になっており、以下の処理が自動的に行われます。

  • S3バケットポリシーの更新(CloudFrontからのアクセスを許可)
  • Origin Access Control(OAC)の設定

これにより、S3バケットを完全にプライベートにしつつ、CloudFront経由でのみアクセス可能にすることができます。これが自動で設定されるのはいいですね。

CleanShot 2025-06-18 at 01.36.20@2x 1

ちなみにバケットポリシーは下記のようにS3に自動設定されます。

{
	"Version": "2008-10-17",
	"Id": "PolicyForCloudFrontPrivateContent",
	"Statement": [
		{
			"Sid": "AllowCloudFrontServicePrincipal",
			"Effect": "Allow",
			"Principal": {
				"Service": "cloudfront.amazonaws.com"
			},
			"Action": "s3:GetObject",
			"Resource": "arn:aws:s3:::sample-cloudfront-test-yjinno/*",
			"Condition": {
				"ArnLike": {
					"AWS:SourceArn": "arn:aws:cloudfront::yyy:distribution/xxx"
				}
			}
		}
	]
}

AWS WAFの設定

次のステップでは、AWS WAFの設定が提示されます。

CleanShot 2025-06-18 at 01.37.31@2x

この箇所は今までも設定が可能だったので特に目新しい追加項目はないかと思います。
セキュリティ保護を有効にして、Use monitor modeをオンにします。

ACMの証明書発行 ~ 検証

次にTLS証明書を作成するか聞かれるので、Create Certificateボタンを選択します。

CleanShot 2025-06-18 at 01.59.47@2x

作成して1分少々ぐらいで検証まで完了します。
シームレスに連携できて良いですね。

CleanShot 2025-06-18 at 02.00.11@2x 1

レビュー

CleanShot 2025-06-18 at 08.35.14@2x

ここまでで設定した項目が正しいか確認して、問題なければCreate distributionを選択して作成します。

作成が完了したら、代替ドメイン名にあるRoute domains to CloudFrontを選択します。

CleanShot 2025-06-18 at 02.40.33@2x

選択したらポップアップが表示されるので、Set up routing automaticallyを選択してAレコードを追加します。
CleanShot 2025-06-18 at 02.14.15@2x
これでディストリビューションの作成が完了です!

動作確認

カスタムドメイン名でアクセスしてみると問題なくHTMLが返却されてWebページが確認できます。

CleanShot 2025-06-18 at 02.44.06@2x

コンテンツとドメインの準備が整っていればコンソール上から簡単にWAFやACMと連携しつつサクッとディストリビューションを作成できましたね。

おわりに

コンソール上からS3バケットをオリジンとした場合、OACの設定が自動で行われるようになったかつ、ACMとの連携もサクッと実現できて良きですね。

本記事が少しでも参考になりましたら幸いです。
最後までご覧いただきありがとうございましたー!!

Share this article

facebook logohatena logotwitter logo

© Classmethod, Inc. All rights reserved.