Chapter 09

CloudFront + S3の環境を作成して、フロントエンドアプリをデプロイする

shitakemura
shitakemura
2022.02.13に更新

はじめに

本チャプターでは、AWS CDK を使って、CloudFront + S3 の環境を作成し、ビルドしたフロントエンドアプリのデプロイを行います。

フロントエンド

フロントエンドアプリを静的 HTML ファイルに出力する

npm scriptsを以下の通り変更します。

./frontend/package.json
  "scripts": {
    ...
-   "build": "next build",
+   "build": "next build && next export",
    ...
  },

静的 HTML ファイルを出力します。

./frontend
$ npm run build

./frontend/outディレクトリが出力されているのを確認します。
この中のファイルを以降で作成する S3 にデプロイします。

インフラ & バックエンド

CloudFront + S3 の環境を作成する

AWD CDKを使って CloudFront + S3 の環境を作成します。

./infra-backend/lib/frontend-deployment-stack.ts
import * as cdk from "aws-cdk-lib";
import * as cloudFront from "aws-cdk-lib/aws-cloudfront";
import * as s3 from "aws-cdk-lib/aws-s3";
import { Construct } from "constructs";

export class FrontendDeployStack extends cdk.Stack {
  constructor(scope: Construct, id: string, props?: cdk.StackProps) {
    super(scope, id, props);

    const todoBucket = new s3.Bucket(this, "TodoBucket", {
      websiteIndexDocument: "index.html",
      autoDeleteObjects: true,
      removalPolicy: cdk.RemovalPolicy.DESTROY
    });

    const todoOAI = new cloudFront.OriginAccessIdentity(this, "TodoOAI");

    todoBucket.grantRead(todoOAI);

    const todoWebDestribution = new cloudFront.CloudFrontWebDistribution(
      this,
      "TodoWebDestribution",
      {
        originConfigs: [
          {
            s3OriginSource: {
              s3BucketSource: todoBucket,
              originAccessIdentity: todoOAI,
            },
            behaviors: [{ isDefaultBehavior: true }],
          },
        ],
      }
    );

    new cdk.CfnOutput(this, "TodoWebDestributionName", {
      value: todoWebDestribution.distributionDomainName,
    });
  }
}
./infra-backend/bin/index.ts
  import { InfraBackendStack } from "../lib/infra-backend-stack";
+ import { FrontendDeployStack } from "../lib/frontend-deploy.stack";

  const app = new cdk.App();
  new InfraBackendStack(app, "InfraBackendStack", {});
+ new FrontendDeployStack(app, "FrontendDeployStack", {});

cdk synthで CloudFormation テンプレートを確認し、cdk deployでデプロイを行います。

./infra-backend
$ cdk synth FrontendDeployStack
$ cdk deploy FrontendDeployStack

出力した静的 HTML ファイルを S3 にデプロイする

出力した静的 HTML ファイル./frontend/out内のファイルを S3 にデプロイします。

./infra-backend/lib/frontend-deployment-stack.ts
+ import * as s3Deployment from "aws-cdk-lib/aws-s3-deployment";
+ import * as path from "path";

export class FrontendDeployStack extends cdk.Stack {
  constructor(scope: Construct, id: string, props?: cdk.StackProps) {
    super(scope, id, props);
    ...

    const todoWebDestribution = new cloudFront.CloudFrontWebDistribution(
      ...
    );

+   new s3Deployment.BucketDeployment(this, "TodoBucketDeployment", {
+     sources: [
+       s3Deployment.Source.asset(
+         path.resolve(__dirname, "../../frontend/out")
+       ),
+     ],
+     destinationBucket: todoBucket,
+     distribution: todoWebDestribution,
+     distributionPaths: ["/*"],
+   });

    ...
  }
}

デプロイします。

./infra-backend
$ cdk diff FrontendDeployStack
$ cdk deploy FrontendDeployStack

AWS 管理画面の AWS S3 > frontenddeploymentstack-todobucketXXXXXX を開き、out ディレクトリ内のファイルがデプロイされているのを確認します。

CloudFront > ディストリビューション より、オリジンが frontenddeploymentstack-todobucketXXXXXX のディストリビューションを選択し、ディストリビューションドメイン名 を確認します。

ディストリビューションドメイン名でブラウザを開き、アプリが動作するか確認します。

以上で CloudFront + S3 の環境作成、フロントエンドアプリのデプロイは完了です。

参考情報