Amazon EBSのボリュームを自動でattachしてマウントしたい

 

EC2でインスタンスを起動すると、Instance IDが割り振られる。Amazon EBS(Elastic Block Store)のボリュームをインスタンスにattachすると、このInstance IDとボリュームが紐付くことになる。fstabにマウント情報を書いておけば、インスタンスを再起動してもこの紐付きは維持され、再起動後も普通にマウントされる。

だが、Instance IDはインスタンスをshutdownすると変わってしまい、都度ボリュームをattachし直さないといけない。これはウザい。耐えられない。

おなじことを考えている(?)人がいた。

Possible to Auto-Attach/Mount EBS at Boot?
http://developer.amazonwebservices.com/connect/thread.jspa?messageID=103331&#103331

そして、EBSのボリュームを自動でattach/detachして、マウントするためのスクリプトをPythonで書いた勇者がいた。

Scripts to automatically attach and mount an EBS Volume at Boot Time
http://developer.amazonwebservices.com/connect/thread.jspa?messageID=99100

早速試してみたときのメモ。

■インスタンスを起動して、EBSをattach

AWS Management ConsoleとかでEBSのボリュームを作成しておく。今回、デバイス名はsdfとした。
今回は、Oracleが提供しているAMIを使って、インスタンスを起動した。AMI IDはami-cecb2fa7のやつを使った。
以下を参考に、EBSをattach。

Amazon EBSを活用してデータをバックアップしてみよう ~Amazon EC2/S3環境構築のすべて~
http://codezine.jp/article/detail/3546

EBSボリュームが認識されているか確認。


$ cd /dev
$ ls sd*
sda1 sda2 sda3 sdf

ファイルシステムつくる。


mkfs -t ext3 /dev/sdf

マウントポイントを作っておく。今回は/opt/oracleとする。


mkdir /opt/oracle

マウントする。


mount /dev/sdf /opt/oracle

fstabにエントリを追記しておく。


echo "/dev/sdf /opt/oracle ext3 noatime 0 0" /etc/fstab

あと、今回使ったAMIでは、デフォルトではsda2がマウントされていなかったので、上記と同じような要領で、/volにマウントしておいた。後述のec2-bundle-vol実行用。

■ec2-api-toolsを使えるようにしておく

EC2のインスタンス上で、ec2-api-toolsを使えるようにしておくこと。
以下、やったこと。

・ネットから落としたJRE解凍して、/usr/localに配置した。Oracle付属のJREあったけど、なんとなく気持ち悪いので。
・ec2-api-tools.zipをダウンロードして、サーバにアップ。unzipして、/usr/localに配置した。
・/rootに、証明書ファイル(cert-なんたら)と秘密鍵ファイル(pk-なんたら)を配置した。
・後は適当に、環境変数の設定とか。JAVA_HOME、EC2_HOME、EC2_PRIVATE_KEY、EC2_CERT、PATHとか。

■スクリプトの準備

スクリプトをダウンロード。wgetできなかったので、クライアント側に一旦取得して、インスタンス側にアップロードした。
http://developer.amazonwebservices.com/connect/servlet/JiveServlet/download/30-24163-99100-1963/mount_ebs_volume.py
http://developer.amazonwebservices.com/connect/servlet/JiveServlet/download/30-24163-99100-1964/.ec2cred
http://developer.amazonwebservices.com/connect/servlet/JiveServlet/download/30-24163-99100-1965/aws_ebs_mount
http://developer.amazonwebservices.com/connect/servlet/JiveServlet/download/30-24163-114043-2210/mount_ebs_volume.patch

スクリプトにパッチを当てる。


$ patch < mount_ebs_volume.patch patching file mount_ebs_volume.py

mount_ebs_volume.pyの# setup environmentセクションを修正。
元々のos.putenv行をコメントアウトして、自分とこのインスタンスの環境に合わせて記述。


