AWS CDK(Python)を使って繰り返し処理でEC2インスタンスを作成してみる

2019.05.27

おはようございます、もきゅりんです。

最近、CFnを触ることが多いのですが、先日、CFnのBlackBeltを改めて眺めていると、(遅ればせながら)AWS Cloud Development Kit (以下、AWS CDK)に気付きました。

こいつあ楽しそうじゃないですか〜。

世の中の皆さんは割りとTypeScriptでトライしているし、自分は敢えてJavaで久し振りに何か書いてみようかな、なんて思ってたら、タイムリーにPythonが追加されているじゃないですか!

これは乗るしかない!と思って触ってみたのがこのブログです。

なお、触って思ったのが、やはりCFnで手が届かない、痒そうな部分に手の届く柔軟感が良さそうです。

また、yamlで作成したときの冗長感だったり、構成が複雑になってきたときの可読性の悪さを改善できそうだな、と感じました。

個人的には今後も使っていきたいツールと感じました。

やること

  • Exampleのapplication-load-balancerを試してみること
  • ParameterStoreから最新のAmazonLinux2のAMIを取得して既存VPCでEC2インスタンスを2つ起動する

前提条件

AWS CDKを利用するには、Node.js等の前提ツールが必要になります。本エントリではAWS CDKのセットアップについては割愛しますのでGetting Started with the AWS CDKをご確認ください。

なお、今回はPythonで対応するのですが、改めて注記すべき点は以下です。

  • Node.js >= 8.11.x

  • Python >= 3.7.1

それと、自分はMacなのですが、Pythonを3.7.Xにする際に怒られた際、こちらを参考にしました。

[MacOS Mojave]pyenvでpythonのインストールがzlibエラーで失敗した時の対応

application-load-balancerで試してみる

まずは、CDK Examplesでウォームアップ。

application-load-balancerを選びました。

ふんふん、言われた通りに進めていきます。

npm install -g aws-cdk
cd python/application-load-balancer
pip3 install -r requirements.txt

ん...? 何かpylintが怒っている気がする...と思いつつも見て見ぬふりをして進めます。

cdk deploy

# 以下エラー
Traceback (most recent call last):
File "app.py", line 36, in
LoadBalancerStack(app, "LoadBalancerStack")
File "/usr/local/lib/python3.7/site-packages/jsii/_runtime.py", line 66, in __call__
inst = super().__call__(*args, **kwargs)
File "app.py", line 14, in __init__
vpc = ec2.VpcNetwork(self, "VPC")
AttributeError: module 'aws_cdk.aws_ec2' has no attribute 'VpcNetwork'

あーやっぱりそうだよね...で、どうなってんだ?....なんてハマっていたら、こんなのを見つけました...

https://github.com/awslabs/aws-cdk/issues/2577

- ec2.VpcNetwork
+ ec2.Vpc

上記のようにして、修正して実行すると...

無事できました。

確認できたので、消しましょう。

cdk destroy

繰り返し処理でEC2インスタンスを作成してみる

そしたら、今回の本題に入ります。

やることとしては、Hello World Tutorialのように順に進んで、準備していきます。

かなり雑いコードですが、検証なのでお許しを。

mkdir ec2-cdk
cd ec2-cdk
cdk init --language python
pip3 install aws-cdk.aws_ec2
# app.py
Ec2CdkStack(app, "Ec2CdkStack")
# ec2_cdk_stack.py
from aws_cdk import (
aws_ec2 as ec2,
cdk,
)

class Ec2CdkStack(cdk.Stack):

def __init__(self, app: cdk.App, id: str, **kwargs) -> None:
super().__init__(app, id)

ssh_key="YOUR_KEY"

image_id = ec2.AmazonLinuxImage(
generation=ec2.AmazonLinuxGeneration.AmazonLinux2).get_image(self).image_id

for i in range(1, 3):

ec2.CfnInstance(self,
"WebServer" + str(i),
availability_zone="ap-northeast-1a",
image_id=image_id,
instance_type="t2.micro",
key_name=ssh_key,
security_group_ids=["sg-xxxxxxxxxxxxxx"],
subnet_id="subnet-xxxxxxxxxx",
tags=[{
"key": "Name",
"value": "Demo" + str(i)
}]
)
cdk synth
cdk deploy
# 確認
aws ec2 describe-instances \
--filter "Name=instance-state-name,Values=running" |
jq -r '.Reservations[].Instances[] |
.Tags[].Value + "\t" + .InstanceId' | sort

確認できたら、消えてもらいます。

cdk destroy

あとがき

とりあえず、楽しいですね!

ただ情報が比較的まだ少なめなので、自分は結構どうでもよいところでハマりそうな予感してます。

(というか、つまらんところでハマりました...)

時間的に厳しい場合は、通常のCFn使っちゃいそうだけど、ちょこちょこと使っていきたいですね!

オマケ

https://github.com/awslabs/aws-cdk/issues/1248で書かれているように、まだMFA対応していなそうなので、MFAを導入している場合は、AWS CLI で一時的なセキュリティ認証情報を使用するで書かれているように、認証情報を環境変数に出力してCDKコマンドを実行したら良いかと思います。

export AWS_ACCESS_KEY_ID=AKIAI44QH8DHBEXAMPLE
export AWS_SECRET_ACCESS_KEY=wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY
export AWS_SESSION_TOKEN=AQoDYXdzEJr...
aws ec2 describe-instances --region us-west-1

でも、当然いやいや、そんなんいちいちメンドくさいわ、、、ってなりますよね。 そんな方には是非、下記弊社ブログの設定をお勧めします!

[小ネタ]ディレクトリ移動した際に自動で一時クレデンシャルを取得・設定する

すいません、宣伝でした!

以上、どなたかのお役に立てれば幸いです。

参考

Getting Started With the AWS CDK/Hello World Tutorial

【awslabs探訪】AWS Cloud Development Kit (AWS CDK)を使ってみた

AWS Cloud Development Kit (AWS CDK)でECS環境を構築してみた

[MacOS Mojave]pyenvでpythonのインストールがzlibエラーで失敗した時の対応