EC2でinstance storeなインスタンスからEBSなインスタンスを作る

EC2 で Root Device が instance store なインスタンスから、Root Device が EBS なインスタンスを作る作業を行いました。

この手の情報はネット上に溢れていますが、私の環境だと書かれていない問題が色々と発生したので、備忘録的な意味も込めて書いておこうかと。

作業の背景としては、こんな感じ。

instance store で運用していたシステムの負荷が高くなってきたので、よりハイスペックなインスタンスタイプに変更したい。
が、インスタンスタイプの変更はインスタンを停止しないと無理。
instance store の場合システムが停止した時点でデータが消失するのでインスタンスを停止できない。
EBS ならインスタンスタイプの変更が可能。
instance store から EBS に変更すればいいんじゃないの?

なので、EBS にすると同時にインスタンスタイプを m1.small から m1.medium に変更しました。

ちなみに、Fedora 8 32bit のインスタンスです。

では、一応ひと通り instance store から EBS インスタンスを作成する手順をザックっと書きます。

ちなみに、以下の手順は AMI ToolsAPI Tools がインストールされていることを前提に書いてます。
まぁ、API Tools の方は入って無ければ EC2 のコンソールを使えば良いだけだけど、入れとくと便利なので、入って無ければこの機会にセットアップしておくと良いと思います。

あと、証明書のパスを $EC2_CERT に、プライベートキーのパスを $EC2_PRIVATE_KEY に登録してある状態で書いてあるので、その辺りも適当に読み替えて下さい。


# 元の instance store インスタンスからイメージを作成
cd /tmp
ec2-bundle-vol -d /tmp -u 720720518663 -c $EC2_CERT -k $EC2_PRIVATE_KEY
ec2-unbundle -m /tmp/image.manifest.xml -s /tmp/ -d /tmp/ -k $EC2_PRIVATE_KEY
 
# 次に、EBSボリュームを作成。
ec2-create-volume --size 10 --availability-zone ap-northeast-1a

availability-zone には、元となるインスタンスと同じ物を指定します。

この例では 10GB で作成してますが、それは元にした instance store のインスタンスの Root Device のサイズが 10GB だったからです。

新しいインスタンスの領域を拡張したい場合、この段階で拡張しても良いのですが、この段階で下手に拡張してしまうと後から自由が効かなくなってしまうので、最終的にインスタンスを作成するときに拡張したほうが良いと思います。

# 作成したEBSボリュームをアタッチ
ec2-attach-volume [VolumeID] --instance [InstanceID] -d /dev/sdf1
 
# データをコピー
dd if=/mnt/tmp/image of=/dev/sdf1

サイズによりますけど、それなりに時間がかかるので終わるまで待ちます。

コーピーが終わったら、EBSボリュームのスナップショット作成します。

ec2-create-snapshot [VolumeID]

ここでは、先ほど作成した EBSボリュームの ID を指定します。

コマンド自体はすぐに終了しますが、スナップショットが取れるまでそれなりに時間がかかるので、完了するまで待ちます。

スナップショットのステータスは管理コンソールで確認できますが、以下のコマンドでも確認できます。

ec2-describe-snapshots [Snapshot ID]
 
# こういう時は watch を使うと便利。
watch --interval=60 ec2-describe-snapshots [Snapshot ID]

で、AMI を登録します。

ec2-register -n [AMI Name] -s [Snapshot ID]

一応、ここではこう書いておきますが、この手順からは別な手順のほうが変えた方が良かったりします。
最後まで読んでみて下さい。・・・

ここまで来たら、後はインスタンスを立ち上げるだけ・・・

ってのがよく書いてある手順です。

確かに、これだけでも EBS インスタンスは作成できます。


で、何が問題なのかというと、この手順で作成すると、元のなった instance store インスタンスと、新しく作成した EBS インスタンスのカーネルのバージョンが変わってしまうんですよ・・・

普通に WEBサーバーとしては動作していたので、最初は気が付きませんでした。

が、インスタンスを m1.medium に変更して作業をしていた時に、サービスの起動の途中で良く分からないエラーが出ていたり、modprobe を実行すると lib が見つからない的なエラーが出たり、yum でパッケージをインストールしようとした時に、なぜか 64bit のパッケージが候補に出てきたりして、異変に気が付きました。

# modprobe -l
FATAL: Could not load /lib/modules/2.6.16.33-xenU/modules.dep: No such file or directory

こんな感じで、変なエラーが出ます。
で、uname -a を見てみると、思いっきり 64bit のカーネルバージョンが返ってきてる。。。

# uname -a
Linux ip-xxx-xxx-xxx-xxx 2.6.16.33-xenU #2 SMP Wed Aug 15 17:27:36 SAST 2007 x86_64 x86_64 x86_64 GNU/Linux

WEB サーバーとしては問題なく動いてますけど、かなり怪しいです。

気持ちが悪いし、後々問題になると嫌なのでバージョンは合わせて置いたほうが良いと思い、以下の様な対策を取りました。


既に AMI イメージを作っている場合はインスタンスを起動する時点で、元のインスタンスと同じ Kernel ID と Ramdisk ID を指定して起動します。

こうやって起動することで、元と全く同じ環境で起動します。

なので、AMI を作成する際に Kernel ID と Ramdisk ID を指定して作成すると良いと思います。

ec2-register -n [AMI Name] -s [Snapshot ID] --kernel [Kernel ID] --ramdisk [Ramdisk ID]

このようにして作成すると、インスタンスを立ち上げる際に一々指定しなくても大丈夫みたいです。

一つの AMI から複数のインスタンスを作成する場合なんかは AMI を作成する際に指定しておいた方が断然楽だと思います。


って事で、EBS にしてみましたけど、やっぱ EBS の方がメンテナンスを考えると楽ですね。

簡単にインスタンスを複製できるし、インスタンスタイプの変更も楽です。