memcacheデーモンのプールを使用してセッションをより効率的に共有できますか?


25

1台のWebサーバーのセットアップから2台のWebサーバーのセットアップに移行しているため、2つの負荷分散マシン間でPHPセッションの共有を開始する必要があります。すでにmemcachedがインストールされており(開始されているため)、php.iniファイル内の3行のみ(session.save_handlerおよびsession.save_path)を変更するだけで、新しいサーバー間でセッションを共有できることに驚きました

私は置き換えました:

session.save_handler = files

で:

session.save_handler = memcache

次に、マスターWebサーバーでsession.save_pathlocalhostを指すように設定します。

session.save_path="tcp://localhost:11211"

スレーブWebサーバーではsession.save_path、マスターを指すように設定します。

session.save_path="tcp://192.168.0.1:11211"

仕事は終わった、私はそれをテストし、それは動作します。しかし...

明らかにmemcacheを使用するということは、セッションがRAMにあり、マシンがリブートされるかmemcacheデーモンがクラッシュすると失われることを意味します-これには少し懸念がありますが、2つのWebサーバー間のネットワークトラフィックを特に心配しています(特になぜなら、誰かがスレーブWebサーバーに負荷分散されると、そのセッションはマスターWebサーバーからネットワークを介してフェッチされるからです。save_pathsネットワークを使用する前にマシンが独自のセッションストレージを検索するように2つ定義できるかどうか疑問に思っていました。例えば:

マスター:

session.save_path="tcp://localhost:11211, tcp://192.168.0.2:11211"

スレーブ:

session.save_path="tcp://localhost:11211, tcp://192.168.0.1:11211"

これにより、サーバー間でセッションが正常に共有され、パフォーマンスが向上しますか?つまり、ネットワークトラフィックを50%節約します。または、この手法はフェイルオーバー専用です(たとえば、1つのmemcacheデーモンに到達できない場合)。

:memcacheの複製について具体的に尋ねているわけではありません-PHP memcacheクライアントがプール内の各memcacheデーモン内でピークに達し、見つかった場合はセッションを返し、見つからない場合のみ新しいセッションを作成できるかどうかすべての店で。私がこれを書いているとき、私はPHPに少し質問していると思っています、笑...

想定:スティッキーセッションなし、ラウンドロビンロードバランシング、LAMPサーバー。


1
Memcacheのドキュメントでは、セッションストレージにMemcacheを使用することはお勧めしません。code.google.com/p/memcached/wiki/…を参照してください!!

回答:


37

免責事項:たくさんのテストを行わず、資格のある人から第2の意見を得るまでもなく、私に耳を傾けることに夢中になるでしょう 。このゲームは初めてです

この質問で提案された効率改善のアイデアは機能しません。私が犯した主な間違いは、memcachedストアがプール内で定義されている順序が何らかの優先順位を規定していると考えることでした。これはそうではありません。memachedデーモンのプールを定義する場合(たとえばを使用session.save_path="tcp://192.168.0.1:11211, tcp://192.168.0.2:11211")、どのストアが使用されるかを知ることはできません。データは均等に分散されます。つまり、アイテムが最初に格納される場合もあれば、最後に格納される場合もあります(または、memcacheクライアントが複製するように構成されている場合は両方になる可能性があります-複製を処理するのはクライアントであり、memcachedサーバーはそれ自体をしないでください)。どちらの方法でも、localhostをプールの最初として使用してもパフォーマンスは向上しません。いずれかのストアにヒットする可能性は50%です。

memcacheを使用してサーバー間でセッションを共有できると結論付けましたが、おそらくしたくないと思います-共有を使用するのと同様にスケーリングもしないので、人気がないようですデータベースは堅牢ではありません。詳細については、フィードバックをお寄せください。

PHPアプリがない場合は、以下を無視してください。


ヒント1:memcacheを使用して2つのサーバー間でセッションを共有する場合:

PHP memcacheクライアントをインストールし、ファイルに以下を追加したときに、「memcacheセッションハンドラーのサポートを有効にしますか?」に対して「はい」と回答したことを確認します。/etc/php.d/memcache.ini

session.save_handler = memcache

Webサーバー1(IP:192.168.0.1):

session.save_path="tcp://192.168.0.1:11211"

Webサーバー2(IP:192.168.0.2):

session.save_path="tcp://192.168.0.1:11211"

ヒント2:memcacheを使用して2つのサーバー間でセッションを共有し、フェイルオーバーをサポートする場合:

以下を/etc/php.d/memcache.iniファイルに追加します。

memcache.hash_strategy = consistent
memcache.allow_failover = 1

Webサーバー1(IP:192.168.0.1):

session.save_path="tcp://192.168.0.1:11211, tcp://192.168.0.2:11211"

Webサーバー2(IP:192.168.0.2):

session.save_path="tcp://192.168.0.1:11211, tcp://192.168.0.2:11211"

ノート:

  • これは、元の質問で私が犯した別の間違いを強調しています- session.save_pathすべてのサーバーで同一のものを使用していませんでした。
  • この場合、「フェイルオーバー」とは、1つのmemcacheデーモンに障害が発生した場合、PHP memcacheクライアントが他のmemcacheデーモンの使用を開始することを意味します。つまり、ストアでセッションに失敗したユーザーはログアウトされます。透過的なフェールオーバーではありません。

ヒント3:memcacheを使用してセッションを共有し、透過的なフェールオーバーをサポートする場合:

/etc/php.d/memcache.iniファイルに次を追加する必要があることを除いて、ヒント2と同じです。

memcache.session_redundancy=2

ノート:

  • これにより、PHP memcacheクライアントは2つのサーバーにセッションを書き込みます。冗長性(RAID-1など)が得られるため、書き込みはn個のミラーに送信get'sされ、失敗はミラーで再試行されます。これは、1つのmemcacheデーモンに障害が発生しても、ユーザーがセッションを失うことはないことを意味します。
  • ミラー化された書き込みは並行して行われ(非ブロッキングIOを使用)、ミラーの数が増えても速度のパフォーマンスが低下することはありません。ただし、me​​mcacheミラーが異なるマシンに分散されている場合、ネットワークトラフィックが増加します。たとえば、localhostを使用してネットワークアクセスを回避する可能性は50%ありません。
    • どうやら、書き込みレプリケーションの遅延により、キャッシュミスではなく古いデータが取得される可能性があります。問題は、これがアプリケーションにとって重要かどうかです。どのくらいの頻度でセッションデータを書き込みますか?
  • memcache.session_redundancyセッションの冗長性のためmemcache.redundancyですが、異なるレベルの冗長性を持たせたい場合、PHPアプリケーションコードで使用できるiniオプションもあります。
  • PHP memcacheクライアントの最新バージョン(現時点ではまだベータ版)が必要です-peclのバージョン3.0.3が機能しました。

「共有データベースを使用するのと同じように拡張できません」についてコメントできますか?通常のマスター/スレーブDBセットアップとの違いはわかりません。ありがとう!
少年Baukema

これはかなりクールな内訳です​​が、ext/memcacheバージョン3.x を使用すると期待どおりに動作しないという噂(バグレポート)があります。私たちもそのオプションで遊んでいるので、サーバーリストをループして自分で書き込むことにしました。
ティル

ヒント3の場合:memcachedホストが1つダウンしてから起動すると、ホストが数秒ダウンするとどうなりますか。私が理解しているように-セッションデータは復元されず、その一部は失われますよね?
GioMac

28

再:上記のヒント3(Google経由でこれに遭遇した他の人)、少なくともこれが機能するmemcache.session_redundancy = N+1ためには、少なくともあなたのプール内のN台のサーバーに使用する必要があります働く価値。(Debian安定版、pecl memcache 3.0.6、2つのmemcachedサーバーでphp 5.3.3でテストしました。でsession_redundancy=2最初のサーバーをオフにするとすぐに失敗し、正常 save_pathsession_redundancy=3動作します。)

これは、次のバグレポートに記録されているようです。


1
十分なあなたをupvoteすることはできません...
フェスト

1
下にスクロールできてうれしいです。これが問題でした。
ダレンシュウェンケ

私には明確ではありませんが、この機能はPECL memcache 3.xシリーズでのみ利用できますか?これらはすべて、pecl.php.net / package / memcacheのベータ版ソフトウェアにリストされていますが、2.2.7では、リーダーを見つけたサーバーを強制終了すると、すべてが停止します。
ジョー

正直に言うと、これを見てから何年も経ちました。私が思い出すように、これは3.xの機能(icbw)でした。そのプラグインの「ベータ版」を使用して多くのシステムを展開しました(一部は非常にトラフィックが高い)が、それに関連するように見える問題はありませんでした。YMMV、ライブに進む前にテストなど:)私はここ数年PHPで仕事をしていないので、トリビアの細かい点のいくつかが消え始めています。
マイケルジャクソン14

