コネヒト開発者ブログ

コネヒト開発者ブログ

AWS Fargateを本番運用した所感

こんにちは。インフラエンジニアの永井(shnagai)です。

今回は、Fargateを本番投入し1ヶ月強が過ぎたので、運用する中で気付いた点について書こうと思います。

以前書いた、Fargateに関する調査のまとめ記事はこちら。

tech.connehito.com

内容はざっくり下記3項目です。

  • いきなりFargateはハードルが高め
  • 良かった点
    • コンテナのリソースキャパシティを簡単に変更出来る
    • オートスケーリングもシンプルに組める
    • 安定運用
  • つらい点
    • タスクの起動速度がEC2バックエンドと比べるとやはり遅い
    • 料金面

いきなりFargateはハードルが高め

Fargate導入を通して一番感じたのは、新規にコンテナ化するアプリケーションをECSで動かす場合、EC2バックエンドで試験をパス出来る状態まで持っていった後に、最後にFargateで動かすパターンがよさそうということです。

今回のFargateの本番投入では、 EC2で動いているサービスをDockerコンテナ化して新たにFargateでリリースするというものでした。 他のサービスでも同じような作業をしていたので、 Dockerコンテナ化やアプリケーション改修については比較的スムーズに終わりました。

サービス公開前に試験用ECSをFargateで作り、コンテナをデプロイして試験を始めたのですが色々と困りごとが起こりました。 アプリケーションがうまく動かず下記のような会話が繰り広げられました。

  • 環境変数がうまく読み込めていないのでは?
  • NW通信がうまく出来ていないのでは?
  • ちょっと1コマンド叩いて検証したい。

docker exec でコンテナに入りデバッグ出来たらすぐに解決出来るような問題ばかりなのですが、Fargateはコンテナに入りデバッグが出来ないのがネックになりました。 初期の環境構築では、どうしても意図せぬ設定漏れ等が出てくることはあり、それを潰すための試験だったのですが、デバッグに時間がかかり非効率になってしまいました。

結局EC2バックエンドで試験環境を作り、試験をパスした状態でFargate用にタスク定義を作り直すというステップを踏むことにしました。

もちろん標準出力は、CloudWatchLogsにはかれるのである程度はデバッグ出来るのですが、NWの問題やOSレイヤのデバッグは少し厳しいなというのが正直な感想です。 本番運用後は、コンテナにログインするような事はないので特に問題ないのですが、開発フェーズではEC2バックエンドでdocker execでデバッグ出来る状態にしたほうが、効率よく作業出来ると思いました。

良かった点

ここからは、Fargateを導入してよかった点について書いていきます。

コンテナのリソースキャパシティを簡単に変更出来る

Fargateの最大のメリットだなと個人的に感じた点で、 これまで意識しなければならなかったクラスタを構成するEC2側のリソースキャパシティを考慮せずに、 タスク単位で自由に割当リソースの変更が可能となります。

※現状だと1コンテナあたり Memory:0.5〜30GB vCPU 0.25〜4の制限あり

下記図をみていただくとわかりやすいのですが、EC2バックエンドとFargateではコンテナに対するリソース割り当ての考え方が根本的に違います。

f:id:nagais:20181121150313j:plain

何が嬉しいかというと、負荷試験で決めたキャパシティが実際にサービスインしてみると不足していたり逆に少し過剰気味というようなケースやサービスが爆発的に成長してリソース増強が必要になるようなケースで、コンテナに割り当てるリソースの見直しを行うステップが劇的に簡単になります。

【EC2バックエンド時代】

  1. EC2バックエンドの実態である、AutoScallingGroup(ASG)でインスタンスタイプや台数を変更すると同時にECSサービス側で新しいASGでもコンテナが動くように起動数を調整
  2. ASGの変更内容を元に計算し、タスク定義にて1コンテナあたりに割り当てるリソース量を変更
  3. 新たなタスク定義でECSサービスを更新して反映

1のステップが特に面倒で、リソースを縮退する時には、コンテナがリソース不足で落ちてしまわないように注意を払う必要がありました。

これがFargateになると下記のように簡単なステップでリソースの変更が可能になります

【Fargate】

  1. タスク定義で、コンテナに割り当てるリソース量を変更
  2. 新たなタスク定義でECSサービス更新

クラスタ側のリソースは考えずに、コンテナに割り当てたいリソース量を変更するだけでOKとなります。

今後、Fargateに関してはリソース容量の増加や様々なアップデートがあるのではと予想していますが、タスク定義を変更するだけで柔軟に設定が変えられるのは大きなメリットだなと思いました。

