這篇文章主要介紹了php中實現精確設定session過期時間的方法,需要的朋友可以參考下
#大多在資料情況下我們對於session過期時間使用的是預設設定的時間,而對於一些有特殊要求的情況下我們可以設定session過期時間。
對此,可以在PHP中,設定php.ini,找到session.gc_maxlifetime = 1440 #(PHP5預設24分鐘)
這裡你可以隨便設定一下過期時間.但有人說設定以後,好像不起作用!
其實不是不起作用,而是因為系統預設:
session.gc_probability = 1 session.gc_pisor = 1000
garbage collection 有個機率的,1/1000就是session 1000次才有一次被回收。
只要你的訪問量大了,那就能達到回收的效果.
或者你也可以設定一下session.gc_pisor 的值,
比如:session.gc_pisor = 1 ,這樣就能明顯的看到SESSION過期的效果了.
我們最常用的是在php程式中設置,如下例程式所示:
<?php if(!isset($_SESSION['last_access'])||(time()-$_SESSION['last_access'])>60) $_SESSION['last_access'] = time(); ?>
這樣就搞定了,如果要設定已過期的話也可以在程式中實現:
<?php unset($_SESSION['last_access']);// 或 $_SESSION['last_access']=''; ?>
session有過期的機制:
session.gc_maxlifetime 原來session 過期是一個小機率的事件,分別使用session.gc_probability和session.gc_pisor 來決定運行session 中gc 的機率session.gc_probability和session. gc_pisor的預設值分別為1和100。分別為分子與分母 所以session中gc的機率運行機會為1% 。如果修改這兩個值,則會降低php的效率。所以這種方法是不對的! !
因此,修改php.ini檔案中的gc_maxlifetime變數就可以延長session的過期時間了:(例如,我們把過期時間修改為86400秒)
session.gc_maxlifetime = 86400
然後,重啟你的web服務(一般是apache)就可以了。
session「回收」何時發生:
預設情況下,每一次php請求,就會有1/100的機率發生回收,所以可能簡單的理解為「每100次php請求就有一次回收發生」。這個機率是透過下列參數控制的
#機率是gc_probability/gc_pisor
session.gc_probability = 1 session.gc_pisor = 100
注意1:假設這種情況gc_maxlifetime=120,如果某個session檔案最後修改時間是120秒之前,那麼在下次回收(1/100的機率)發生前,這個session仍然是有效的。
注意2:如果你的session使用session.save_path中使用別的地方保存session,session回收機制有可能不會自動處理過期session檔案。這時需要定時手動(或crontab)的刪除過期的session:
cd /path/to/sessions; find -cmin +24 | xargs rm
PHP中的session永不過期
不修改程序是最好的方法了,因為如果修改程序,測試部一定非常鬱悶,那麼只能修改系統環境配置,其實很簡單,打開php.ini設定文件,修改三行如下:
1、session.use_cookies
把這個的值設為1,並利用cookie來傳遞sessionid
2 、session.cookie_lifetime
這個代表SessionID在客戶端Cookie儲存的時間,預設是0,代表瀏覽器一關閉SessionID就作廢…就是因為這個所以PHP的session不能永久使用!那我們把它設定為一個我們認為很大的數字吧,999999999怎麼樣,可以的!就這樣。
3、session.gc_maxlifetime
這個是Session資料在伺服器端儲存的時間,如果超過這個時間,那麼Session資料就會自動刪除!那我們也把它設定為99999999。
就這樣一切ok了,當然你不相信的話就測試一下看看--設定一個session值過個10天半個月的回來看看,如果你的電腦沒有斷電或是宕機,你仍然可以看見這個sessionid。
當然也可能你沒有控制伺服器的權限並不能像我一樣幸運的可以修改php.ini設置,一切依靠我們自己也是有辦法的,當然就必須利用到客戶端存儲cookie了,把得到的sessionID儲存到客戶端的cookie裡面,設定這個cookie的值,然後把這個值傳遞給session_id()這個函數,具體做法如下:
<?php session_start(); // 启动Session $_SESSION['count']; // 注册Session变量Count isset($PHPSESSID)?session_id($PHPSESSID):$PHPSESSID = session_id(); // 如果设置了$PHPSESSID,就将SessionID赋值为$PHPSESSID,否则生成SessionID $_SESSION['count']++; // 变量count加1 setcookie('PHPSESSID', $PHPSESSID, time()+3156000); // 储存SessionID到Cookie中 echo $count; // 显示Session变量count的值 ?>
#session失效不傳遞
#我们先写个php文件:=phpinfo()?>, 传到服务器去看看服务器的参数配置。
转到session部分,看到session.use_trans_sid参数被设为了零。
这个参数指定了是否启用透明SID支持,即session是否随着URL传递。我个人的理解是,一旦这个参数被设为0,那么每个URL都会启一个session。这样后面页面就无法追踪得到前面一个页面的session,也就是我们所说的无法传递。两个页面在服务器端生成了两个session文件,且无关联。(此处精确原理有待确认)
所以一个办法是在配置文件php.ini里把session.use_trans_sid的值改成1。
当然我们知道,不是谁都有权限去改php的配置的,那么还有什么间接的解决办法呢?
下面就用两个实例来说明:
文件1 test1.php
<?php //表明是使用用户ID为标识的session session_id(SID); //启动session session_start(); //将session的name赋值为Havi $_SESSION['name']="Havi"; //输出session,并设置超链接到第二页test2.php echo "<a href="test2.php" rel="external nofollow" >".$_SESSION['name']."</a>"; ?>
文件2: test2.php
<?php 表明是使用用户ID为标识的session session_id(SID); //启动session session_start(); //输出test1.php中传递的session。 echo "This is ".$_SESSION['name']; ?>
所以,重点是在session_start();前加上session_id(SID);,这样页面转换时,服务器使用的是用户保存在服务器session文件夹里的session,解决了传递的问题。
不过有朋友会反映说,这样一来,多个用户的session写在一个SID里了,那Session的价值就发挥不出来了。所以还有一招来解决此问题,不用加session_id(SID);前提是你对服务器的php.ini有配置的权限:
output_buffering改成ON,道理就不表了。
第二个可能的原因是对服务器保存session的文件夹没有读取的权限,还是回到phpinfo.php中,查看session保存的地址:
session.save_path: var/tmp
所以就是检查下var/tmp文件夹是否可写。
写一个文件:test3.php来测试一下:
<?php echo var_dump(is_writeable(ini_get("session.save_path"))); ?>
如果返回bool(false),证明文件夹写权限被限制了,那就换个文件夹咯,在你编写的网页里加入:
//设置当前目录下session子文件夹为session保存路径。 $sessSavePath = dirname(__FILE__).'/session/'; //如果新路径可读可写(可通过FTP上变更文件夹属性为777实现),则让该路径生效。 if(is_writeable($sessSavePath) && is_readable($sessSavePath)) { session_save_path($sessSavePath); }
相关推荐:
PHP 中cookie 和session的联系以及session配置
以上是php中實作精確設定session過期時間的方法的詳細內容。更多資訊請關注PHP中文網其他相關文章!