web-dev-qa-db-ja.com

高可用性アプリケーションを設計する方法

現在、クラシックなn層アプリケーションがあります:DB/Webサービス/フロントエンド。他のコンポーネントがありますが、それは基本的なレイアウトです。

アプリケーションの可用性を向上させる主な理由は3つあります。

  1. 私たちのホストは時々(すべてのように)停止を経験し、私たちは顧客への影響を最小限にしたいので、たとえば、データセンターAがダウンした場合、彼らはデータセンターBをオンにします。
  2. バージョンをアップグレードすると、メンテナンスのためにサイトがシャットダウンされ、通常は数時間かかります(移行スクリプトなど)。ユーザーには、ダウンタイムを最小限に抑えて、よりシームレスな移行を望んでいます(サーバーAのアップグレード中にサーバーBを使用します)。
  3. オプションとして、私たちの顧客は世界中にあり、私たちは彼らの接続が不安定である可能性があるにもかかわらず、可能な限り最高の体験をしてもらいたいと思っています(インドの開発者と働いた人は誰でも私が何を言っているか知っているはずです)。理想的には、私たちは彼らのオフィスにサーバーを接続できるようにしたい(または彼らの都市の近くのデータセンターを使用できる)ようにしたい、そしてそれは私たちのアーキテクチャにシームレスに統合するだろう。

リモートでは、95%の場合でも99%の可用性は必要ありません。ドキュメント管理アプリです。誰も気にしない。ただし、移行には時間がかかる場合があり、世界中にお客様がいるため、お客様が1日のほとんどの時間にわたって仕事をすることができない場合があります。

SQLの部分については、「適切な」DBAは存在しませんが、 SQLの可能性については知っています :レプリケーション、ミラーリングなど。DB側では、このためのリソースを見つけるのは非常に簡単です。セッションやコードの保存など、他のすべてが難しいのは何ですか。Webサービスサーバーがダウンした場合、UIはそれを切り替える必要があることをどのようにして知るのでしょうか。セッションはどのようにサーバー間で保持されますか?

残念ながら、私たちの誰もこの分野での経験がなく、どこを見ればよいのかさえわかりません。このためのベストプラクティスはありますか?デザインパターン?ライブラリー(お金がないため、無料で使用できます)?

私たちはASP.NetとSQL Serverを使用しており、中央にWCF Webサービスがあります。 Windowsサービスはたくさんありますが、ミッションクリティカルではありません。Webサイトを処理する方法がサービスに適用できると思います。

ほとんどのクラウドプラットフォームがこのための組み込みシステムを提供していることを理解していますが、私たちのシステム管理者はすべてを自分で管理し、誰にも依存しないことを望んでいるため、クラウドホスティングは不可能です。

9
thomasb

探している高可用性の種類を明確にする必要があります。私が実行する可用性の高いアプリケーションには、95%の時間を必要とするものがあります。 99%で実行する必要がある他のものがあります。 100%の稼働時間を必要とする生死のシナリオを考えることができます。これら3つだけでは、アプローチとコストが大幅に異なります。