オートスケーリングもシンプルに組める

オートスケーリングについても前述のEC2を意識しないキャパシティプランニングが可能なことと同じ理由で、 シンプルにコンテナあたりのCPU、MemoryもしくはELBでカウントするリクエスト数のしきい値ベースで設定が可能なので設定が簡単になります。

安定運用

1ヶ月強本番運用している中で、Fargate起因でサービスが落ちたことはないので基盤として安定しているのはとても安心出来ます。 ECSのオートヒーリングがあるので、仮に1コンテナ落ちたとしてもサービス影響は限定的ではあるのですが。

つらい点

今回一部のサービスをFargate化しましたが、全部を入れ替えるのはまだ先だなと感じたつらいポイントについても書こうと思います。

タスクの起動速度がEC2バックエンドと比べるとやはり遅い

Fargateにするとホストが固定されないため、Docker Pull時のレイヤキャッシュが効かなくなります。 それが理由でEC2バックエンド時代と比べるとECSサービス更新からコンテナが立ち上がるまでの時間が約1.5〜2分程遅くなりました。 その分デプロイ速度が遅くなってしまいます。

これはDockerイメージのサイズも大きく影響するので一概には言えないですが、アーキテクチャ上仕方ないとは思いつつ、AWSの今後の進化に期待したい部分だと思っています。 Cron的な起動時間が厳格に求められるスケジュールバッチのバックエンドには、FargateでなくEC2バックエンドを使うのが今のところは正解かなと個人的には思っています。

料金面

スポットインスタンスやリザーブドインスタンス(RI)を使って、EC2バックエンドでは大幅なコスト削減が可能です。 同じリソースを使った際のオンデマンド料金でも、Fargateの価格設定は少し割高かつRIのような料金プランもないので現状コスト比較をすると分が悪いです。

これは、来週開催されるre:invent かその後かはわからないですが、そのうちRDSのRIのように柔軟なリソース変更に自動適用する形でRIが発表されるのではと期待しています。

まとめ

先日、パラメータストアに置いた秘匿変数をタスク定義で環境変数に展開する機能がリリースされたり、 ECSでのDockerコンテナ運用は、Dockerイメージ+タスク定義で簡単に出来る世界が徐々に整備されつつあるなと感じる今日このごろでした。

dev.classmethod.jp

コネヒトではコンテナ周りの基盤を整備したりサービス改善を行うエンジニアを募集しています。 少しでも興味もたれた方は、是非気軽にオフィスに遊びにきていただけるとうれしいです。

www.wantedly.com

PSR-18: HTTP Clientが採択されたので読んで・考え・まとめてみる

こんにちは、サーバーサイドのお仕事してます金城(@o0h_)です。
先日、社内Slackで「面白い漫画、オススメ教えてください!」と投稿したら弊社デザイナー氏から推薦された「舞妓さんちのまかないさん」がとても良かったです。ほっこりして、「なんか・・仕事頑張ろう・・」という気持ちに。

舞妓さんちのまかないさん 1 (1) (少年サンデーコミックススペシャル)

そんな弊社デザイナ、12月に開催されるDesignshipに公募スピーカーとしてお話をするよ!!との事でコネヒトメンバー一同で応援をしております。

design-ship.jp

前回・前々回と私がこちらに書いた記事がPHPを離れていた事もあり、「そろそろPHPネタを」というエントリーです。
つい先日、新しいPSRが採択されて && そのタイトルが「自分が触れるものに関わってきそう!!」と興味を持ちました。思考の整理がてら情報のシェアしてみたいと思います。

PSR-18: HTTP Client についてです。

続きを読む

Papertrail + Amazon CloudWatchでアプリケーション監視の幅を広げる

こんにちは、サーバーサイドのお仕事してます金城(@o0h_)です。
今更ながら「映画大好きポンポさん」(の2巻)を読みました、めっちゃ良くないですか・・・

映画大好きポンポさん2 (MFC ジーンピクシブシリーズ)

映画大好きポンポさん2 (MFC ジーンピクシブシリーズ)

本日は、サービスの監視の話です。
コネヒトではエラートラッキングにSentryを用いていますが、CloudWatch Alarmによる定量的なエラー観測も併せて行っています。
「どう使い分けるの」「どうやって観測しているの」というお話をさせていただきます。

https://cdn.mamari.jp/authorized/amana_5bbb0ea4-8550-4449-ba79-002aac120002.jpg

続きを読む

チームに「効く」ダッシュボードを考える

