別記事で書いたように、EC2上にSubversion+Redmineの環境を作りました。
この際、Security Group で接続元を制限しているのですが、自宅に固定IPはないので、当然IPアドレスが変わります。
そこで、Security Group のルールを動的に変更する処理を入れてみたいと思います。やり方は基本的にダイナミックDNSの設定で行った方法と同じです。
EC2 APIツールのインストール
まず、EC2のAPIを操作するために、APIツール(コマンドラインツール)を導入します。前提として、EC2 APIツールはJavaで書かれているので、JREが必要になりますので、まずJREをインストールします。
bitnami@ip-10-150-181-105:~$ sudo apt-get install default-jre
念のため、AWSのドキュメント(ツールのセットアップ)に従って、gpgでダウンロードしたファイルを検証しておきます。
次に、ec2-api-tool をインストールします。zipファイルを解凍後、
bitnami@ip-10-150-181-105:~$ unzip ec2-api-tools.zip bitnami@ip-10-150-181-105:~$ sudo mv ec2-api-tools-1.6.5.2/ /usr/local/bin/ bitnami@ip-10-150-181-105:~$ cd /usr/local/bin/ bitnami@ip-10-150-181-105:/usr/local/bin$ sudo chmod -R root:root ec2-api-tools-1.6.5.2/ bitnami@ip-10-150-181-105:/usr/local/bin$ sudo ln -s ec2-api-tools-1.6.5.2 ec2-api-tools
として、/usr/local/binに入れておきます。
次に、ドキュメントに従って、いくつか環境変数を設定します。
環境変数にはAWSアカウントのX.509証明書も指定します。これは、AWSのサイトから『アカウント/コンソール』→『セキュリティ証明書』と選択し、『アクセス証明書』の『X.509証明書』のタブを選び、『新しい証明書を作成する』を選択し、X.509証明書を作成します。
証明書を作成したら、秘密鍵と、X.509証明書をダウンロードします。ダウンロードしたら、SFTPなどで、EC2のインスタンスにこれら2ファイルをアップロードします。
環境変数設定は、/etc/ec2ディレクトリを作成し、ここに bash_ec2envという名前で保存しておきます。
# bash_ec2env # # some definitions for ec2 command line tools # # written by Junichi MORI, 2012/12/7 # java environment export JAVA_HOME=/usr # ec2 environment export EC2_HOME=/usr/local/bin/ec2-api-tools export PATH=$PATH:$EC2_HOME/bin # keys export EC2_PRIVATE_KEY=/etc/ec2/pk-xxxxxxxxxxxxxxxxxxxxxxxxxxxx.pem export EC2_CERT=/etc/ec2/cert-xxxxxxxxxxxxxxxxxxxxxxxxxxxx.pem # endpoint : Tokyo region export EC2_URL=https://ec2.ap-northeast-1.amazonaws.com
なお、エンドポイントは東京リージョンにしました。
ここまでできたら、コマンドラインツールが使えるか試してみます。
bitnami@ip-10-150-181-105:~$ . /etc/ec2/bash_ec2env bitnami@ip-10-150-181-105:~$ ec2ver 1.6.5.2 2012-10-01 bitnami@ip-10-150-181-105:~$
問題なくバージョンが表示できればOKです。
なお、コマンドラインツールを使いたいユーザーは、.bashrcから、
# EC2 definitions. # added by Junichi MORI, 2012/12/7 if [ -f /etc/ec2/bash_ec2env ]; then . /etc/ec2/bash_ec2env fi
のようにして、bash_ec2envを読み込めばOKです。
SecurityGroupを動的に変更
これで、Security Group のルールを変更するスクリプトの準備ができました。今回作成したスクリプトec2-sg-update.shは次のようなものです。
#!/bin/bash # # Security Group Rules auto update # https access allows to my office ip address defined by dynamic dns host name # # written by Junichi MORI, 2012/12/7 # variables EC2_ENV=/etc/ec2/bash_ec2env CurrentIPFile=/etc/ec2/current_ip TargetDomain=xxxxx.mori-soft.com SecurityGroupName=xxx HttpsPort=xxx # functions function getCurrentIP() { currentIP= if [ -f $CurrentIPFile ] then currentIP=`cat $CurrentIPFile` fi } function getNewIP() { newIP=`host $TargetDomain | awk '/has address/ {print $4}'` } function message() { echo `date +"%F %T %Z"` : $* } # environment setting if [ ! -f $EC2_ENV ] then message "error: ec2 environment difinition file is missing" exit -1 fi . $EC2_ENV # update SecurityGroup IP getCurrentIP getNewIP if [ "$currentIP" != "$newIP" ] then message "update current ip, $currentIP , to new ip, $newIP ." # write new ip # If there is a short interval in cron job, multi update processes exec # because this update process takes more time. # So prevent multi update processes, the guard condition sets. echo $newIP > $CurrentIPFile # check #message "check SecurityGroup before update" #ec2-describe-group --filter "group-name"=$SecurityGroupName # delete old one if [ "$currentIP" != "" ] then message "delete current ip rule" ec2-revoke $SecurityGroupName -P tcp -p $HttpsPort -s ${currentIP}/32 fi # add new one message "add new ip rule" ec2-authorize $SecurityGroupName -P tcp -p $HttpsPort -s ${newIP}/32 # check #message "check SecurityGroup after update" #ec2-describe-group --filter "group-name"=$SecurityGroupName fi # if ip address don't change, do nothing.
自分用のスクリプトなんで、もし、トラぶった場合は手動で直すことを前提にしているのでエラー処理は省いています。
/etc/ec2に現在割り当てられているIPアドレスを記載したファイルを作成し、IPアドレスをチェック後、もし変わっていれば自動的に変更を行います。変更は、一度、古いIPアドレスのルールを削除し、その後新しいIPアドレスのルールを追加する、という方法を取ります。
なお、IPアドレスをファイルへ書き出す処理を、一連の変更処理の最初に行っています。これは、Security Group の確認(checkとしてコメントアウトしている処理)を行う場合、時間がかかるケースがあり、cronの呼出し間隔によっては重複して変更処理が動くことがあったためです。
ここまでできれば、このスクリプトをcronで定期的に呼び出すようにします。たとえば、こんな感じにして、/etc/cron.dに入れておきます。
bitnami@ip-10-150-181-105:/etc/cron.d$ cat ec2_sg_update # PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin LOGDIR=/var/log # m h dom mon dow user command */1 * * * * root /etc/ec2/ec2-sg-update.sh >> $LOGDIR/ec2sg.log 2>&1 bitnami@ip-10-150-181-105:/etc/cron.d$
これで、タイムラグはあるものの、手作業でSecurity Group のIPアドレスを編集する手間が省けるようになりました。