CDKでFargateを構築してみる with TypeScript
最近、AWS の勉強を始めました。はじめはコンソールでぽちぽちしてたんですが、自分がした作業をふりかえりやすいので、CDK を使うようになりました。
今回は、CDK を使って Fargate でサンプルアプリを動作させてみます。言語は TypeScript です。
今回書いたコードは下記に置いてあります。
AWS CDK のセットアップ
下記を参考に進めます。
下記を参考に、AWS アカウントを作っておきます。
ローカルマシンに AWS CLI と CDK をインストールします。
$ brew install awscli aws-cdk
下記を参考に、AWS CLI に AWS アカウントを紐づけます。
$ aws configure
CDK を初期化します。
$ cdk bootstrap aws://<AWSアカウントID>/<リージョン>
CDK プロジェクトを初期化します。今回は TypeScript を使います。
$ cdk init app --language typescript
$ ls
bin/
lib/
node_modules/
test/
README.md
cdk.json
jest.config.js
package-lock.json
package.json
tsconfig.json
必要なファイルが一通り生成されました。
Docker イメージの準備
動作させる Docker イメージを準備します。
今回は、下記の Node.js のサンプルページに従って進めます。
ポートだけ、サンプルページと違って、80 に変更しています。
後ほど package-lock.json を生成する必要があるので、Node.js をインストールします。
$ brew install node@14
今回は、CDK のリポジトリに app/ ディレクトリを作って、そこにコードを置くことにします。
$ mkdir app
$ cd app
サンプルページに沿ってファイルを準備します。
{
"name": "docker_web_app",
"version": "1.0.0",
"description": "Node.js on Docker",
"author": "First Last <first.last@example.com>",
"main": "server.js",
"scripts": {
"start": "node server.js"
},
"dependencies": {
"express": "^4.16.1"
}
}
"use strict";
const express = require("express");
const PORT = 80;
const HOST = "0.0.0.0";
const app = express();
app.get("/", (req, res) => {
res.send("Hello World");
});
app.listen(PORT, HOST);
console.log(`Running on http://${HOST}:${PORT}`);
FROM node:12
WORKDIR /usr/src/app
COPY package*.json ./
RUN npm install
COPY . .
EXPOSE 80
CMD [ "node", "server.js" ]
node_modules
npm-debug.log
package-lock.json を生成します。
$ npm install
Docker イメージをビルドします。
$ docker build . -t node-web-app
一度動かしてみます。
$ docker run -p 80:80 -d node-web-app
ローカルで動作することを確認できました 🎉
ECR へ Docker イメージを push
下記を参考に進めます。
ECR に対して Docker クライアントを認証します。
$ aws ecr get-login-password --region <リージョン> | docker login --username AWS --password-stdin <AWSアカウントID>.dkr.ecr.<リージョン>.amazonaws.com
ECR リポジトリを作ります。
今回は、sample-node-web-app という名前で作りました。
$ aws ecr create-repository \
--repository-name sample-node-web-app \
--image-scanning-configuration scanOnPush=true \
--region <リージョン>
IMAGE ID を確認します。
$ docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
node-web-app latest 75ed3927be19 7 minutes ago 920MB
イメージに ECR 用のタグをつけます。
$ docker tag 75ed3927be19 <AWSアカウントID>.dkr.ecr.<リージョン>.amazonaws.com/sample-node-web-app:latest
イメージを push します。
$ docker push <AWSアカウントID>.dkr.ecr.region.amazonaws.com/sample-node-web-app:latest
CDK で Fargate を構築する
いよいよ本題です。
lib/fargate-cdk-sample-stack.ts を書き換えていきます。
下記を参考にしています。
import { Stack, StackProps } from "aws-cdk-lib";
import { Construct } from "constructs";
import * as ec2 from "aws-cdk-lib/aws-ec2";
import * as ecr from "aws-cdk-lib/aws-ecr";
import * as ecs from "aws-cdk-lib/aws-ecs";
import * as ecs_patterns from "aws-cdk-lib/aws-ecs-patterns";
export class FargateCdkSampleStack extends Stack {
constructor(scope: Construct, id: string, props?: StackProps) {
super(scope, id, props);
const vpc = new ec2.Vpc(this, "MyVpc", { maxAzs: 2 });
const cluster = new ecs.Cluster(this, "Cluster", { vpc });
const repository = ecr.Repository.fromRepositoryName(
this,
"SampleRepository",
"sample-node-web-app" // 先ほど作ったリポジトリ名
);
new ecs_patterns.ApplicationLoadBalancedFargateService(
this,
"FargateService",
{
cluster,
taskImageOptions: {
image: ecs.ContainerImage.fromEcrRepository(repository),
},
}
);
}
}
デプロイします。
$ cdk synth
$ cdk deploy
cdk deploy
で最後の方にコンソールに出力されている URL にアクセスしてみます。
無事、デプロイできました 🎉
あとがき
Web コンソールでぽちぽちやってるときより、楽しいと感じました。
このあたりが楽しかったのかな、とふりかえってます。
- 一応 TypeScript のコードを書くことになること
- デプロイするときのバーが進む感じが何となくカッコイイ
楽しさは大事ですね。
Discussion