Creating Effective Dashboards

こんにちは、サーバーサイドのお仕事してます金城(@o0h_)です。
つい先日、なんか気分が乗らないぜ〜〜って時にスピナーベイトを読み直してみたんですけど、気分の悪さが・・・上塗りされました・・・気をつけましょう。

スピナーベイト (1) (バーズコミックス)

さて、今回は抽象的な話になります。
「チームで毎日見るようなプロダクトの成長のためのダッシュボードってどういうのを作るんだっけ」という内容です。

https://cdn.mamari.jp/authorized/5b7ed6a6-dbc4-4548-a9f5-0017ac120002.jpg

続きを読む

ランサーズさんとランチLT大会を行いました

こんにちは。 Free! が終わってしまい夏の終わりを感じている @super_mannerです。2020年までは頑張って生きようと思いました。

さて、今回は先日開催されました、ランサーズさんとのランチLT大会についてお伝えできればと思います!

なぜ開催されたのか

コネヒトでは先日、コネヒトーク というイベントを開催いたしました。
ありがたいことにビジネスサイド、デベロッパーサイド共にたくさんのゲストの方にお越しいただき、楽しんでいただけるイベントとなりました。
そんなコネヒトークの懇親会で出会ったのがまなみんさんです。
同じサーバーサイドエンジニアということもあり、話が盛り上がり

「実はCakePHPを使っている会社の方とゆっくりお話できる機会って結構貴重なのかも?!」
「最近、コネヒトでも社内勉強会、社外勉強会を開催する事が増えてきたし、このあたりで一つ一緒に勉強会を実施するのもおもしろいのかも?!」

というその場の思いつきを口にしたところ、とても良い反応をいただきまして、あれよあれよと合同勉強会の開催決定しました🎉

折角共通の知識ですので、今回のLTテーマは「CakePHPに関すること」として実施することに決定。
また、ランサーズさんは時折ランチでゲストを招いて勉強会を行っているとのことでしたので、今回もその形式でお邪魔することになりました。

LT大会当日の様子

コネヒトでもこういった形式での勉強会は初めてなので、当日は発表者である弊社のサーバーサイドエンジニア陣はドキドキしながら伺ったのですが(私が一番ドキドキしていたのは秘密)、明るく迎え入れてくださりランサーズの皆さんの素敵なお人柄をうかがい知ることができました(^^) まずはランチを取りながら自己紹介等でアイスブレイクをした後に、いよいよLTのお時間です。

発表にのぞむ弊社エンジニアの金城
発表にのぞむ弊社エンジニアの金城

今回の勉強会は、コネヒトから3名、ランサーズさんから3名の合計6名のLTで執り行いました。 発表者以外にもたくさんのエンジニアの方にご参加いただくことができ、 質疑応答でも毎回何かしら手が挙がる等いい感じに盛り上がり、あっという間にお開きの時間を迎えてしまいました。
私個人といたしましても、扱っているバージョンが違うことや、アプリケーションを取り巻く環境の違いから、私も勉強になることが大変多く楽しませていただきました。
なお、コネヒト側が行ったLTの資料はこちらに上がっておりますので興味がある方は見てみてください! *1

最後に

今回開催するに当たり、お声がけをいただいたまなみんさんをはじめ、広報の宮田さんにも大変尽力いただきました! 重ねて、LTをしてくださった皆様も本当にありがとうございました 🙏 こうした取り組みも今後増やしていきたいと思いますので、今後共コネヒトをよろしくお願いいたします!

*1:対象の資料タイトルはそれぞれ、 「よいOSSを支える3C」「Bye Bye Magic Number」「雰囲気で使わないjoinメソッド」

社内のGoogle Apps Scriptを整理しはじめた

f:id:dachi023:20180921153427p:plain

こんにちは。エンジニアの安達 (@ry0_adachi) です。

先週くらいから社内に散らかった大量のGoogle Apps Script (以降GAS) の管理をすることにしたので1週間でやったこと、これからやっていきたいことを本記事でまとめます。

そもそも何で管理が大変なのか

GASって散らかってる感がすごいけど、なんでそう思うんだろうね?
を考えてみたのですが、だいたいこの3つが悪い気がしました。

  • コードの一覧性が低い、権限問題により全体像がつかめない
  • 同じようなコードが量産される (共通化されない)
  • トリガーがどのアカウントに紐付いているか分からない

誰でもカジュアルにコードを書けるし便利だけど、しっかり管理しないと気づいた頃には大変なことに...ということなんだと思います。

それぞれの問題に対してとった対策

