複数のWebサーバーでセッションの持続性はどのように達成されますか?


23

StackOverflow / ServerFaultにはいくつのWebサーバーがありますか?

回答が「複数」の場合、DNSポーリング中にセッションスティッキネスが達成されますか?


そうではありませんが、言い回しが違うと興味深い質問になるかもしれません。

質問を言い換えるべきです。タイトルを「複数のWebサーバーでセッションスティッキ性をどのように達成しますか?」に変更します。またはそのような何か...
ウィリアムブレンデル

正しいフレーズを見せてくれませんか?

1
複数のサーバーを持つことはスティッキーなセッションを暗示しているという仮定-これは忌まわしいことです-は私を苦しめます。
ワンブル

回答:


42

大規模なWebサイトは、複数のマシン間で「負荷分散」される場合があります。多くの負荷分散セットアップでは、セッション中にユーザーがバックエンドマシンのいずれかにヒットする場合があります。このため、多くのマシンがユーザーセッションを共有できるようにするための方法がいくつかあります。

選択される方法は、使用される負荷分散のスタイル、およびバックエンドストレージの可用性/容量によって異なります。

Cookieのみに保存されるセッション情報:セッション情報(セッション識別子だけではありません)はユーザーのCookieに保存されます。たとえば、ユーザーのCookieには買い物かごの内容が含まれる場合があります。ユーザーがセッションデータを改ざんするのを防ぐために、CookieとともにHMACが提供される場合があります。この方法は、ほとんどのアプリケーションにおそらく最適ではありません。

  • バックエンドストレージは不要です
  • ユーザーは毎回同じマシンにアクセスする必要がないため、DNSロードバランシングを使用できます。
  • データベースマシンからのセッション情報の取得に関連する待ち時間はありません(HTTPリクエストで提供されるため)。サイトが異なる大陸のマシンによって負荷分散されている場合に役立ちます。
  • セッションに保存できるデータの量は制限されています(4K Cookieサイズの制限により)
  • ユーザーがセッションの内容を表示できないようにする場合は、暗号化を使用する必要があります
  • セッションデータのユーザーによる改ざんを防ぐために、HMAC(または同様の)を使用する必要があります
  • セッションデータはサーバー側に保存されないため、開発者がデバッグするのはより困難です

ロードバランサーは常にユーザーを同じマシンに誘導します。多くのロードバランサーは、ユーザーがどのバックエンドマシンからリクエストを行っているかを示す独自のセッションCookieを設定し、将来それらをそのマシンに送信します。ユーザーは常に同じマシンに誘導されるため、複数のマシン間でセッションを共有する必要はありません。これはいくつかの状況で良いかもしれません:

  • 既存のアプリケーションのセッション処理は、複数のマシンに対応するために変更する必要がない場合があります
  • セッションを保存するために共有データベースシステム(または同様のもの)は必要ありません。おそらく信頼性は向上しますが、複雑さが犠牲になります。
  • バックエンドマシンがダウンすると、それで開始されたすべてのユーザーセッションがダウンします。
  • 機械をサービスから外すことはより困難です。メンテナンスのためにマシン上でセッションを終了するユーザーは、マシンの電源を切る前にタスクを完了することができます。これをサポートするために、Webロードバランサーには、特定のバックエンドマシンにリクエストを「排出」する機能があります。

共有バックエンドデータベースまたはキー/値ストア:セッション情報はバックエンドデータベースに格納され、すべてのWebサーバーがクエリと更新にアクセスできます。ユーザーのブラウザーは、セッション情報を指す識別子(セッションIDなど)を含むCookieを保存します。これはおそらく3つの中で最もクリーンな方法です。

  • ユーザーは、保存されたセッション情報にさらされる必要はありません。
  • ユーザーは毎回同じマシンにアクセスする必要がないため、DNSロードバランシングを使用できます。
  • 1つの欠点は、採用されているバックエンドストレージシステムに配置できるボトルネックです。
  • セッション情報は期限切れになり、一貫してバックアップされる場合があります。

