13

ログインしたメンバーエリアを持つサイト/システムがあり、ユーザーがサイト/システムで作業しているときにログアウトすることはめったにありませんが、非常に不便だとしましょう。

ユーザーが長時間アイドル状態ではなかったので、おそらくセッションの有効期限が切れています。また、セッションがアイドル状態の場合でも、定期的な AJAX 要求、いわゆるハートビートを追加しました。これにより、セッションのアクセス時刻と変更時刻が更新されます。ユーザーが何かをクリックするか、ハートビートが呼び出されるたびに、 touch($session_file) を追加しました。セッションIDも再生成してみました。何も助けませんでした。

残念ながら、これまでのところ、問題をローカルで再現することはできませんでした。これは、リクエストが増えると頻繁に発生するためです。いくつかの php.ini パラメータ:

session.use_cookies = 1
session.use_only_cookies = 1
session.cookie_lifetime = 0
session.gc_probability = 1
session.gc_divisor = 1500
session.gc_maxlifetime = 10800
4

5 に答える 5

6

セッションと認証は、コード内の 1 つのスーパー コントローラーを介して既に処理されているため、少なくともセッションの破棄を除外することは簡単です。

通常、ログイン ページのみがセッションを作成するため、この時点で、セッション ID などの既知の値を内部に追加できます (追加する必要があります)。

他のページ (ハートビートを含む) は既存のセッションを再開するため、この時点で上記の値を探します。見つからない場合は、さらにいくつかのチェックを行うことができます。

  • セッション Cookie が渡されましたか? そうでない場合は、ブラウザ/クッキーの問題です。
  • セッション Cookie は に対応していsession_id()ますか? そうでない場合は、ガベージ コレクションによりセッション ファイルが失われました。
  • 既知の値がセッションに存在するか? そうでない場合は、セッションが切り捨てられたか、誰かがセッション採用攻撃を試みています。
  • 既知の値はセッション Cookie に対応していますか? そうでない場合、セッションは Cookie 以外の方法で確立されました。設定を確認できsession.use_only_cookiesました。

上記の一連のチェックにより、正しい方向に進むはずです。

于 2012-08-13T09:04:42.277 に答える
3

組み込みの PHP ファイル セッション ストレージを使用していると思いますか? これには既知の競合状態の問題があります。

同じセッション ID からの同時要求があったときに、セッション ID を失うという同様の問題がありました。ファイルが最初の要求によってロックされたため、他のすべての同時接続はファイルにアクセスできず、それらのいくつかは新しいセッション ID を生成しました。これらの状況も非常にまれであり、問​​題を特定するのに時間がかかりました. それ以来、私はセッション ストレージに memcached を使用しており、これらの問題は解消されました。

于 2012-08-14T18:46:48.667 に答える
2

これ以上の情報なしでこれに答えるのは難しいですが、これはトラフィックが多い場合にのみ発生すると確信していますか. できること:

  • コードを追加
  • OS ディストリビューションとバージョン
  • PHP のバージョン

IP に依存するセッション チェックはありますか。その場合、(Cloudflare のように) 頻繁に異なる IP を提供するプロキシを実際に使用している可能性があります。この場合、 を使用しHTTP_CF_CONNECTING_IPて実際に一定の IP を取得できます。

また、もう1つ気づいたことがあります。

session.use_only_cookies = 1
session.cookie_lifetime = 0

そのため、ブラウザを閉じると、Cookie は実際に破棄されます。ユーザーがタブを閉じたために接続が失われた可能性はありますか (一部のブラウザーでは実際に Cookie が消去されます)。

他の人が示唆しているように、DB セッションに移行することを強くお勧めします。中央セッション ストアを使用すると、競合状態を停止するのに役立ちます。完全に停止するわけではありませんが、より困難になります。また、本当に多くのセッション ID を取得した場合は、組み込みの PHP セッション ID 以外のものを使用して検討することもできますが、組み込みのハッシュは非常に一意であり、重複する可能性が非常に低いため、それがあなたのものではないと思います問題。

明確化編集:

Cloudflare に別のプロキシを使用している場合は、もちろん、プロキシ セットの HTTP ヘッダーを取得する必要があります。Cloudflare の使用がその例です。

于 2012-08-21T20:42:56.943 に答える
0

提供されたすべての回答は、質問に対する優れた洞察を示していますが、私は自分の正確な問題の解決策を共有する必要があります。ようやく問題を再現して修正することができました。

したがって、システムには2つのサブシステム、たとえば管理者インターフェイスとクライアントインターフェイスが含まれていました。管理者が別のタブでクライアントとしてログインし、管理者としてログインしているときにクライアントインターフェイスからログアウトすると、管理者が予期せずログアウトしました。これは、すべてが名前空間を使用して1つのセッションに書き込まれたためです。私がしたことは、ログアウトアクションでセッションを破壊し続けたコードを削除し、セッション名前空間の設定を解除して、ログインページにのみアクセスできるその名前空間のゲストセッションに置き換えることです。

于 2012-11-24T13:09:16.063 に答える
0

ここに私が使用したものがあります。JavaScript を使用して、10 分間隔でサーバーを「ping」します。

<form method="POST" target="keepalive-target" id="keepalive-form">
    <input type="hidden" name="keepalive-count" id="keepalive-count">
</form>
<iframe style="display:none; width:0px; height:0px;" name="keepalive-target"></iframe>
<script>
    var kaCount=0;
    setInterval(function()
    {
        document.getElementById("keepalive-count").value=kaCount++
        document.getElementById("keepalive-form").submit();
    },600000);
</script>
于 2012-08-22T07:35:40.843 に答える