質問: WebメディアをHerokuで運用しているものです。サーバーの知識はほとんどありません、、、 機能追加やデザイン修正などで随時Herokuにデプロイする必要があり、現在は`git push`コマンドで手動でデプロイしています。 今まではアクセス数がそこまで多くない時を見計らってそのままデプロイしていた(アプリケーションを停止したりなど一切せず)のですが、つい先日ふとこのやり方でいいのかと疑問を感じました。 例えば同時アクセス数が200ぐらいあるときに、そのままの状態でデプロイしても問題ないのでしょうか? それとも、デプロイする際は`heroku stop`でアプリケーションを必ず停止してからにすべきなのか等、正しいやり方をご教授いただきたいです。 特に、同時アクセス数が多い時にどうしても修正したい部分があってデプロイしたいとき、サーバー側とユーザー側のメリット/デメリットを天秤にかけて、どうするのがより良いのかをアドバイス頂けると幸いです。 回答どうぞ宜しくお願い致します。
回答: 「**ベストな方法**は?」と質問するのは簡単ですが、何を持ってベストと判断するかは極めて難しいです。ご質問が非常に抽象的なので(判断材料が何もご提示頂けていないので)、一般論になってしまいますが... ローカルなテスト環境へリリースする場合は完全に自己都合でリリースできますけれども、サービスを **公開** するとなると、**リリース運用** について事前にきちんと **設計** すべきです。 その際、以下のような要素について検討する必要があると思います。 1. どのような性質のサービスを提供するのか 2. サービスの提供レベルをどの程度に設定するのか 3. どの程度の予算を割けるか **1) サービスの性質について** 趣味的な内容を一方的に提供するサービスと乗換案内のような公共性の高いサービスでは、当然、求められるサービスのレベルが異なってきます。また、金融機関が提供するでは、利用者の金銭的な利害に大きな影響を与えるので、求められるサービスの質も当然高くなります。 **2) サービスの提供レベルについて** 仮にPVの多いサイトを運用しているとしても、たとえば趣味的な情報の公開が目的で、**短時間であれば不定期のサービス停止が許容される**(利用者が待ってくれる)のであれば、リリース運用についてあまり厳密に考える必要はないかもしれません。 また、一口に金銭的な利害が関係していると言っても、ネットバンキングサービスのように、**月に1回程度**、日曜日の深夜帯などにメンテナンス目的で **計画に停止できる** 場合と、デイトレーディングのためのサービスで、数秒のサービスダウンが非常に高額な損失に繋がるために **365日24時間休みなく** サービスを提供しなければならない場合では全く異なります。 **3) 予算について** 高品質のサービスを提供するにはそれなりのコストが掛るので、そのサービスに振り分けられる予算もリリース運用を設計する上で重要な要素となります。 上記、1) 〜 3) の各要素に関しどの要素に重きを置くかによっても、リリース方式が変わリます。 こうした要素を考慮した上で、より具体的に検討すると... ypponさんが公開されているサービスはどのようなものでしょうか? **a) リリース頻度について** そもそも **Heroku** を利用しているということは、**サービスの提供レベル** よりは、**新しいサービスを短納期・低コストで** 提供することに重きを置いておられるのではないでしょうか?もしそうであれば、**必要が生じる度に不定期に** リリースを実施すること自体は間違っていません。 **b) サービスの継続性について** > > 機能追加やデザイン修正などで随時Herokuにデプロイする必要があり > > > とは言っても、本当にそれは大勢の方が利用中に **予告なくサービスを打ち切ってリリースする必要がある** 程の緊急性のあるものなのでしょうか?(言い換えると、利用を続けると損害を与えるような障害なのでしょうか?) それとも事前予告した上で、**計画停止中に** リリースして機能アップすれば良い性質のものですか? 利用中にサービスを中断すると、単に結果が得られないだけですか?それとも間違った結果を返してしまうというような不具合は発生しませんか? サービスを中断しても不具合を生じないのであれば、現在のように「エイッ」とリリースしてしまえば良いです。しかし、もしサービスを中断すると不具合が生じるのであれば、**サービス閉塞** の仕組みを作りこむ必要があるかもしれません。 サービス閉塞というのは、簡単に言えば、新規のリクエストをSorry画面(「ご迷惑をお掛けしております。ただいまメンテナンス中...しばらく待ってからアクセスしてください。」のような画面)へ誘導し、**リクエストを受け付けない(サービス提供を中断する)** ことです。 そうすれば、仕掛中の処理が全て完了してから安全にリリースを実施し、ローカルからアクセスしてリリース結果を確認した後に、サービスを再開(公開)する事ができます。 もしリアルタイム性が求められる(メンテナンス目的で中断できない)サービスであれば、大抵は何らかの方法で冗長化されているはずですので、それを利用します。 本サイト(正系)の障害発生時に備えてバックアップシステム(副系)があるのであれば、まず副系をバージョンアップしてから副系に切り替え、その間に正系もバージョンアップしてから正系に切り戻すことで、サービスを中断することなくリリースを実施できます。 また、バックアップシステムではなくて、負荷分散のためにロードバランシングを行っているのであれば、**サービス縮退**(複数ある系統のうち一部を切り離す)を行って、切り離した系統を順番にバージョンアップしながら *五月雨式に* リリースして行くことも出来ます。 **c) リリースの規模** リリース方式については事前に設計する必要がありますが、各回のリリースの規模に応じて *臨機応変に* 対応するのが実際的な取り組み方というものです。 たとえば、CSSのマイナーチェンジで画面のデザインが少々変わる程度であれば、何も気にせずにリリースしても影響はないと思います。デザインが大きく変わるようであれば、予告なしの変更はユーザーを驚かせてしまうでしょう。そして、サービスの内容(機能)自体が変わるのであれば、サービス提供中にリリースすると問題を生じる可能性が高いので、事前に設計した運用に則ってリリースすべきです。 リリース方式っていろいろなバリエーションがあるので、個々のサービスの性質や求めるレベル、予算などによって慎重に設計する必要があります。100個のシステムがあれば100通りのリリース運用があると言っても過言ではないと思います。 以上、非常に大雑把な説明になってしまいましたが...上記の内容をご参考にして頂いて、まずは大雑把でも良いので **目指す方向性** を決められると良いと思います。方向が決まればより具体的な検討も出来るでしょうし、更にお知りになりたい点があれば、改めて具体的にご質問頂ければ良いと思います。