|
今天遇到一个客户用IE8访问CI的session丢失问题,我用的是CI 1.7.1 ,使用的是CI自带的SESSION类。
问题比较奇怪,因为在自己这里IE8是支持的。
通过查找论坛帖子,换用了KNDB session,不过问题依旧。不过大概看出点问题,好像是有个director,IE8会把COOKIE的有效期给清了。
然后搜国外的论坛,发现CI的SESSION对IE8支持有问题,还有人报BUG。从论坛上分析,CI的IE8主要是2个问题:
1、重定向会导致IE8的sess_match_useragent不正确,比如论坛上有人集成了PAYPAL,然后回来的时候IE8的USERAGNET就变成了IE7,导致COOKIE过期
2、重定向会导致COOKIE的有效期过期。然后有2,3中做法。我参考了其中的一种,尝试修改,解决了问题。我猜测可能是我用AJAX有个重定向导致了COOKIE过期,做法如下:
The problem lies in the fact that IE8 removes the CI session cookie even though the expiration timestamp should prevent this
NOTE: Above happens especially when you would like to use clientredirect via: header( “Location: ” ) call instead of following the linkclick
My solution is to patch one line of the Session::_set_cookie() method in your Session.php:function _set_cookie($cookie_data = NULL)
{
/* HERE WE HAVE SOME CODE WHICH WE DO NOT TOUCH... */
/* ... WE CHANGE THE setcookie() CALL BY CHANGING THE */
/* THIRD PARAM TO 0 (originally the third parameter */
/* was set to $this->sess_expiration + time() */
// Set the cookie
setcookie(
$this->sess_cookie_name,
$cookie_data,
0, // <--- HERE YOU PLACE THE 0
$this->cookie_path,
$this->cookie_domain,
0
);
}
By patching as described above (third param of setcookie set to 0)we instruct the browser not to delete the cookie until the browsersession is finished (so in most cases until the browser is closed).
What we might also want to do is to make sure we have following call somwhere in code of our controller:$this->session->set_userdata('last_activity' => $this->session->_get_time());
This ensures that the lastActivity (in CI 1.7.2) is updated indatabase to the current timestamp. Thanks to this CI session will bedestroyed after the inactivity time passes (so the “inactivity logout”will still work even though the cookie will not be deleted by thebrowser..) <- beware however that CI must still execute call to_sess_gc() to destroy the session.. and this call depends on value of$gc_probability.. so when testing this the best is to set the$gc_probability to 100)
NOTE: If you implement this you might want to omit call to$this->session->_get_time() since this is marked as CI privatemethod. In this case write your own method to get the time
基本上我就跟着这个操作,在system/libraries/Session.php的类里面的function _set_cookie($cookie_data = NULL)这个方法的($this->now - 31500000)改成0,然后再session建立的
set_userdata这里面多加一个变量$this->session->set_userdata('last_activity' => $this->session->_get_time());这样子就会保持到关闭IE才过期。
通过这个方法解决了问题。
顺便说一下,下午调试过程中从贴子里面学到的一招:
IE8的COOKIE调试可以先按F12,再点cache里面的view cookie information 就能看到COOKIE的数据
FIREFOX反正用developer插件就能搞定,就不多说了
建议把COOKIE数据在服务器存储在数据库里面,可以从数据库里面查看SESSION数据是IP变化了还是useragent发生变化导致的问题。
今天为了SESSION丢失的问题,花了一天的时间,希望对大家有点帮助。
|
评分
-
查看全部评分
|