ニーズと95〜99%の稼働時間SLAに基づいて推測するだけです。

  • ほとんどの変更について、データベースの移行はリアルタイムで実行できるはずです。実践 進化的データベース設計 。より侵襲的な動作が必要な変更については、いくつかのオプションがあります。 1つはダウンタイムを取ることです。可能であれば、サービスを読み取り専用モードで実行すると機能する場合があります。完全な機能を実現するために、しばらくScaleArcを試してみたいと思っていました。これは、SQL Serverの世界でスケーリングと復元力を実現するための非常に洗練されたツールのように見えます。
  • 顧客のサイト内にサーバーを配置することは、世界規模の展開戦略(移行の説明に基づいてまだ実現していない)がない限り、管理不可能な災害のレシピです。パフォーマンスの問題があるため、オンプレミスでクラウドサービスをプッシュしないでください。パフォーマンスの問題を今すぐ解決すれば、コストのかかる問題に対処する必要がなくなります。
  • 状態サーバーは、何らかのデータベースである必要があります。 HAガイドラインに従ってください。 SQL Serverは既に使用できるため、SQL Serverを使用できます。
  • データベースと言えば、レプリケーションはHAを有効にしません。実際、SQLレプリケーションは毎ターン問題を引き起こします(複数ノードのレプリケーションシナリオの経験から言えば)。ミラーリングは機能しますが、最後に覚えているように、SQLクラスタリングは新しいサーバーにフェイルオーバーするのに1〜5分かかります。 AlwaysOnについて良いことは聞いたが、Microsoftの実績を考えると、私はまだ疑わしい。ここでは、ScaleArcのようなものがさらに役立つ場合があります。
  • Webサーバーはステートレスである必要があります。 3つまたは4つスピンアップし、ロードバランサーの後ろに置きます。これで稼働時間の心配が解消されます。フレデリクが前述したように、ローリングデプロイメントをこの方法で行うこともできます。
  • Webサービスはおそらくステートレスでなければなりません。そうでない場合は、ステートレスビットとステートフルビットに分解できるかどうかを確認してください。同じロードバランサーの背後に複数のインスタンスを配置すると、稼働時間の問題が解決され、より関心の高いデプロイメントシナリオ(青/緑のデプロイメントなど)が可能になります。

フレデリクとは異なり、私はあなたのクラウドパラノイアを不当なものとはしません。稼働時間の要件によって異なります。冗長性のために、サービスはさまざまな国のさまざまなプロバイダーが運営する複数のデータセンターで実行する必要があると考えられます。しかし、あなたの現在の状態を考えると、AWS、Azure、または同様のものがおそらくあなたの会社にとって安全な賭けであることに同意します。

5
mgw854

Webおよびアプリケーション層である程度のHAを取得する:

  1. 理想的には、データベースやメモリ内のセッション状態サーバーなどの共有状態システムに、セッション状態を含むすべての状態を除外します。アプリケーションの設計によっては、追加のレイテンシが大量の状態を取得するため、パフォーマンスの問題が発生する可能性があります。

  2. Webサイトとアプリケーション層には、それぞれの前に独立したロードバランサーが必要です。 NGINXはトリックを行いますが、IISもこれを行うことができます(ARR))。

  3. 単一のデータベースが負荷を処理できない場合は、セッション状態のパーティション分割(またはシャーディングまたは一貫したハッシュ)を利用して、特定の要求を特定のデータベースボックスにルーティングします。

状態の抽出が難しい場合は、負荷分散のためのサーバーアフィニティを使用できます(つまり、ユーザーは常に同じボックスにルーティングされ、多くの場合、Cookieベースです)。ボックスの停止はそのボックスのすべてのユーザーと状態に影響を与えるため、ステートレスラウンドロビンアプローチほど高可用性ではありませんが、完全な停止(ユースケースに依存)に勝ります。

アップグレード側:

  1. システムの実行中にデータベースのアップグレードを実行できるように、つまり下位互換性を維持するように、データベーススクリプトを設計します。そのために適切に機能するパターンは、「展開してから縮小する」です。追加する後方互換の変更のみを行いますが、削除したいフィールド(など)への依存関係を削除します。次に、データベースのすべてのクライアントをv-latestにアップグレードします。次に、別のdb-upgradeを実行して、データベース内の古いフィールド(など)を削除します。大規模なデータベースがあり、システムのパフォーマンスを損なわないように注意する必要がある場合、これは処理が遅くなる可能性があります。

  2. アプリ層のアップグレード:クラウド環境を使用していないため、カナリアデプロイメントパターンに従うことをお勧めします。ウェブ層と中間層ボックスのローリングアップグレードを実行します。デプロイがうまくいかない場合は、失敗したかのように、ロードバランサーから箱を取り出します。