3

上記のphp.ini設定に加えて、以下も設定されていることを確認してください。

memcache.allow_failover = 1  
memcache.hash_strategy = 'consistent'

その後、完全なフェイルオーバーとクライアント側の冗長性が得られます。このアプローチの注意点は、memcachedがlocalhostでダウンしている場合、php memcacheクライアントがsession.save_pathで指定されたプール内の次のサーバーを試行する前に常に読み取りミスが発生することです。

これは、Webサーバーで実行されているphp memcacheクライアントのグローバル設定に影響することに注意してください。


consistentハッシュ戦略を使用することsession.save_pathは、各Webサーバーで異なることを考慮して意味がありますか?
トム

1

memcachedはそのようには動作しません(間違っている場合は修正してください!)

アプリケーションに冗長セッションストレージを持たせる場合は、両方のmemcachedインスタンスへのエントリを変更/追加/削除するものを作成する必要があります。memcachedはこれを処理せず、キーハッシュストレージとしてのみ提供します。だから、複製も同期もなし、なだ。

私がこの問題について間違っていないことを願っていますが、これがmemcachedについて知っていることです。


あなたが間違っていた場合、それは私にとって便利でしょう。:-) phpslacker.comphpslacker.com/2009/03/02/php-session-clustering-with-memcache)には、memcachedが質問で説明されているように機能することを示唆する記事があります。おそらく、memcacheクライアントがハッシュ戦略をどのように実装するかによりますか?
トム