#os.putenv('PATH', '/root/ec2-api-tools/bin/:' + os.getenv('PATH'))
#os.putenv('EC2_HOME', '/root/ec2-api-tools/')
#os.putenv('JAVA_HOME', '/usr/lib/jvm/java-6-sun')
os.putenv('PATH', '/usr/local/ec2-api-tools-1.3-34128/bin/:' + os.getenv('PATH'))
os.putenv('EC2_HOME', '/usr/local/ec2-api-tools-1.3-34128/')
os.putenv('JAVA_HOME', '/usr/local/jre1.6.0_13')

.ec2credファイルは、Windowsのクライアントで取得すると先頭の「.(ドット)」が消えてしまうので、元の名前にリネームしておく。


$ mv ec2cred .ec2cred

.ec2credの内容を書き換える。


CERT=/root/cert-自分とこのcertファイルの文字列.pem
PRIVKEY=/root/pk-自分とこのpkファイルの文字列.pem
AWSACCOUNTID=自分とこのAWS Account ID(XXXX-XXXX-XXXX)

スクリプトに実行権限ふっとく。


$ chmod +x mount_ebs_volume.py

aws_ebs_mountを/etc/init.dにコピーして、実行権限ふる。


$ cp aws_ebs_mount /etc/init.d/
$ chmod +x /etc/init.d/aws_ebs_mount

自分とこの環境に合わせてaws_ebs_mountの中身を書き換える。


# Carry out specific functions when asked to by the system
case "$1" in
start)
echo "Mounting Elastic Block Store Volumes."
/root/mount_ebs_volume.py mount vol-xxxxxxxx /dev/sdf ext3 /opt/oracle ←ここ
;;

stop)
echo "Unmounting Elastic Block Store Volumes."
/root/mount_ebs_volume.py unmount vol-xxxxxxxx /dev/sdf ext3 /opt/oracle ←ここ
;;
esac

起動スクリプト作っておく。Oracleの起動スクリプトがS99dboraなので、98にしてみた。このあたり、ちゃんと動くか確認要。


例)
ln -s /etc/init.d/aws_ebs_mount S98aws_ebs_mount
ln -s /etc/init.d/aws_ebs_mount K98aws_ebs_mount

インスタンス落とす前に、AMIを作っておく

手順はいろんなところで説明されているので、詳細は割愛。
システムバックアップ取得。


ec2-bundle-vol -d /vol -k /root/pk-自分とこのpkファイルの文字列.pem -c /root/cert-自分とこのcertファイルの文字列.pem -u 自分とこのAWS Account ID(XXXX-XXXX-XXXX) --fstab /etc/fstab -r i386

後でわかりやすいようにimage.manifest.xmlをリネーム。


mv image.manifest.xml Enterprise-Linux-i686-oracle-11106-EE-200905020756.image.manifest.xml

S3にシステムバックアップイメージをアップロード。


ec2-upload-bundle --bucket cyberarchitect --manifest Enterprise-Linux-i686-oracle-11106-EE-200905020756.image.manifest.xml --access-key 自分とこのアクセスキー --secret-key 自分とこのシークレットキー

AMIを登録。これで、インスタンスをshutdownしても、ec2-bundle-volを実行したポイントからまた起動できる。


ec2-register cyberarchitect/Enterprise-Linux-i686-oracle-11106-EE-200905020756.image.manifest.xml

■動作確認

インスタンスをshutdown後、さっき登録したAMI(Enterprise-Linux-i686-oracle-11106-EE-200905020756.image.manifest.xml)を起動。

ちゃんと自動でattach、マウントされたみたい。


$ df -k
Filesystem 1K-blocks Used Available Use% Mounted on
/dev/sda1 10321208 6493564 3303356 67% /
none 870484 0 870484 0% /dev/shm
/dev/sda2 153899044 192072 145889348 1% /vol
/dev/sdf 10321208 154240 9642680 2% /opt/oracle