警告の言葉:HA向けに設計されていないシステムを1つに進化させることは、長くて費用のかかるプロセスになる可能性があります。途中でトレードオフを行う必要があります(特定のレベルの可用性に到達するためのコストと労力)

クラウドのパラノイアは不当です-AWSなどのプロバイダーは、あなたの側の優れた実践と組み合わせてほとんどのリスクを制御/軽減できます-コンプライアンスのページを見て、どの規制に準拠しているかを感じてください: https ://aws.Amazon.com/compliance/

5
Frederik

TL; DR:冗長なモジュール式のビルド。可用性をテストします。よく監視してください。

説明を絞り込もうとすると非常に長くなる可能性があることを認識した後、私が行ったすべての観察結果を書き留めます。

前提を問う

クラウドシステムは万能薬です

トップクラウドプロバイダーを使用して完全にクラウドに移行する場合でも、回復力を備えたアプリケーションを設計する必要があります。 AWSがVMを置き換える可能性がありますが、アプリケーションは、計算の途中で放置された場合でも再起動できる必要があります。

X/y/zのため、クラウドシステムを使用したくない

あなたが超大規模な組織でない限り、あなたはクラウドシステムを使用する方が利益があります。トップ3クラウドシステム(AWS、MSFT、Google)は、何千ものエンジニアを雇用して、約束されたSLAと管理しやすいダッシュボードを提供します。実際には、この社内で10セントを費やす代わりにそれらを使用するのはお買い得です。

スコーピングとデザインの問題

サービスの可用性を定義、定量化し、継続的に測定することは、可用性の問題に対するソリューションを作成するよりも大きな課題です。

「可用性」の定義と測定は予想よりも難しい

複数の利害関係者は可用性について異なる見方をしており、最高の給与を持つ人が他の定義よりも優先される定義が起こる可能性があります。これは正しい定義である場合もありますが、多くの場合、エコシステムは同じものを測定することを前提として構築されていません。その理想的な定義は測定が非常に難しく、リアルタイムで監視することはできません。リアルタイムで監視できない可用性の定義がある場合、不気味な類似点を持つ自己実行の類似プロジェクトが何度も見つかります。理にかなったものと簡単に監視できるものにこだわる。

人々は常に利用可能なシステムの複雑さを過小評価しています。

部屋の象に対処するために、「マルチコンピュータシステムは100%利用可能ではありません。将来的には、現在のテクノロジーでは利用できなくなる可能性があります。」ここでは、現在のテクノロジーで、光の速度などよりも信号を速く送信できないことを指します。 分散コンピューティングの制限 を知っている価値のあるすべてのcomp-sciエンジニアは、会議でそれを言及せず、初心者のように見えることを恐れています。 分散コンピューティングの制限に言及していないすべての人を補うために 私は言うでしょう、それは複雑ですが常にコンピュータを信頼するわけではありません

人々は彼ら/彼らのエンジニアの能力を過大評価している

残念ながら、可用性はあなたが何を望んでいるのかは分からないがあなたが何を望んでいないのかを知っているカテゴリーに分類されます。 UIなどの「欲しいものを知っている」カテゴリは少しトリッキーです。他人の経験などから学ぶには、少しの経験と多くの読書が必要です。

ゼロから利用可能なシステムを構築する

システム要件としての可用性の適切な優先順位について、すべてのアーキテクチャおよび設計チームに伝道するようにしてください。

可用性を支援するシステムの属性

以下のシステム特性は、システムの可用性に貢献していることが示されています。

冗長性

この例としては、VMの後ろにVIPが1つしかないことや、データのコピーが1つだけ保存されないことが挙げられます。これらは、優れたIAASを使用すると、解決が容易になりますが、これらの決定を行う必要があります。

モジュール性