コードの一覧性

f:id:dachi023:20180921130944p:plain

今まではGASのダッシュボードからしか見る術がなかったのですが今はGitHubにコードをPushするようにしました。最初はGoogle Apps Script GitHub アシスタントというChromeの拡張を使っていたのですが、今はclaspというツールでやっています。

claspの詳細な使い方については触れませんが、GASのコードをローカルでpullしたりpushできるようにするためのCLIツールです。claspでプロジェクトを作成して好きなエディタでコードを書いてpushして反映、といった感じでローカルで作業できる範囲が広がるのでだいぶ効率はよくなりました。

Command Line Interface using clasp  |  Apps Script  |  Google Developers

権限ない問題

権限ない問題は個別に招待や共有をするのではなく「XXXの全員が閲覧or編集可能」など組織ごとに権限を付与するようにお願いするしかない気がします、大変そうです。とはいえ社員全員から見えたらまずいもの (個人情報とかそういうの) とかもあるので全部キッチリやる必要はないかなと思います、この辺は完璧を目指さないほうがいいのかもしれません。

同じようなコードの量産

共通化するのにはGASの機能で公開APIとして社内向けに公開するか、ES Modulesを使って書いたコードをBabelとGAS用のプラグインで変換すれば良さそうです。この辺は特に難しいことを考えずにコードをキレイにするだけだったので重複するコードが大量にあった、ということ以外は特に大変ではなかったです。

公開API

f:id:dachi023:20180921160359p:plain

webpack, BrowserifyのPlugin

トリガーを設定したアカウントがわからない

GASに設定したトリガーは設定したアカウントでしか表示されないのでかなり厄介です。離職などによってアカウントを停止すると今まで実行されてた処理が止まってしまった、ということも前にありました。トリガーを紐付けておくために専用アカウントを作ってはみたのですがアカウント切り替えるのが面倒というのもあってあまり進捗は良くないです。いい方法があればブコメなどで教えてもらえると嬉しいです。

今後やりたいこと

  • 今閲覧できているコードを全部GitHubにpushする
  • 便利そうなものはAPI化して他の人も使えるようにしておく
  • 周りを巻き込んでいってこれをちゃんと標準のやり方にする

このあたりでしょうか。
結構泥臭い作業が多いし、GSuiteの権限との絡みで制御できないものもあり辛いことも多々あるんですが、GASを今より簡単に使えるようにしたら会社の中がもっと便利になりそうだなぁと思っているのでそれを糧にもうちょっと頑張ってみようと思ってます。

ECSのバックエンドをEC2からFargateに変更するにあたり知っておくとよさそうな事

こんにちは。インフラエンジニアの永井(shnagai)です。

これまでEC2バックエンドでECSを運用してきたが、Fargateを採用するにあたり、EC2バックエンド時と比べた差分についてまとめてみました。

内容は、ざっくり下記5項目について。

  • NW(awsvpc)
  • タスク定義
  • サービス
  • AutoScalling
  • メトリクス/ログ

Fargateをやってみたというのは出たての頃にやったので、今回は本番運用を考えるにあたり知っておいたほうがよさそうな点についてまとめてます。

tech.connehito.com

NW(awsvpc)

アーキテクチャ的に一番大きく変わるのは、NWの部分だと思う。 EC2上で、タスクを動かすときはデフォルトだと「bridge」が指定されるので、ホスト経由で外部と通信を行っていた。同一タスク(コンテナのリッスンポートが同じもの)を効率的にEC2上で動かすために、動的ポートマッピングを使うのが通例となっていた。

Fargateになると、EC2の存在は隠蔽されるが、当然VPC内にタスクを立てたかったり、セキュリティグループを指定したいのでそれを実現するために、awsvpcネットワークモードを使うことになる。 ちなみに、awsvpcはEC2バックエンドの時でも使えるので、Fargate用の機能ではない。

awsvpcネットワークモード

  • タスクネットワーキング機能により、Amazon EC2 インスタンスと同じネットワーキングプロパティが Amazon ECS タスクに提供される。
  • awsvpcの指定は、タスク定義で行う
  • タスクが、独自のENI(Elastic Network Interface)を持つ。(プライマリプライベート IP アドレス、内部 DNS ホスト名)
  • ENIに対して、VPCフローログ使えるので通信キャプチャ出来る
  • 同じタスクに属するコンテナは、localhost インターフェイス経由で通信できる

タスクネットワーキング機能