全体として、ほとんどの動的Webアプリケーションは多数のデータベースクエリまたはキー/値ストアリクエストを実行するため、データベースまたはキー/値ストアはセッションデータの論理的な保存場所です。


2
+1かなり包括的な答えで、それを書くのを節約できます。:) dbストレージに関する限り、リレーショナルデータベースはおそらく間違っているでしょう。永続的なmemcachedフォークのようなものの方が優れています。memcachedbが適している場合があります。また、サーバー間のセッション情報の複製を見逃しました。これは最良の方法ではありませんが、Tomcatのようなものが行うので、文書化する価値があります。
デビッドパシュリー

Google、Twitter、Facebookのどのアプローチが利用されていますか?
ダニーボーイ14

1
Google、Twitter、Facebookについてはわかりませんが、Redisはセッションストアに最適です。その基本的に「永続的なmemcached」であるDavid Pashleyは、Redisが初期の2009年に推奨していました。
ベンR

4

質問が複数のフロントエンドWebサーバー間でセッションを維持する方法である場合、答えは通常、集中型データベースを使用することです。Webサーバーインスタンスに依存してローカルファイルシステム上のセッションファイルを追跡する代わりに、セッションIDとデータを中央DBに書き込むと、すべてのWebサーバーが代わりにそこからデータを取得します。


集中化されたデータベースに言及するための+1。そのアイデアを少し拡張/単純化するだけです。グローバルユーザーIDなどの一意の値を使用してユーザーのPCにCookieを設定すると、そのGUIDをデータベースに保存できます。クライアントがGUID / Cookieを持っている限り、クライアントがどのサーバーに接続するかは問題ではありません。データベースに対してそれらを検索し、それに応じてセッションを追跡できます。
KPWINC 2009年

2
リレーショナルデータベースにセッションを保存することは常に悪い考えです。一時データの保存にデータベースを使用しないでください。
デビッドパシュリー

2

nemcachedを使用することは、@ David Pashleyで言及されていない良い解決策のようです

すべてのサーバーで共有されるリモートmemcachedインスタンスを持ち、独自のセッションハンドラーを提供するmemcache PECL拡張機能を使用することを意味します。

PHP構成の2つのパラメーターを変更するだけです!

良いチュートリアルhttp://www.dotdeb.org/2008/08/25/storing-your-php-sessions-using-memcached/


しかし、複数のデータセンターがあるのは何ですか?
ダニーボーイ14

0

IIRCは、DotNetRocks#440で、1サーバー期間と述べました。それがまだ当てはまるかどうかわからない。

編集:実際には、Hanselminutes#134でした。ごめんなさい。


0

クッキーを設定できます。

リモートIPのハッシュを計算できます(最も単純な奇数番号のリモートホストはサーバーAに、偶数番号のホストはサーバーBに移動します)。

sslトンネルを使用している場合、ソースシステムにとどまるいくつかの値を介して実行することもできます。

通常、上記の各メカニズムには、「リバースプロキシ」サーバーまたは何らかのロードバランサーが必要です。そのロードバランサーはトラフィックを受け入れ、上記の基準の1つに基づいて、最初にセッションを持っていたサーバーにトラフィックを転送します。

ただし、「DNSポーリング」の意味はわかりません


0

a)セッション情報をユーザーcookieに保存できます。ステートレス硬化クッキー、サーバー側で保存なしデータが、ジャムセッション状態を参照してくださいhttp://www.cl.cam.ac.uk/~sjm217/papers/protocols08cookies.pdfを。b)セッションバックエンドストレージをデータベースまたはmemcachedに変更できます。単一障害点を排除するために、データベース複製または複数のmemcachedノードを設定できます。セッションでユーザー状態を失うことは大きなエラーではなく、彼を非常に不幸にしないセットアップでは、memcachedが推奨されることに注意してください。状態を維持することが重要な場合は、データベースを使用します。PHP、Django、およびRailsの両方で、開発者はカスタムセッションバックエンドを作成できます。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.