モジュラー [〜#〜] rest [〜#〜] は、モノリシックSOAよりも優れています。モジュール式のマイクロサービスでも、実際には通常の [〜#〜] hateos [〜#〜][〜#〜] rest [〜#〜]よりも実際に利用可能です 。推論は、次のセクションのYield関連の議論で見つけることができます。バッチ処理を行う場合は、1,000,000のバッチを処理するよりも、10秒の合理的なバッチでバッチ処理を行う方が適切です。

弾力性

"I am always angry"
                    - Hulk

回復力のあるシステムは、いつでも回復する準備ができています。この復元力は、RAIDディスクへの書き込み後にのみ書き込みに対するACKを確認するなどのインスタンスに適用されます。別の最新の傾向は、 競合のないデータ構造 を使用することです。この場合、データ構造は、2つの異なるバージョンが提示されたときに競合を解決する責任を負います。システムは後付けとして弾力性を持たせることはできず、予測して組み込む必要があります。故障は長期にわたって保証されているので、常に復旧計画を立てておかなければなりません。

ログ証跡

これは技術的にはレジリエンスのサブタイプですが、すべての機能をキャッチできるため、非常に特別なタイプです。最善の努力にもかかわらず、利用不可のパターンを予測できない場合があります。可能であれば、システムイベントを再生できるように、システムアクティビティの十分なログトレイルを維持してください。これにより、手作業で大きなコストをかけて、予期しない状況から回復することができます。

可用性の属性

「可用性」の網羅的ではないtop-of-mind属性リスト:議論のために、ユーザーの質問が「ショッピングカートにはいくつの商品がありますか?」

正しさ

あなたは最も正確な可能な答えを出さなければなりませんか、それとも間違いを犯しても大丈夫ですか?参考までに、ATMからお金を引き出す場合、正確であるとは限りません。銀行が間違いを見つけた場合、取引を取り消す可能性があります。あなたのシステムが素数を生成しているなら、私は推測するでしょう、あなたはいつも正しい答えが欲しいかもしれません。

産出

前のトピックの質問に対して常に正しい回答をした場合は、このポイントをスキップしてください。時々、質問に対する答えは正確である必要はありません。現在Facebookには何人の友達がいますか?しかし、答えは常にボールパーク+/- 1にあると予想されます。期待どおりの結果が得られる場合、利回りは100です。

一貫性

あなたの答えはある時点では正しいかもしれませんが、光が画面を出て観察者の網膜に入る時までに、物事は変わっていたかもしれません。それはあなたの答えを間違っていますか?いいえ、一貫性がなくなります。ほとんどのアプリケーションは結果的に整合性がありますが、秘訣は、アプリケーションが提供する整合性モデルの種類を定義することです。たまたま、アプリケーションを1台のコンピューターで実行できる場合は、 CAP定理 でこの読み物をスキップできます。

費用

多くは、短期的な影響(収益の損失)と長期的な影響(悪い評判、顧客維持)の全体的な影響によって異なります。顧客のタイプ(有料/無料、繰り返し/一意、キャプティブ)とリソースの可用性に応じて、さまざまなレベルの可用性保証を組み込む必要があります。

既存システムの可用性の向上に向けて

個々のマシンとネットワークの運用管理は非常に複雑で、クラウドプロバイダーに任せているか、自分が何をしているのかを知るのに十分な専門知識があると思います。空室状況の下で他のトピックに触れます。長期的な戦略では、 Define-Measure-Analyze-Control は天国での一致であり、私自身が見たものです。

  1. ステークホルダーへの「可用性」を定義
  2. 定義したものをどのように測定しますか
  3. 根本原因分析ボトルネックを特定する
  4. 改善のためのタスク
  5. システムの継続的な監視(制御

利用できない原因

物理的なインフラストラクチャ管理をカバーする運用管理は専門家によって行われるべきであることに同意したので、完全を期すために、利用できない他の原因に触れます。 IMOの可用性には、期待される動作の欠如も含まれる必要があります。つまり、ユーザーに期待されるエクスペリエンスが表示されない場合、何かが利用できません。その広い定義を念頭に置いて、次のものは利用できなくなる可能性があります:-コードのバグ-セキュリティの問題-パフォーマンスの問題

1
Ajeet Ganga