1
memcacheはそのようには機能しませんが、phpは希望どおりに機能するようです。説明のようにphp.iniを変更するか、アプリを変更する必要があります。ブログから:あなたが尋ねるクラスタリングはどこにありますか、まあ、真実は何もないと言われます。これまでのところ、2つのサーバーで構成されるmemcacheプールがあります。PHPは、プールに書き込むように構成されています。PHPは、「session.save_path」iniディレクティブで指定された順序でサーバープールの読み取り/書き込みを行います。読み取りの場合、PHPはプールからキーでキャッシュオブジェクトを要求します。「フェイルオーバー」が有効になっているため、PHPはmemcacheサーバーのプールを1つずつ照会します。[...]
tore-

1

memcachedはそのままでは複製できませんが、repcached(パッチを適用したmemcached)は複製します。ただし、すでにmysqlを使用している場合、そのレプリケーション機能をマスターマスタレプリケーションで使用して、完全なデータレプリケーションのメリットを享受するだけではありません。

C.


情報をありがとう。私が望んでいるのは本当に複製ではありません。セッションが見つかるまで、各memcachedを順番にピークにしたい場合が多くあります。つまり、最速であるため最初にローカルホストをチェックし、次に他のサーバーをチェックします。
トム

1
すべての神の名においてなぜ???? これは完全に間違った解決策です...私が考えることができるどんな問題についても。サーバーが2台だけでも非常に非効率であることに加えて、サーバーをさらに追加すると、パフォーマンスが急速に悪化します。また、実際にサーバーをクラスターに追加することで停止の可能性を減らす必要がある場合、ソリューションが単一サーバーの2倍の停止を引き起こすという事実を考慮していません。(ところでDNSベースのラウンドロビンを意味する場合、セッションアフィニティは暗黙的です!)
symcbean

フィードバックのおかげで、はい、私はセッション共有の初心者です!:-)しかし、なぜ私の提案がこんなにsoいのか理解できませんでした。共有DBを使用するよりも効率的であると考え、また、停止の可能性を低くすることも考えました。
トム

いいえ、可能性が高くなります。このようなデータのフェデレーションは、レプリケーションの量を減らすために非常に多数のノードがある場合に意味がありますが、通常は、可用性を維持するために定義された数のプールでレプリケーションを行います。repcachedレプリケーションとmysqldレプリケーションの違いを確認するには、パフォーマンスを非常に慎重にする必要があります。
symcbean

allow_failover = 1を使用している限り、複数のミラーによって停止が少なくなる可能性があることをテストして確認しました。ログアウトせずに、1つのミラーをシャットダウンし、それを再起動して、もう1つのミラーを再起動して、最初のミラーを再びシャットダウンできます。PHP memcacheクライアントは、舞台裏で多くの策略を行っていると思います。
トム
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.