##目標
AWS SDK(AWS SDK for Ruby)を利用してEC2自動構築を行う。
##はじめに
AWS SDKの基礎知識をまとめた後、実際の動作をAWS SDK for Rubyを利用したEC2自動構築で試してみます。
##AWS SDK
AWSが提供しているAPIの一種で、AWSがサポートする様々なプログラミング言語にライブラリとしてインポートして利用します。
現在以下の言語がサポートされており、各種プログラムからのAWSリソース操作を可能にします。
・C++
・Go
・Java
・JavaScript
・.NET
・Node.js
・PHP
・Python
・Ruby(本記事ではこれを利用)
##AWS CLI、SDK利用時の認証
AWS CLI(OSコマンドライン上やシェルスクリプト、PowerShell上で利用)、AWS SDK(各種プログラミング言語上で利用)を利用する際には認証情報が必要となります。
認証情報の設定方法には以下3つの方法が存在しており、参照優先度が異なります。
項番 | 優先度 | 認証情報の設定箇所 |
---|---|---|
1 | 高 | OS環境変数 |
2 | 中 | 認証情報ファイル |
3 | 低 | インスタンスプロファイル(IAMロール認証) |
①OS環境変数
環境変数のAWS_ACCESS_KEY_ID および AWS_SECRET_ACCESS_KEYという環境変数を利用して認証情報の設定が可能です。
認証設定方法の中で最も優先度が高いです。
例えば以下のように設定を行います。
# For LINUX
export AWS_ACCESS_KEY_ID=your_access_key_id
export AWS_SECRET_ACCESS_KEY=your_secret_access_key
# For Windows
set AWS_ACCESS_KEY_ID=your_access_key_id
set AWS_SECRET_ACCESS_KEY=your_secret_access_key
②認証情報ファイル
OSユーザのホームディレクトリ内の「aws」ディレクトリに存在する「credentials」というファイルが認証情報ファイルです。
そのファイル内のaws_access_key_idとaws_secret_access_keyにアクセスキーとシークレットアクセスキーを投入します。
# 認証情報ファイル
~/.aws/credentials
[default]
aws_access_key_id = your_access_key_id
aws_secret_access_key = your_secret_access_key
③インスタンスプロファイル
インスタンスプロファイルとは、IAMロールを利用した認証で利用される実行環境ことです。
IAMロール作成時に自動作成されます。
IAMロールを納めるための容器であり、EC2にアタッチする時に必要なコネクターの役割をするようです。
IAMロールを利用するこの認証方法はAWS SDK及びAWS CLI利用時のベストプラクティスであり、アクセスキーとシークレットアクセスキーを利用する上記2つの方法より認証情報漏洩のリスクが軽減されるため推奨されております。
ちなみに、認証方法としての優先度が最も低いため、環境変数や認証情報ファイル内の情報に注意を払う必要があります。
インスタンスプロファイルの詳細に関しては、以下サイトが参考になりました。
EC2にIAMRole情報を渡すインスタンスプロファイルを知っていますか?
##作業の流れ
項番 | タイトル |
---|---|
1 | AWS SDK for Rubyのセットアップ |
2 | EC2自動構築用スクリプトのセットアップ |
3 | 動作検証 |
##手順
###1.AWS SDK for Rubyのセットアップ
①AWS SDK for Rubyインストール
かなり時間かかるので注意…
gem install aws-sdk
②アクセスキーとシークレットアクセスキーの発行
アクセスキーとシークレットアクセスキーが未発行の場合は新規作成する必要があります。
手順は以下を参考
【AWS CLI】Red Hat Enterprise Linux 8でAWS CLIを使用可能にする(3. アクセスキーIDとシークレットアクセスキーの発行)
③認証情報ファイルの編集
今回はAWS SDKの認証情報を認証情報ファイル内に設定する形で保存します。
認証情報ファイル~/.aws/credentials
内のaws_access_key_id
とaws_secret_access_key
にアクセスキーとシークレットアクセスキーを記載してください。
# 認証情報ファイル編集
vi ~/.aws/credentials
[default]
aws_access_key_id = your_access_key_id
aws_secret_access_key = your_secret_access_key
###2.EC2自動構築用スクリプトのセットアップ
①EC2自動構築用スクリプトをAWS SDKをセットアップした環境に配備
スクリプト内の各種環境依存の変数(<ami_id>
、<keypair_name>
、<security_group_id>
、<instance_type>
、<az_name>
、<subnet_id>
、<userdata_pass>
)は環境に従って書き換えをします。
また、<userdata_pass>
に指定したファイルの中にはEC2に設定したいユーザデータ処理を書いておきます。
ファイル名: ec2_create.rb
# **********************************************************************************
# 機能概要: EC2の自動構築
# スクリプト用法: ruby <スクリプトパス> <インスタンス名>
# **********************************************************************************
unless ARGV.size() == 1
puts "The number of arguments is incorrect."
exit
end
require 'aws-sdk'
require 'base64'
# EC2の構成要素定義(以下変数を環境に応じて編集)
image_id = '<ami_id>' # AMIID
key_name = '<keypair_name>' # キーペア名
security_group_ids = '<security_group_id>' # セキュリティグループID
instance_type = '<instance_type>' # インスタンスタイプ
availability_zone = '<az_name>' # 利用AZ
subnet_id = '<subnet_id>' # 利用サブネットID
user_data = '<userdata_pass>' # ユーザデータのファイルパス
# ユーザデータ設定
if File.exist?(user_data)
file = File.open(user_data)
script = file.read
file.close
else
script = ''
end
encoded_script = Base64.encode64(script)
# EC2リソース操作用インスタンス作成
ec2 = Aws::EC2::Resource.new
# EC2作成実施
instance = ec2.create_instances({
image_id: image_id,
min_count: 1,
max_count: 1,
key_name: key_name,
security_group_ids: [security_group_ids],
user_data: encoded_script,
instance_type: instance_type,
placement: {
availability_zone: availability_zone
},
subnet_id: subnet_id
})
# インスタンスが利用可能になるまで待機
ec2.client.wait_until(:instance_running, {instance_ids: [instance[0].id]})
# インスタンス名(Nameタグ)を付与
instance_name = ARGV[0]
instance.batch_create_tags({ tags: [{ key: 'Name', value: instance_name }]})
puts "#{instance_name}(#{instance[0].id})が作成されました!"
###3.動作検証
<前提>
以下のパラメータでEC2を作成します。
# EC2の構成要素定義(以下変数を環境に応じて編集)
image_id = 'ami-067152a7c26866dcb' # AMIID
key_name = 'mykeypair' # キーペア名
security_group_ids = 'sg-64a59718' # セキュリティグループID
instance_type = 't2.medium' # インスタンスタイプ
availability_zone = 'ap-northeast-1a' # 利用AZ
subnet_id = 'subnet-41d23b09' # 利用サブネットID
user_data = '/tmp/userdata' # ユーザデータのファイルパス
また、EC2に設定予定のユーザデータは以下の内容
$ cat /tmp/userdata
#!/bin/bash
yum update -y
yum install -y httpd
systemctl start httpd
systemctl enable httpd
①スクリプト実行
インスタンス名を第一引数に指定してスクリプト実行します。
$ ruby ec2_create.rb test_server
test_server(i-0a4fd9cfe1613a8d6)が作成されました!
②結果確認
インスタンス名、インスタンスタイプ、サブネットID、キーペア名、AZ名、AMIIDがスクリプト内での設定値通り設定されています。
一応OSログイン確認と、ユーザデータが正常に実行されているかも確認してみます。
# httpdがユーザデータ実行により起動している
$ systemctl status httpd
● httpd.service - The Apache HTTP Server
Loaded: loaded (/usr/lib/systemd/system/httpd.service; enabled; vendor preset: disabled)
Active: active (running) since Sat 2020-07-11 03:03:01 UTC; 12min ago
Docs: man:httpd.service(8)
Main PID: 21821 (httpd)
Status: "Total requests: 0; Idle/Busy workers 100/0;Requests/sec: 0; Bytes served/sec: 0 B/sec"
CGroup: /system.slice/httpd.service
tq21821 /usr/sbin/httpd -DFOREGROUND
tq21831 /usr/sbin/httpd -DFOREGROUND
tq21832 /usr/sbin/httpd -DFOREGROUND
tq21833 /usr/sbin/httpd -DFOREGROUND
tq21834 /usr/sbin/httpd -DFOREGROUND
mq21835 /usr/sbin/httpd -DFOREGROUND
Jul 11 03:03:01 ip-172-31-40-241.ap-northeast-1.compute.internal systemd[1]: Starting The Apache HTTP Server...
Jul 11 03:03:01 ip-172-31-40-241.ap-northeast-1.compute.internal systemd[1]: Started The Apache HTTP Server.
# また、enabledにもなっている
$ systemctl is-enabled httpd
enabled
全て設定値通りに作成されているのでOKとします!
##参考サイト
各種サービスにおけるAWS SDK For Rubyを利用した実装例が確認できます。
AWS SDK for Ruby コード例