ECSのタスクに対して、独自のネットワークNameSpaceを提供する機能(EC2バックエンドの時は、EC2のネットワークをbridgeだったりhostマウント形式で使っていたので使わなくてもよかった)

  • Amazon ECS コンテナインスタンスには、タスクネットワーキングを有効にするために、コンテナエージェントのバージョン 1.15.0 以上が必要
  • 現時点では、Amazon ECS 対応 AMI またはその他の ecs-init パッケージの Amazon Linux バリアントだけがサポート
  • Application Load Balancer および ネットワークロードバランサーのみサポート(CLBは使えない)
  • awsvpc 上で動くfargateタスクをELBにぶら下げる際は、ターゲットタイプとして instance ではなく、ip を選択する必要がある。これは大事。つまり、EC2で運用していたALBだったりにぶら下げる時は、新しくALBのターゲットグループを作りipタイプのターゲットで作ってあげる必要がある。

タスク定義

元々EC2で動かしていたタスク定義を、Fargate対応に切り替える想定で変更点を記載

ネットワークモード

  • awsvpc選ぶ

Requires Compatibilities(互換性が必要)

  • FARGATEを選ぶ

タスクサイズ

組み合わせがあるので、例えばメモリ2GBだと0.25vCPUから1vCPUまでの間から選ぶようなイメージ

  • タスクメモリ 0.5〜30GB
  • vCPU 0.25〜4

コンテナの定義

  • ホストポートマッピングは使えない
  • メモリ、CPUの総量がタスクサイズを超えないように調整
  • ログドライバとして選べるのは、awslogsのみ

サービス

タスク定義でawsvpcネットワークモードを指定しているタスクを動かす場合に、VPCとセキュリティグループを指定することが出来る。

EC2バックエンド時は、EC2側に設定していた項目がここに来たイメージ。

  • クラスタVPC
  • サブネット
  • せキュリティグループ
  • パブリックIPの自動割当
  • ALB・NLB使う際は、ターゲットグループがIPになっているものを選ぶ(なければ作っておく)

デプロイ(サービス更新)時は、EC2インスタンスの時と同じで、タスク起動数が最小数を満たすようにタスク新規作成が始まり、ALB(NLB)ターゲットのdraining期間が過ぎるのを待って旧タスクは落ちる

AutoScalling

Fargateにする一つの大きなメリット。これまでは、EC2(ASG)のスケールアウト+サービスのスケールアウトのつじつま合わせながら組まないといけなかったので障壁高かったが、Fargateならリソース負荷ベースで気軽にスケールアウトが組める

  • スケールの単位は、CPU,Memory,ALBのリクエスト数もしくはCloudWatchアラーム
  • スケジュール単位のスケールがほしいがなさそう(CloudwatchEventsとLambda組み合わせれば出来るかな)

メトリクス/ログ

メトリクス周りが若干弱いけど、これはせっかくEC2管理から逃れられるんだから、リソースとかあまり気にせずAutoScallingをうまく組んで自動で運用していくって流れがいいのかなと思ったり。 ログは、コンテナに直接ログイン出来ない点埋めるべく標準出力は簡単に見れるような仕組みが提供されている。

内部にはログ溜めずにツール使って外に飛ばしたり、標準出力をうまく使って状況把握出来るように運用していくのが吉。 デバッグは、コンテナなんだからローカルで動けば基本OKなはずで、どうしてもってときは同じイメージをEC2バックエンドで動かすしかないかなと思ったり。

  • メトリクスはクラスタとしては出てこなくて、ECSサービス単位でCPUとmemoryが見れる
  • 標準出力は、ECSコンソール上から閲覧可能
  • ecs-cliコマンドから叩くことで tail -f 的にリアルタイムでみることも出来る(awslogsを使ってCloudwatchLogsから同じように取得も可能)

ecs-cli logs - Amazon Elastic Container Service

ecs-cli logs --follow --task-id task-id

[Tue Sep 04 04:03:41.332650 2018] メッセージ
[Tue Sep 04 04:03:41.391128 2018] メッセージ

最後に

検証しながら気付いた点

  • やはり、EC2バックエンド時と違い、ホスト側で行われていたdocker pull時のキャッシュがきかないので起動時間は長かった
  • キャッシュでごまかされていたので、webの運用ではあまり気にならなかったが、デプロイ時間に直接響くのでDockerイメージを小さくしていくことが必要になってくる

コネヒトではコンテナ周りの基盤を整備したりサービス改善を行うエンジニアを募集しています。 少しでも興味もたれた方は、是非気軽にオフィスに遊びにきていただけるとうれしいです。

www.wantedly.com