個人開発物のインフラを爆速で改善する(ECS,Fargate,Docker Compose)
1. はじめに
タイトルにもあるとおり、今回やったことは個人開発物のインフラ環境の改善です。対象としたのは約一年前に個人で作成した学習アプリ。当時の僕はアプリケーション周辺の経験しかありませんでした。そんな僕が苦し紛れに作ったインフラは、あまりにもお粗末であったため、今回インフラの勉強も兼ねて、やってみることにしました。
2. どんなアプリ ?
対象となるアプリケーションは、「Effectivest」という学習アプリです。技術スタックは以下の通り。
- フロントエンド : React / SPA
- サーバサイド : Node.js ・ Express ・ MySQL ・ Docker Compose
現在はインフラの移行も終え、こちらに公開済みです。
「単語を単語帳で暗記するのって効率悪いよなー」「個人でちゃんとしたWebサービスを作りたいなー」などの理由から頑張って作りましたが、悲しいことに自分も含め誰にも使われていません。ですが、それは逆にいえば、自分のいじりたい放題であるということ。サービスが停止したところで誰にも怒られません。ユーザーがいないことを前向きに捉え、インフラ環境を改善していきます。
3. 劇的! インフラ構成 ビフォーアフター
ということで一年前に作ったインフラ環境と今回作り直したインフラ環境をビフォーアフターで比較してみましょう。
ビフォー
アフター
なんということでしょう。GCEの仮想マシンだけであったインフラが、FargateやECS、Firebaseといったフルマネージドサービスを活用したなんともモダンな構成になっているではありませんか。
4. なんで移行したのか?
このようにアプリケーションの本番環境をGCPからFirebase・AWSに移行し、フロントエンド ・サーバサイド いずれもサーバレス・フルマネージドなサービスに移行したわけですが、ここで「なぜ移行したの?」という部分についてです。
先にも述べたとおり、ユーザー数はあってないようなものなので、「3章のBefore」であげたインフラのままでもスペック面では全く問題ありませんでした。
しかし、それでも、移行したい!と思った理由としては「デプロイフローを改善したかった」という切実な思いがあります。
改善前、CIの知識など全くなかった僕は、サーバが停止する都度、
- VMのインスタンスを立て直す。
- DockerとGithubをインストールする
- Github経由でコードをインスタンスに転送。
- Dockerを起動
- DBにデータを入れる
といった操作をコンソール上からいちいち行っており、デプロイだけで30分 ~ 1時間くらいかかっていました。
この一連の操作がコマンド一つでできた日には...こんな嬉しいことってないですよね?
ということで、これからの章では、
- これらの移行をしていく上で実際に行ったこと
- デプロイフローがどのように改善されたのか?
という点をフロントエンド ・サーバサイド のそれぞれについて紹介していきます。
5. フロントエンド 編
まずフロントエンド についてです。
フロントエンド は先にも述べた通り、React * create-react-appによるSPAです。そのためHTML/CSS/JSを静的にホスティングしてくれれば十分でした。
静的サイトホスティングのサービスであれば、netlifyやVercel,S3といった選択肢もありますが、今回はそのデプロイの容易さや使い慣れているといった理由からFirebase Hostを選定しました。
Firebase Hostのプロジェクトへの導入は公式の説明がわかりやすいので、ここでは割愛します。
導入 & 設定後、package.json内に以下のような記述を追加します。
"deploy":"react-scripts build && firebase deploy"
すると、
$ yarn deploy
と実行しただけでReactアプリのビルドとfirebaseへのデプロイできるようになります!スーパー便利!!!
6. サーバサイド 編
次にサーバサイド です。「ビフォー」ではGCPのVM上でコンテナを動作させていますが、これらを全てAWS上のECS・Fargate上に移行しました。
AWSとその他周辺のフルマネージドサービスを選定した理由は、
- EC2ではないコンテナ専用のAWSサービス使いたい。
- CI/CDの改善
- 今回はやらなかったけどIaaCとかの拡張も今後やりたいので、AWSの方がより充実していそうなイメージがあった。
- 勤務先との先の技術スタックに合わせる。
などが挙げられます。
なお今回は、昨年の11月に一般提供が開始された、「Docker Compose for Amazon ECS」を使用しました。これにより、「docker compose up 」を実行するだけでAWSのECS上にデプロイすることができます。便利だね。
導入手順
ECRへのpush
- Docker Composeファイルのイメージ名を ECRのリポジトリ名に変更する
image: {aws account id}.dkr.ecr.ap-northeast-1.amazonaws.com/effectivest/database:latest
- ECR への認証
$ aws ecr get-login-password --region ap-northeast-1 --profile {profile name} | docker login --username AWS --password-stdin {aws account id}.dkr.ecr.ap-northeast-1.amazonaws.com
- Dockerイメージのpush
$ docker-compose push
ECSへのデプロイ
- ECS用のDocker Context の作成
$ docker context create ecs {context名}
上のコマンドを実行するとAWSへの認証情報が求められます。
- Contextを使用
$ docker context use {context名}
- ECSへデプロイ
$ docker compose up
を実行すると、ECSにデプロイされます!
- デプロイしたコンテナの停止
$ docker compose down
を実行すれば、コンテナの停止も簡単です。
7. まとめ
今回、個人開発物のインフラをサーバサイド・フロントエンド、両方移行してみました。
個人開発物って自分の好きな技術を好きなように導入できるのが醍醐味ですよね。今回の移行だけでも、だいぶCIが改善された気がするのですが、
- Circle CIやCodeBuild等でコンテナがPushされたら自動でデプロイされるようにする。
- IaaCの導入
- セキュリティ等も考慮したインフラの改善
などにも今後取り組んで行こうかと思います。
8. 参考文献
Discussion