記事の概要
- AWSへリソースをデプロイ/管理するIaCツールとして
terraform
の利用経験はあったが aws-cdkは経験がなかった。 - また
node.js
やtypescript
の開発経験もありません。 - そんな私が
aws-cdk
へ入門した際のメモ。
やった事
- 頭を空にしてAWSの公開している 入門ガイド に沿ってサンプルコードで
VPCとサブネットを作成する
ところまでをとりあえず。- AWS CDK の使用を開始する 入門ガイド: https://aws.amazon.com/jp/getting-started/guides/setup-cdk/
事前用意したもの
- 作業PC
- 今回は macを使用して作業した
- AWS CLIの実行環境
-
brew instal awscli
などする。
-
- node.js実行環境
-
brew install node
でもよいが、nodeのバージョン管理ツールを使った方がよさそう。
-
- AWS CLI の認証情報
- AWSアカウントID(12桁の数字)
- リージョン: 今回は
ap-northeast-1
を使用した -
AdministratorAccess
相当の権限を持ったIAMユーザ - 手元の作業環境に 同IAMユーザのAPIキーを設定した profileの設定
- 今回は
cdk-test
という profileをあらかじめ用意した
入門ガイドに沿ってやっていく
- AWS CDK の使用を開始する 入門ガイド: https://aws.amazon.com/jp/getting-started/guides/setup-cdk/
とりあえず 入門ガイドに沿ってやっていきます
1. aws-cdk cli インストール
ここから https://aws.amazon.com/jp/getting-started/guides/setup-cdk/module-two/
AWS CDK CLI をインストールするためには、まず、Node Package Manager をインストールする必要があります。 次のコマンドを実行して、AWS CDK CLI をグローバルにインストールします
なるほど、はい。
作業PCに グローバルで aws-cdk cli をインストールしていきます。
% npm install -g aws-cdk
バージョン確認
% cdk --version
2.45.0 (build af1fb7c)
無事にインストールできたようです。
cdk の実行は cdk
で良いようです。
helpを見たい時は cdk --help
で確認できるようです。
% cdk --help
Usage: cdk -a <cdk-app> COMMAND
Commands:
~
2. bootstrapの実行
デプロイする多くの AWS CDK スタックには、アセット、AWS Lambda 機能や Docker イメージなど、スタックとともにデプロイされる外部ファイルが含まれています。CDK は、これらをAmazon S3 バケットや他のコンテナにアップロードして、デプロイ中に AWS CloudFormation で使用できるようにします。デプロイには、これらのコンテナが AWS アカウントとデプロイ先のリージョンに既に存在していることが必要です。これらのコンテナの作成は、ブーストラップと呼ばれています。AWS アカウント (および特定のリージョン) をブートストラップするには、次を実行します。
...はい。
要は このcdk bootstrap
を実行することでAWSアカウント上に、aws-cdkを使うためのリソース一式を用意してくれるようです。
ドキュメントに沿ってコマンドを実行していきます
% aws sts get-caller-identity
Unable to locate credentials. You can configure credentials by running "aws configure".
...認証情報が無いぞ的なエラー
上記のコマンドはアクセスしようとしているAWSのアカウント情報を表示してくれるコマンドのようです。
今回は 検証用に profileを cdk-test
で用意していたので --profile で指定。
% aws sts get-caller-identity --profile cdk-test
{
"UserId": "xxxxxxxxxxxxx",
"Account": "123456789012",
"Arn": "xxxxxxxxxxxx"
}
※ 実際の値とは異なります
profile cdk-test の情報を確認できました。
アカウントID
と決めておいたデプロイ先のリージョンap-northeast-1
を指定して cdk bootstrap
を実行。
cdk bootstrap aws://123456789012/ap-northeast-1
※ 実際の値とは異なります
指定した "AWSアカウント" と "リージョン” の組み合わせで "初めて" bootstrapが実行された場合、aws-cdk用のリソース一式が作成されるようです。
既にAWS側に関連リソースが存在する場合は再作成はされない。が、必要に応じてバージョンアップされるようです。
3. 新しい CDK プロジェクトを作成する
ここから https://aws.amazon.com/jp/getting-started/guides/setup-cdk/module-three/
新しい CDK プロジェクトを作成するために、CDK CLI を使用します。開始するには、システムに空のディレクトリを作成し、そのディレクトリに変更します。次に、cdk init を使用して、新しい TypeScript CDK プロジェクトを作成します。
cdk-demo
ディレクトリを作成し、そこへ移動、cdk init --language typescript
コマンドを実行するようです
mkdir cdk-demo
cd cdk-demo
cdk init --language typescript
下記のようなディレクトリ/ファイル郡が作成された事を確認した。
% tree -L 1
.
├── README.md
├── bin
├── cdk.json
├── jest.config.js
├── lib
├── node_modules
├── package-lock.json
├── package.json
├── test
└── tsconfig.json
4. インフラストラクチャを作成する
最初の VPC を作成する前に、cdk init コマンドが作成したファイルを理解する必要があります。
...なるほど。
入門ガイドに書いてある事を読んで cdk init
で作られたものをとりあえず確認していきます...
https://aws.amazon.com/jp/getting-started/guides/setup-cdk/module-three/
CDK アプリケーションを構築してデプロイする
入門ガイドを読み進める。
├── bin
│ └── cdk-demo.ts
├── cdk.json
├── jest.config.js
├── lib
│ └── cdk-demo-stack.ts
├── package.json
├── package-lock.json
├── README.md
├── test
│ └── cdk-demo.test.ts
└── tsconfig.json
重要なファイルのいくつかとそれらの用途は次のとおりです。
- bin/cdk-project.ts
* これは CDK アプリケーションへのエントリポイントです。これにより、lib/* で定義したすべてのスタックがロード/作成されます。- lib/cdk-project-stack.ts
* ここでメインの CDK アプリケーションスタックが定義されます。リソースとそのプロパティはこちらに含めることができます。- package.json
* ここで、プロジェクトの依存関係、およびいくつかの追加情報とビルドスクリプト (npm build、npm test、npm watch) を定義します。- cdk.json
* このファイルは、アプリケーションの実行方法、および CDK とプロジェクトに関連する追加設定とパラメータをツールキットに指示します。lib/cdk-demo.ts ファイルと bin/cdk-demo.ts ファイルに焦点を当てます。コードを追加しましょう。
... cdk init
で吐かれた構成では bin/ckd-project.ts
lib/cdk-project-stack.ts
というファイルは居ないが bin/cdk-demo.ts
と lib/cdk-demo-stack.ts
のことでよさそう。
bin/cdk-demo.ts
lib/cdk-demo-stack.ts
- package.json
- cdk.json
あたりを抑えておけば良さそう?
アプリケーションでいくつかのことを定義する
bin/cdk-demo.ts スタックを次のように変更します。AWS アカウント ID を正しい番号に置き換え、正しいリージョンを選択してください。このガイドでは、us-east-1 または eu-west-1 のいずれかを選択することをお勧めします。
...はい。
とりあえず今回は ap-northeast-1
を使うと決めてるのでそのように記述していきます。
#!/usr/bin/env node
import 'source-map-support/register';
import * as cdk from '@aws-cdk/core';
import { CdkDemoStack } from '../lib/cdk-demo-stack';
const app = new cdk.App();
new CdkDemoStack(app, 'CdkDemoStack', {
env: { account: '123456789012', region: 'ap-northeast-1' },
});
※ 実際の値とは異なります
env:
の行にAWSアカウントと リージョンを設定して保存。
cdk init
で作成されたテンプレートを編集しようとして少し注意が必要だった点として
入門ガイドに掲載されていたコードは、cdk init
で出力されたコードとimportの書き方が若干異なりました。
// cdk init で吐かれたテンプレートの import
import * as cdk from 'aws-cdk-lib';
↓
// 入門ガイドの import
import * as cdk from '@aws-cdk/core';
aws-cdk v1とv2の違いとかだろうか?(どうも入門ガイドの方が v1の書き方で古いっぽい気配?)
VPC のコード
モジュールをインストールするには、npm を使用します。プロジェクトディレクトリで次のコマンドを実行します。
...はい。
npm install @aws-cdk/aws-ec2
package.json
というファイルが作成され、必要なモジュール類がインストールされたようです。
これで、VPC を作成する準備が整いました。lib/cdk-demo.ts でスタック定義を開きます。最初にファイルを開くと、次のようなものが表示されます。
これがこのプロジェクトの骨組みです。ここで CDK を実行する場合、まだ定義していないため、リソースは作成されません。VPC の使用を開始するには、インストールされているモジュールをインポートし、その中のコードモジュールを参照する必要があります。Vpc クラスと SubnetType クラスをインポートします。
VPC を作成するには、以下に示すように、2 つの AZ と詳細を指定してパブリックサブネットを作成します。
なるほど。lib/cdk-demo.ts
では
- 必要なモジュールを追加して
- リソースを定義する。
...ってコト?
import * as cdk from '@aws-cdk/core';
// CHANGE: This is where you import the classes from the module:
import { Vpc, SubnetType } from '@aws-cdk/aws-ec2';
export class CdkDemoStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
// The code that defines your stack goes here
// CHANGE: We have created the vpc object from the Vpc class.
const vpc = new Vpc(this, 'MainVpc',{
// CHANGE: this is where we define how many AZs to use
maxAzs: 2,
// CHANGE: We define a single subnet configuration per AZ.
subnetConfiguration: [
{
// CHANGE: this is it's CIDR mask so 255.255.255.0
cidrMask: 24,
// CHANGE: a name for each of these subnets
name: 'public-subnet',
// CHANGE: and the subnet type to be used - here we will have
// a public subnet. There are other options available here.
subnetType: SubnetType.PUBLIC
},
]
});
}
}
※ このファイルも、cdk init
で出力されたテンプレートの内容と 入門ガイド で掲載されているコードの import 内容が少し異なったので、init のテンプレートを元に変更しようとする場合は注意が必要。
これで、このインフラストラクチャの変更をアカウントにデプロイする準備が整いました。
やったね。
デプロイ時間
デプロイをテストする時間です。コードが有効かどうかを確認するには、TypeScript を JavaScript にコンパイルする npm ビルドを実行します。それが成功した場合は、次のデプロイコマンドを実行できます。
はい。なるほど?
% cdk deploy --profile cdk-test
...と。早まってこれをすぐ実行してしまうと、確認なしで AWS側へデプロイされてしまうようです。割と怖い?。
入門記事の文面は、おそらく要は test を通してから、という事を言いたかった?が、具体的な test については特に触れずにスルーされている?
記事には無かったが cdk deploy
する前に cdk diff
コマンドを使うと terraform plan
と同じように変更差分を確認できるようです。
% cdk diff --profile cdk-test
また、cdk synth
コマンドでデプロイされるCFnそのものが 同じ階層の ckd.out/ ディレクトリに出力されるのでCFnを読める場合は内容を確認できるようです。
% cdk synth
記事で飛ばされている test については、node.js または typescript での適切なテストを構築する必要があるようです。
私にはまだその辺の知見があまり無いので一旦スルー。
問題なさそうなら cdk deploy
します。
% cdk deploy --profile cdk-test
deploy が成功すると、指定したAWSアカウントとリージョンで
-
CloudFormation
に今回実行したstack が新たに作成されている事 - コードで記述したVPCとサブネット、および付随するリソースが新規に作成されている事
が確認できました。また、
-
cdk diff
で出ていた IGW や Routetable はコードには明示的に書いて無いが自動で作成されていた。CFnのスタック内を確認すると暗黙的に作成されたリソースも確認できる。 - リソースの
Name
タグはTerraform
では設定しなければ付与されなかったが、aws-cdkでは自動でわかりやすい物が付与されていた。良いですね。
リソースをクリーンアップする (オプション)
今回作成したリソースをまとめて削除する事ができます
% cdk destroy --profile cdk-test
stack名が表示され、消していいか聞かれるので'y' と回答すると、先ほどcdk deploy
で作成されたCFn一式が削除されました。
というところまでで 入門ガイド の内容は終了。
フォルダ構造、設定、スタック、アプリケーションなどの概念について詳しく知りたい場合は、ドキュメントを読むことをお勧めします。
https://docs.aws.amazon.com/ja_jp/cdk/v2/guide/home.html
はい、今後も功夫を積んで行きたいと思います。
その他
CFn の stack 名を変えてみる
今回サンプルにしたコードの場合は bin/cdk-demo.ts
ファイルの下記の部分で変更できました。
new CdkDemoStack(app, 'CdkDemoStack', {
↓
new CdkDemoStack(app, 'myDemoStack', {
NameタグやCFnのスタック名に付与される Prefixになっているようです。
が、デプロイ済みのスタック名を後から変更した場合、変更
としての追従はされず 別のスタック
として扱われるようでした。
設計,運用時には注意が必要になりそう。
AZの数を変えてみる
lib/cdk-demo-stack.ts
の設定箇所を変えれば簡単に変更できました。
// CHANGE: this is where we define how many AZs to use
maxAzs: 2,
リソースごとのパラメータはドキュメントを見て行けばよさそう。
変更後は cdk diff
で差分を確認して cdk deploy
すれば反映されました。
感想
- 今回はVPCとSubnetを作っただけだったが比較的少ない操作でも実現できるのは良い体験だった。
- CFnを素で書こうと思うと、個人的には大変な苦痛を伴う事が多いので 読みやすい言語で書けるのはよさそう。
- AWSが開発しているのでAWSを使う上では新機能への追従などは
terraform
より早そう?という期待。 - 今回参考にした入門記事が aws-cdk v1準拠で書かれている場合は、v2に対応させるという事もやってみるか...
- ECSを操作する
aws copilot
という同じくAWSの開発しているOSSがあるが、使用感が近いかもと思った。