ホームページ >php教程 >php手册 >PHP はセッションのライフサイクルを設定します

PHP はセッションのライフサイクルを設定します

WBOY
WBOYオリジナル
2016-06-21 08:49:16984ブラウズ

この記事では主に php セッションのライフサイクルに関する知識を共有します。

まずはセッション作成の開始から終了までの流れを説明します。

プログラムがクライアントのリクエストに対してセッションを作成する必要がある場合、サーバーはまずクライアントにセッション ID と呼ばれるセッション識別子が既に含まれているかどうかを確認します (既に含まれている場合、取得メソッドは session_id() です)。セッション ID は、クライアントが以前にセッションを作成したことがあり、サーバーがセッション ID に従ってセッション内の値を取得することを意味します。クライアントにセッション ID が含まれていない場合は、クライアントが初めてサーバーを要求したことを意味します。キャッシュ ファイルを手動でクリアし、このクライアントのセッションを作成し、このセッションに関連付けられたセッション ID を生成します。一般的に、セッション ID の値は繰り返されず、暗号化された文字列であるこのセッション ID が使用されます。セッションは応答で保存するためにクライアントに返されます。

セッションはいつ作成されましたか?

通常 (通常という意味) ブラウザがサーバーに最初のリクエストを行うときに作成され、一定量のメモリ領域を占有するため、不要な場合はセッションを閉じるようにしてください。

セッションはいつ削除されますか?

通常、セッションは次の状況で削除されます:

まず、session_destroy() リセット関数を使用して手動で削除します。

2 つ目は、セッションの最後のアクティビティ時刻と現在時刻の間の間隔がセッションのタイムアウト設定を超えていることです。3 つ目は、サーバー プロセスが停止していることです。

ブラウザを閉じたときにセッションを削除するにはどうすればよいですか?

理論的には、これは不可能です。HTTP はステートレス プロトコルであるため、サーバーはクライアントがいつブラウザを閉じたかを知りません。また、PHP にはこの情報を取得するための関連機能がありません。しかし、この問題はまだ解決できます。つまり、Web ページの特殊効果コード window.oncolose を使用してブラウザの終了アクションを監視し、Ajax を使用してサーバーにセッションを削除するリクエストを送信しますが、この方法では問題が完全に解決されるわけではありません。ブラウザのクラッシュ、突然の停電、ユーザーのフリーズなど、状況によっては応答できなくなります。

一定期間後にセッションが自動的に期限切れになる (削除される) ように設定するにはどうすればよいですか?

session_start() はセッションメカニズムの始まりであり、一定の確率でガベージコレクションを有効にします。セッションはファイルに保存されるため、SESSION のリサイクル (削除) は無効になります。この確率は php.ini の設定に基づいて決定されますが、一部のシステムでは session.gc_probability = 0 が設定されており、これは確率が 0 であることを意味し、ガベージ コレクション (つまり、セッションの削除) が実装されます。 cronスクリプト。

PHP のデフォルトのセッション有効期間は 1440 秒 (24 分、注意: php5 のデフォルトは 180 分) です。つまり、クライアントが 24 分を超えて更新されない場合、現在のセッションは期限切れになります。明らかに、これはニーズを満たしていません。

既知の効果的な方法は、session_set_save_handler を使用してすべてのセッション管理作業を引き継ぐことです。一般に、セッション情報はデータベースに保存されるため、SQL ステートメントを通じて期限切れのセッションをすべて削除でき、セッションの有効期間を延長できます。正確に制御されています。これは、PHP ベースの大規模な Web サイトで一般的に使用される方法でもあります。ただし、通常の小規模な Web サイトの場合は、それほど苦労する必要はないようです。

しかし、一般的なセッションには有効期限があり、ユーザーがブラウザを閉じると、セッション変数は保存できません。では、Session の永続的な寿命を達成するにはどうすればよいでしょうか?

ご存知のとおり、セッションはクライアントから提供されたセッション ID に基づいてサーバー側に保存され、そのファイルは変数の値を取得するために読み取られます。クライアントのCookieまたはHttp1.1プロトコルのQuery_String(つまり、アクセスしたURLの「?」以降の部分)がサーバーに送信され、サーバーはSessionディレクトリを読み取ります。

セッションの永続的な存続を実現するには、まずセッションに関する php.ini の関連設定を理解する必要があります (「[セッション]」セクションで php.ini ファイルを開きます)。

1. session.use_cookies: デフォルト値は「1」です。これは、SessionID が Cookie によって渡されることを意味します。それ以外の場合は、Query_String によって渡されます。

2. session.name: これは、Cookie または Query_String によって渡される変数名です。

3. session.cookie_lifetime: これは、セッション ID がクライアント Cookie に保存される時間を表します。デフォルトは 0 です。これは、ブラウザが閉じるとすぐにセッション ID が無効になることを意味します。セッションは永続的に使用することはできません。

4. session.gc_maxlifetime: セッション データがサーバー側に保存される時間です。この時間を超えると、セッション データは自動的に削除されます。

多くの設定がありますが、これらはこの記事に関連するものです。永続セッションの使用方法の原則と手順について説明します。

前に述べたように、サーバーは SessionID を通じてセッション データを読み取りますが、通常、ブラウザーから送信された SessionID はブラウザーを閉じると失われるため、SessionID を手動で設定して保存するだけで済みます。サーバーを操作する権限がある場合、次の手順に従うだけで、セットアップは非常に簡単になります。

1. 「session.use_cookies」を 1 に設定し、セッション ID を保存するための Cookie をオンにします。ただし、デフォルトは 1 であり、通常は変更する必要はありません。

