書いたこと
- Amazon ECSを用いてRuby on Railsを動かす構成の紹介
- そこで出た課題と解決手法の紹介
ECSを用いてRuby on Railsを動かす構成の紹介
- Amazon ECSとは
- Amazon Elastic Container Service
- コンテナオーケストレーションサービス
- Amazon Elastic Container Service
- Dockerコンテナ化されたアプリケーションをECSで定義してデプロイ・スケールができる
ECSでの定義例
大きく分けて以下3つの定義をECS上で定義すれば環境が構築できる
1. クラスタの定義
- グループの定義
- 「本番環境」など
2. サービスの定義
- クラスタ内で公開したいサービスの定義
- Railsで動いている〇〇サービスなど
3. タスクの定義
- サービスを実行するためのDockerコンテナと、コンテナを動かすための条件等の定義
- Nginx + Railsで動かすためにそれぞれのDockerコンテナを用意と指定
- それぞれの仮装CPUと仮想メモリの指定
- 必要な環境変数の設定
- 起動のためのコマンドの指定
インフラ構成
クラスタ・サービスを指定してデプロイする
$ ecs deploy [クラスタ] [サービス] ...
そうすると、ECSのエージェントがタスク定義に従ってDockerコンテナをデプロイしていく
運用開始、そして・・
- スキーマ変更、その他Rake Task
bundle exec rails db:migrate
- などなど、Webアクセス経由とは別の重い処理もRailsのdocker内で行った
- 定期実行
- 本当に実行されたのだろうか
=>コマンドによってCPU・メモリ負荷上昇・最悪の場合アクセス不能に
=> 定期実行の監視の不確実さ
タスク実行専用のサービスを作ろう
クラスタの定義例
- 新しいサービスを定義した
- Webからのアクセスがないサービスなので、Railsのコンテナのみ定義
インフラ構成
$ ecs deploy [クラスタ] [サービス] ...
$ ecs run [クラスタ] [サービス] -c [コマンド]
サービスのデプロイと、コマンドの実行
コマンド実行後はサービスは終了する
定期実行を行う
- タスクスケジューラーが定義できる
- どのサービスを・どれくらいの頻度で、もしくはどのような時に・何を実行するかを指定
- 実行時にサービスがデプロイされ、コマンドを実行する
- コマンド実行後はサービスは終了する
- 実行ログやトリガーの結果はCloudWatchで確認
どうなったか
- サービスがWebと別に切り出されたので、重いコマンドを実行してもクラスタ内の別の仮装環境の中で実行されるようになった
- Web側がコマンドに起因してアクセス不能になることはなくなった
- 定期実行の監視が容易になった
- CloudWatchイベントの通知を利用し、監視できるようになった
- Webから独立したCloudWatchログを確認できるようになった