はじめに
過去の記事(【Pulumi】Pulumi AIが生成したコードでEC2インスタンスを構築したい~第1章:YAML編~)では、
Pulumi AIで生成したYAMLをもとにしてEC2インスタンスを構築しました。
今回はEC2インスタンス構築後にスクリプトを実行して、Ansible Navigatorを使用可能な環境を構築します。
TL;DR
- PulumiでEC2インスタンス構築後にスクリプトを実行するには、aws:ec2:Instanceの
userData
の箇所にスクリプトを記載する - スクリプトは
root
ユーザーで実行されるので、特定のユーザーでの処理がある場合はsu
コマンドでユーザーを切り替える
前提条件
PulumiでAWSを操作するには以下が必要です
- Pulumiのアカウントを所持していること
- AWSにてIAMユーザーのアクセスキーが作成してあること
実行環境
- Amazon マシンイメージ(AMI)
- Amazon Linux 2023 AMI
- Pulumi
- v3.112.0
詳細
1. 事前準備
- 過去の記事(【Pulumi】Pulumi AIが生成したコードでEC2インスタンスを構築したい~第1章:YAML編~)における以下の箇所を実施する
- アクセストークンの作成
- EC2インスタンスにPulumiをインストール
- Pulumi Projectの作成
2. AWSリソースの定義ファイル作成
-
AWSリソースの定義ファイル(
Pulumi.yaml
)を以下のように記載する- 【Pulumi】Pulumi AIが生成したコードでEC2インスタンスを構築したい~第1章:YAML編~で紹介した定義ファイルと大差ありません
-
aws:ec2:Instanceに
userData
が追加されています
--- name: quickstart runtime: yaml description: A program to create an AWS EC2 instance within a VPC with a subnet and security group, accessible over the internet. variables: amiId: "<amiId>" # ex) ami-xxxxxxxxxxxxxxxxx keyName: "<keyName>" instanceType: "<instanceType>" # ex) t2.micro resources: # Create a new VPC myVpc: type: aws:ec2:Vpc properties: cidrBlock: "10.0.0.0/16" tags: Name: "my-vpc" # Create an Internet Gateway myInternetGateway: type: aws:ec2:InternetGateway properties: vpcId: ${myVpc.id} tags: Name: "my-internet-gateway" # Create a new Subnet within the VPC mySubnet: type: aws:ec2:Subnet properties: vpcId: ${myVpc.id} cidrBlock: "10.0.1.0/24" mapPublicIpOnLaunch: true availabilityZone: ${aws:region}a tags: Name: "my-subnet" # Create a new Route Table myRouteTable: type: aws:ec2:RouteTable properties: vpcId: ${myVpc.id} tags: Name: "my-route-table" # Create a route that directs 0.0.0.0/0 to the Internet Gateway myRoute: type: aws:ec2:Route properties: destinationCidrBlock: "0.0.0.0/0" gatewayId: ${myInternetGateway.id} routeTableId: ${myRouteTable.id} # Associate the Route Table with the Subnet myRouteTableAssociation: type: aws:ec2:RouteTableAssociation properties: subnetId: ${mySubnet.id} routeTableId: ${myRouteTable.id} # Create a Security Group within the VPC mySecurityGroup: type: aws:ec2:SecurityGroup properties: vpcId: ${myVpc.id} description: "Allow SSH inbound traffic" tags: Name: "my-security-group" ingress: - protocol: "tcp" fromPort: 22 toPort: 22 cidrBlocks: ["0.0.0.0/0"] egress: - protocol: "-1" # Allow all outbound traffic fromPort: 0 toPort: 0 cidrBlocks: ["0.0.0.0/0"] # Launch an EC2 instance within the subnet myInstance: type: aws:ec2:Instance properties: ami: ${amiId} instanceType: ${instanceType} subnetId: ${mySubnet.id} securityGroups: ["${mySecurityGroup.id}"] availabilityZone: ${aws:region}a keyName: ${keyName} userData: | #!/bin/bash dnf install -y podman python3-pip su ec2-user << EOF podman pull ghcr.io/ansible-community/community-ee-base:latest python3 -m pip install ansible-navigator --user echo 'export PATH=$HOME/.local/bin:$PATH' >> ~/.profile EOF tags: Name: "my-instance" outputs: vpcId: ${myVpc.id} subnetId: ${mySubnet.id} internetGatewayId: ${myInternetGateway.id} routeTableId: ${myRouteTable.id} routeTableAssociationId: ${myRouteTableAssociation.id} routeID: ${myRoute.id} securityGroupId: ${mySecurityGroup.id} instanceId: ${myInstance.id} instancePublicIp: ${myInstance.publicIp}
- ポイントは以下の通り
- AMI IDはRHEL9を指定する
-
aws:ec2:Instanceの
userData
の箇所に、インスタンスの構築後に実行したいスクリプトを記述する- Ansible Navigatorのインストール方法は、Ansible Navigator Documentationを参照
- Ansible実行環境イメージは、ghcr.io/ansible-community/community-ee-baseを使用する
- スクリプトは
root
ユーザーで実行される。そのため、特定のユーザー(今回はec2-user
)での
処理をしたい場合は、su
コマンドでユーザーを切り替える必要がある
3. Pulumiによるリソースの作成
-
IAMユーザーのアクセスキーを登録する
$ export AWS_ACCESS_KEY_ID="<YOUR_ACCESS_KEY_ID>" $ export AWS_SECRET_ACCESS_KEY="<YOUR_SECRET_ACCESS_KEY>"
-
リソースを作成する
$ pulumi up
-
リソースが作成されていることを確認する(以下はログの一部)
Type Name Status + pulumi:pulumi:Stack quickstart-dev created (47s) + ├─ aws:ec2:Vpc myVpc created (1s) + ├─ aws:ec2:SecurityGroup mySecurityGroup created (3s) + ├─ aws:ec2:InternetGateway myInternetGateway created (0.78s) + ├─ aws:ec2:Subnet mySubnet created (11s) + ├─ aws:ec2:RouteTable myRouteTable created (1s) + ├─ aws:ec2:Route myRoute created (0.73s) + ├─ aws:ec2:RouteTableAssociation myRouteTableAssociation created (0.91s) + └─ aws:ec2:Instance myInstance created (32s)
4. Ansible Navigatorの実行確認
-
構築されたEC2インスタンスにログインする
- user:ec2-user(ユーザー名はAMI IDによって異なります)
-
Ansible実行環境イメージが存在することを確認する
$ podman images REPOSITORY TAG IMAGE ID CREATED SIZE ghcr.io/ansible-community/community-ee-base latest 71b6d35cd089 2 days ago 347 MB
-
テスト用のPlaybookを作成する
$ vi playbook.yml
--- - name: Sample Play hosts: localhost gather_facts: false tasks: - name: Hello World! ansible.builtin.debug: msg: "Hello World!"
-
Playbookを実行する
$ ansible-navigator run playbook.yml --eei ghcr.io/ansible-community/community-ee-base --pp never -m stdout
PLAY [Sample Play] ************************************************************* TASK [Hello World!] ************************************************************ ok: [localhost] => { "msg": "Hello World!" } PLAY RECAP ********************************************************************* localhost : ok=1 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
さいごに
- AWSリソースの定義ファイル(
Pulumi.yaml
)で、EC2インスタンス構築後に実行するスクリプトを書けるのは便利だと感じます - AWSリソースの定義ファイル(
Pulumi.yaml
)は複数のEC2インスタンスを構築することも可能なので、
Ansibleの対象機器も構築できれば開発の更なる効率化が見込めるのではないかと思います
参考URL
-
ghcr.io/ansible-community/community-ee-base
- 今回使用したAnsible実行環境イメージ
-
aws:ec2:Instance
- Pulumiにおける
aws:ec2:Instance
の使用方法
- Pulumiにおける
-
Ansible Navigator Documentation
- Ansible Navigatorのインストール方法
関連記事
- 【Pulumi】Pulumi AIが生成したコードでEC2インスタンスを構築したい~第1章:YAML編~
- 【Ansible】Amazon EC2でansible-navigatorを使いたい~第2章:ansible-navigatorの実行~