2. "session.cookie_lifetime" を正の無限大に変更します (もちろん、正の無限大のパラメーターはありませんが、999999999 と正の無限大には違いはありません)。

3. 「session.gc_maxlifetime」を「session.cookie_lifetime」と同じ時刻に設定します。

セッションの有効期間を設定するパラメータは session.gc_maxlifetime であることが PHP ドキュメントに明記されています。このパラメータは、php.ini ファイルまたは ini_set() 関数を通じて変更できます。問題は、多くのテストを行った後、このパラメーターを変更しても基本的には効果がなく、セッションの有効期間がデフォルト値の 24 分のままであることです。

PHP の動作メカニズムにより、セッション情報を定期的にスキャンしてセッション情報が無効かどうかを判断するデーモン スレッドがありません。有効なリクエストが発生すると、PHP はグローバル変数 session.gc_probability/session.gc_divisor (php.ini または ini_set() 関数を通じて変更することもできます) の値に基づいて GC (ガベージ コレクター) を開始するかどうかを決定します。 。

デフォルトでは、session.gc_probability = 1、session.gc_divisor = 100 です。これは、GC が開始される確率が 1% であることを意味します。 GC の仕事は、すべてのセッション情報をスキャンし、現在の時刻からセッションの最終変更時刻 (変更日) を減算し、それを session.gc_maxlifetime パラメータと比較することです。生存時間が gc_maxlifetime を超えている場合、セッションは次のようになります。削除される。

これまでのところ、すべてがうまく機能しています。では、なぜ gc_maxlifetime が無効になるのでしょうか?

デフォルトでは、セッション情報はシステムの一時ファイル ディレクトリにテキスト ファイルの形式で保存されます。 Linux では、このパスは通常 tmp であり、Windows では通常 C:WindowsTemp です。サーバー上に複数の PHP アプリケーションがある場合、それらのセッション ファイルは同じディレクトリに保存されます。同様に、これらの PHP アプリケーションも一定の確率で GC を開始し、すべてのセッション ファイルをスキャンします。

問題は、GC が動作しているときに、異なるサイト上のセッションが区別されないことです。たとえば、サイト A の gc_maxlifetime は 2 時間に設定され、サイト B の gc_maxlifetime はデフォルトの 24 分に設定されます。サイト B の GC が開始されると、パブリック一時ファイル ディレクトリがスキャンされ、サイト A からのものか B からのものかに関係なく、24 分より古いすべてのセッション ファイルが削除されます。このように、サイト A の gc_maxlifetime 設定は役に立ちません。

問題を見つけたら、解決するのは簡単です。 session.save_path パラメータを変更するか、session_save_path() 関数を使用して、セッションが保存されるディレクトリを専用のディレクトリに指定します。 gc_maxlifetime パラメータは正常に機能します。

厳密に言えば、これは PHP のバグですか?

もう 1 つの問題は、gc_maxlifetime が保証できるのはセッションの存続時間の最短時間だけであり、この時間を過ぎるとセッション情報はすぐに削除されることです。 GC は確率に基づいて開始され、長期間開始されない可能性があるため、gc_maxlifetime を超えた後も多数のセッションが有効になります。

この問題を解決する 1 つの方法は、session.gc_probability/session.gc_divisor の確率を 100% まで高めることです。ただし、この問題は明らかにパフォーマンスに重大な影響を及ぼします。もう 1 つの方法は、コード内で現在のセッションの存続期間を確認し、それが gc_maxlifetime を超えた場合は、現在のセッションをクリアすることです。

ただし、サーバーを操作する権限がない場合は、永続的なセッション データの保存を実現するために、PHP プログラムを通じて SessionID を書き換える必要があります。 php.net の関数マニュアルを確認すると、「session_id」関数が表示されます。パラメータが設定されていない場合は、現在の SessionID が返されます。パラメータが設定されている場合、現在の SessionID は指定された値に設定されます。

永続的な Cookie を使用し、「session_id」関数を追加する限り、永続的なセッション データを保存できます。

ただし、便宜上、サーバーによって設定された「session.name」を知る必要がありますが、ほとんどのユーザーはサーバーの php.ini 設定を表示する権限を持っていません。ただし、PHP には非常に優れた関数「phpinfo」が用意されています。 」を使用すると、ほぼすべての PHP 情報が表示されます。

エディタを開いて上記のコードを入力し、ブラウザでプログラムを実行すると、PHP 関連の情報が表示されます。 「session.name」パラメータがあります。これは必要なサーバーの「session.name」で、通常は「PHPSESSID」です。

<?php
phpinfo();

SessionID の名前を書き留めると、永続的なセッション データの保存が可能になります。

さらに、PHP セッションの生存時間を設定するために、ネットユーザーがインターネット上で非常に優れた方法を書いているのを見つけました。ここでコードを共有します。

<?php
session_start();
ini_set('session.save_path','/tmp/');
//6个钟头
ini_set('session.gc_maxlifetime',21600);
//保存一天
$lifeTime = 24 * 3600;
setcookie(session_name(), session_id(), time() + $lifeTime, "/");

使用方法も非常に簡単です。例:

<?php
function start_session($expire=0){
	if($expire==0){
		$expire=ini_get('session.gc_maxlifetime');
	}else{
		ini_set('session.gc_maxlifetime',$expire);
	}
	if(empty($_COOKIE['PHPSESSID'])){
		session_set_cookie_params($expire);
		session_start();
	}else{
		session_start();
		setcookie('PHPSESSID',session_id(),time()+$expire);
	}
}
<?php start_session(600);//600秒以后过期

后记:其实真正的永久储存是不可能的,因为Cookie的保存时间有限,而服务器的空间也有限……但是对于一些需要保存时间比较长的站点,以上方法就已经足够了!



声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。