WordPress移行メモ – ECS+EFS+CloudFront

これまでOpsWorksベースの環境でWordPressを運用していたんですが、re:inventで発表されたFargateに移行したくなり大晦日にECS周りを触っていました。将来的にはECS(Fargate)+EFS+Aurora Serverlessみたいな構成にしたいと考えてますが、Fargateはまだ少し早かったようです。今回はその前段階としてECS+EFS+RDSの構成になりました。

Fargate + WordPressは可能か?

結論から言うと、FargateはEFSと連携する手段が今のところなさそうな感じでした。

You are right that currently, there is no option to mount EFS volumes on Fargate. This is because Fargate launches stateless containers which means they do not store persistent data.

Fargate/EFS

WordPressはどうしてもプラグインのインストール・アンインストール等でファイルシステムを使うので、まずはFargateではない通常のECS+EFSで環境を作ることにしました。FargateのEFS対応もニーズは多そうなので対応したら移したいですね。

ECS + EFS

ECSとEFSの連携ですがどのように連携するのかと言うと、ECSのクラスタインスタンスでEFS(NFS)をマウントし、Volumeとしてコンテナにアタッチするという形になります。やってる事はNFSなのであまり難しくはありません。

今回はEFS連携済みのAMIを作りそれをECSクラスタインスタンスにする事にしました。ECS最適のAMI(ami-fad25980)からUserDataに下記のようなシバンを指定しEC2インスタンスを生成します。

#!/bin/bash
sudo yum install -y nfs-utils
mkdir /efs
echo 'xxxxxx.efs.us-east-1.amazonaws.com:/ /efs nfs4 nfsvers=4.1,rsize=1048576,wsize=1048576,hard,timeo=600,retrans=2 0 0' | sudo tee -a /etc/fstab

起動しsudo mount /efsなどして連携出来てる事を確認できたらAMIを作成します。

ECSクラスタインスタンスの起動

ECS-CLIを使ってdocker-composeベースで環境を構築します。今までECSは敬遠してきたのですが、docker-composeベースで構築ができると知ると途端に親近感が湧いてくるので不思議です。学習コストは低くなるので良いかもしれません。

まず最初にCLIに作成するクラスタの環境設定を行います。

$ ecs-cli configure --region us-east-1 --cluster general

WordPress以外でもsandbox的に使いそうなのでgeneralという汎用的な名前にしました。次に下記のようなコマンドでECSクラスタインスタンスを起動します。

$ ecs-cli up --keypair xxx --image-id ami-xxxx --capability-iam --size 1 --instance-type t2.micro --security-group sg-xxxx,sg-xxxx,sg-xxxx --vpc vpc-xxxxx --subnets subnet-xxxxx,subnet-xxxxx

注意点としてECSクラスタインスタンスのセキュリティグループがSSHできるか?HTTPできるか?RDSと連携できるか?EFSと連携できるか?等はチェックしながら上記のコマンドを実行すると良いと思います。コマンドの時点で抜けがあっても後からManagement Console上で補正すれば問題ありません。

タスク登録(コンテナ起動)

上記でコンテナを起動するためのインスタンスが用意できたので次にその上にコンテナを起動します。ECSの場合コンテナの起動方法に通常のタスクとサービスがあるようですが、今回は常駐のプロセスになるのでサービスとして起動します。

タスクの場合は下記のようにします。

# コンテナ起動
$ ecs-cli compose -f docker-compose.yml up
# コンテナ停止
$ ecs-cli compose -f docker-compose.yml down

サービスの場合は下記のようにします。

# コンテナ起動
$ ecs-cli compose -f docker-compose.yml service up
# コンテナ停止
$ ecs-cli compose -f docker-compose.yml service rm

今回は下記のようなWordPressのみのdocker-composeとなりました。

wordpress:
  image: wordpress:latest
  # t2.microの場合設定している人が多い模様
  mem_limit: 268435456
  ports:
    - "80:80"
  environment:
    WORDPRESS_DB_HOST: xxxx.xxxx.us-east-1.rds.amazonaws.com
    WORDPRESS_DB_NAME: wordpress
    WORDPRESS_DB_USER: xxxx
    WORDPRESS_DB_PASSWORD: xxxx
  volumes:
      # ホスト:コンテナ
      - /efs/wordpress/wp-content:/var/www/html/wp-content

コンテナ起動後、下記のコマンドで起動確認ができます。

$ ecs-cli ps

コマンドの出力結果にIPアドレスがありますが、そのIPアドレスをブラウザで開くとWordPressのインストール画面になっていると思います。

CloudFrontの設定

以前は使ってなかったのですが今回はCloudFrontも設定しました。ただ少し疲れてたのかけっこうハマりました。下記ハマったところのメモです。

  • CloudFront設定のCNAMEsに自分のドメインの設定がないとRoute53のAレコードのAliasで表示されない
  • POST等も明示的に許容する必要がある
  • クッキーの転送をAllにしないとWordPressが動作しない
  • SSL化に関して、WordPress HTTPSがうまく動かないためReally Simple HTTPSに変えたところうまく動いた