【小ネタ】EC2のインスタンスメタデータからリージョンを取得する

2015.11.19

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

EC2にはインスタンスメタデータという機能があり、そのインスタンスに関連する各種情報をEC2インスタンスからHTTPリクエストを投げることで取得することが可能です。

例えば、CUIからはcurlを利用して、http://169.254.169.254/latest/meta-data/にリクエストを投げると以下のようになります。

# どのような値が取得できるかを確認できる
$ curl -s http://169.254.169.254/latest/meta-data/
ami-id
ami-launch-index
ami-manifest-path
block-device-mapping/
hostname
iam/
instance-action
instance-id
instance-type
local-hostname
local-ipv4
mac
metrics/
network/
placement/
profile
public-hostname
public-ipv4
public-keys/
reservation-id
security-groups

$ # インスタンスIDを取得
$ curl -s http://169.254.169.254/latest/meta-data/instance-id
i-01234567

インスタンスIDなどはプログラムでEC2を操作する際に非常に有用です。

リージョンは取得できない?

さて、AWS CLIなどを利用してAWSのAPIを叩く時、必要になるのがリージョン指定です。例えば東京リージョン(ap-northeast-1)に対してAWS CLIを利用する時は、以下のどちらかの方法でリージョンを指定する必要があります。

$ # 何も設定せずにEC2からAWS CLIを実行すると以下のエラーが出る。
$ aws ec2 describe-instances

Unable to construct an endpoint for ec2 in region None

$ # パラメータで指定
$ aws ec2 describe-instances --region ap-northeast-1

$ # または、環境変数 AWS_DEFAULT_REGION で指定
$ export AWS_DEFAULT_REGION=ap-northeast-1
$ # 環境変数で指定した場合はパラメータ無しで実行可能
$ aws ec2 describe-instances

そのため、EC2に配置するシェルスクリプトにリージョンをハードコードされている方も多いかと思います。ですがそれはあまり好ましくありません。例えばAMIをコピーして他のリージョンで起動することになった時、リージョン名をいちいち書き換えるのはイケてないですよね。なので動的に、「そのインスタンスが起動しているリージョン」を指定するのが望ましいです。

ですが、インスタンスメタデータを探してみてもリージョンは存在しません。なので稼働リージョンをインスタンスメタデータから直接取得することはできないようです。

解決方法

リージョンは取得できませんが、インスタンスが稼働しているアベイラビリティゾーンなら取得することができます。そのURLはhttp://169.254.169.254/latest/meta-data/placement/availability-zoneです。

$ # アベイラビリティゾーン取得
$ curl -s http://169.254.169.254/latest/meta-data/placement/availability-zone
ap-northeast-1a

現在、アベイラビリティゾーンの名前は「リージョン名 + アルファベット1文字」になっています。ですので先ほどの結果から末尾一文字削ればOKです。シェルならsedを利用するのが簡単だと思います。

$ # リージョン取得
$ curl -s http://169.254.169.254/latest/meta-data/placement/availability-zone | sed -e 's/.$//'
ap-northeast-1

これを上述の通り、パラメータか環境変数で設定すれば処理可能になります。

$ region=$(curl -s http://169.254.169.254/latest/meta-data/placement/availability-zone | sed -e 's/.$//')

$ # パラメータで指定
$ aws ec2 describe-instances --region ${region}

$ # または、環境変数で指定
$ export AWS_DEFAULT_REGION=${region}
$ aws ec2 describe-instances

EC2のインスタンスメタデータ、活用すると便利ですのでぜひご活用下さい。なお、本ブログではLinuxを利用した例を紹介しましたがWindowsインスタンスでもインスタンスメタデータサービスは利用可能です。