Session:在服务器端建立并存放在服务器的内存中的,Session的内容存储是键值对的列表,格式:名称 | 类型:长度:值
Session的生命周期:在php.ini中 session.gc_maxlifetime 为session设置了生存时间(默认为1440s) 客户端关闭浏览器,不会影响服务器端对session的存储。php
Cookie:在服务器端建立并写回到客户端浏览器,Cookie是http标头的一部分,浏览器接到响应头中关于写Cookie的指令则在本地临时文件夹中,建立了一个cookie文件,用来保存的Cookie内容。Cookie内容的存储是键值对的方式 。web
Cookie的生命周期:能够设置过时时间,若是不设置则是会话级别的,即关闭浏览器就会消失。redis
二:执行过程sql
1. 过程:浏 览器首次访问服务器,若是是登录类型的网站,发送请求若是没有带身份,服务器检测不到cookie会跳转到登陆窗口,输入用户名和密码后再次请求,用户信 息后验证经过后返回请求页,并在HTTP头中添加setcookie信息,浏览器接受到返回内容后会处理http头部的相应信息,这里会设置 cookie,第二次用户访问服务器时会浏览器会自动把cookie内容读取出来并加到http头部,服务器接受请求后验证提交过来的 cookies是否正确,正确直接就返回相应的页面,不正确则返回登陆页面,其中会话是指从一个浏览器窗口打开到关闭这个期间。数据库
2. 原理: PHP默认的Session是基于Cookie的,在此期间首先调用session_start()函数,Session会先判断当前$_COOKIE[session_name()]是否有值(session_name()返回保存session_id的COOKIE键名),这个值能够从php.ini找到 session.name = PHPSESSID(默认值PHPSESSID)。若是没有值,函数会建立一个惟一的SessionID,同时经过header头(header(‘Set-Cookie: session_name()=session_id(); path=/’)) 将SessionID保存到客户端的Cookie中,而且在服务器端生成Session文件,文件名规则是:sess_SESSION_ID(例 如:sess_sgj1k9pq1220g5l6ne283teld1,一个128位的哈希值),Session变量的值经php内部系列化后保存在服务 器机器上的文本文件中和客户端的变量名(默认状况下)为PHPSESSID的Cookie进行对应交互。当再访问这个网站其余页面时将经过http请求头 将客户端的Cookie中保存的SessionID携带过来,这时session_start()函数不会再分配新的SessionID而是在服务器端寻 找和这个SessionID 同名的Session文件将以前保存的信息取出来。apache
3. 依赖性:PHP 中的Session在默认状况下是使用客户端的Cookie来保存session_id的,因此当客户端的Cookie出问题或者禁用的时候就会影响 Session的使用了。可是Session不必定必须依赖cookie。当客户端的Cookie被禁用或出现问题时,PHP会自动把 session_id附着在url中,这样再经过session_id就能跨页使用Session变量了。这种附着也是有必定条件的,即“php.ini 中的session.use_trans_sid = 1或者编译时打开打开了--enable-trans-sid选项”。可是PHP5只能在Linux平台能够自动检测Cookie的状态而在window 平台上没有此功能。数组
三:Session的自动回收机制浏览器
session_start() 是Session机制的开始,它有必定几率开启垃圾回收,由于Session是存放在文件中,PHP自身的垃圾回收是无效的,Session的回收是要删 文件的,这个几率是根据php.ini的配置决定的,有的系统的设置是 session.gc_probability =0,也就是几率是0,而是经过cron或者是其余脚原本实现垃圾回收。默认配置是:服务器
1 session.gc_probability =12 session.gc_divisor =1003 session.gc_maxlifetime =1440
过时时间 默认24分钟,几率是 session.gc_probability/session.gc_divisor 结果 1/100,即session_start()函数被调用1000次才会有一次调用垃圾回收程序,因此页面访问越频繁几率就越小,建议值是1/(1000~5000)。不建议设置太小,由于session的垃圾回收,是须要检查每一个文件是否过时的。cookie
客户端的Cookie的过时机制:失效了浏览器天然发送不了cookie到服务器,这时即便服务器的Session文件存在也没用,由于PHP不知道要读 取哪一个Session文件。咱们知道PHP的Cookie过时时间是在建立时设置的,那么PHP在建立session的同时为客户端建立的cookie的 生周期是多久?这个在php.ini中有设置:session.cookie_lifetime 。这个值默认是0,表明浏览器一关闭SESSIONID 就失效。那就是说咱们把session.gc_maxlifetime和session.cookie_lifetime设置成同一个值就能够控制 Session的失效时间了
四:Session操做
例如:新添加一个值$_SESSION['name'] ='xiaoming'; 那么这个SESSION只会维护在内存中,当脚本执行结束的时候,再把
_SESSION的值写入到session_id指定的文件夹中。这个阶段有 可能执行更改session_id的操做,可能销毁一个旧的的session_id,生成一个全新的session_id,例如:角色的转换,当它登陆后 须要换用新的session_id
1 if (isset($_COOKIE[session_name()])) {2 setcookie(session_name(),'',time() -40000,'/'); // session cookie过时3 }4 session_regenerate_id(); //这一步会生成新的session_id,再调用session_id()返回的是新的值
销毁session的方法有2种
第一种是经过程序session_destory()方法清除全部session unset(session['x'])来清除指定的session['x']。
第二种是经过关闭浏览器,关闭后会直接清除全部session。
设置session生命周期的也有2种方法。
第一种 setcookie() 直接用setcookie设置session id的生命周期。
1 $lifetime=60;//保存1分钟2 session_start();3 setcookie(session_name(),session_id(),time()+$lifetime,"/");
第 二种 session_set_cookie_params() 其中session_regenerate_id();方法用于改变当前session_id的值,并保留session中数组的值。参数默认为 false,若是设置为true则改变session_id的值,并清空当前session数组。
1 $lifetime=60;//保存1分钟2 session_set_cookie_params($lifetime);3 session_start();4 session_regenerate_id(true);
session相关概念
1) session id
用户session惟一标识符,随机生成的一串字符串,具备惟一性,随机性。主要用于区分其它用户的session数据。用户第一次访问web页面的时 候,php的session初始化函数调用会分配给当前来访用户一个惟一的ID,也称之为session_id。
2) session data
咱们把须要经过session保存的用户状态信息,称为用户session数据,也称为session数据。
3) session file
PHP默认将session数据存放在一个文件里。咱们把存放session数据的文件称为session文件。它由特殊的php.ini设置 session.save_path指定session文件的存放路径,CentOS5.3操做系统,PHP5.1默认存放在/var/lib/php /session目录中。
4) session lifetime
咱们把初始化session开始,直到注销session这段期间,称为session生命周期,这样有助于咱们理解session管理函数。
与session存储相关php.ini设置
1) session.save_handler = file
用于读取/回写session数据的方式,默认是files。它会让PHP的session管理函数使用指定的文本文件存储session数据。
2) session.save_path =“/var/lib/php/session”
指定保存session文件的目录,能够指定到别的目录,可是指定目录必需要有httpd守护进程属主(好比apache或www等)写权限,不然没法 回存session数据。当指定目录不存在时,php session环境初始化函数是不会帮你建立指定目录的,因此须要你手工创建指定目录。
它还能够写成这样session.save_path =“N;/path” 其中N是整数。这样使得不是全部的session文件都保存在同一个目录中,而是分散在不一样目录。这对于服务器处理大量session文件是颇有帮助的。(注:目录须要本身手工建立)
3) session.auto_start = 0
若是启用该选项,用户的每次请求都会初始化session。咱们推荐不启用该设置,最好经过session_start()显示地初始化session。
五:Session的同步与对影响系统性能
1:session在大访问量网站上确实影响系统性能,影响性能的缘由之一由文件系统设计形成,在同一个目录下超过10000个文件时,文件的 定位将很是耗时,PHP支持Session目录hash,咱们能够经过修改php.ini中session.save_path = “2;/path/to/session/dir”,那么session将存储在两级子目录中,每一个目录有16个子目录[0~f],PHP session不支持建立目录,须要事先把那么些目录建立好 。
2:小文件的效率问题,通常咱们的Session数据都不会太大(1~2K),若是有大量这样1~2K的文件在磁盘上,IO效率不好,PHP手册上建议使用Reiserfs文件系统。
六:同步问题(session共享)
1:使用数据库保存session, 使用数据库来保存session,就算服务器宕机了也没事,session照样在。问题:程序须要定制;每次请求都进行数据库读写开销不小(使用内存数据 库能够提升性能,宕机就会丢失数据。可供选择的内存数据库有BerkeleyDB,Mysql的内存表);另外数据库是一个单点,能够作数据库的ha来解 决这个问题。
2:使用 memcached来保存session, 这种方式跟数据库相似,不过由于是内存存取的,性能天然要比数据库好多了。固然存储在redis也是比较理想 的选择,方便存储统计在线人数,那么存储在redis中也实现了这个要求,并且redis支持的数据类型多。问题:程序须要定制,增长 了工做量;存入memcached中的数据都须要序列化,效率较低;若是是文件形式的,你能够用NFS统一存储。
3:还有一种方式是经过加密的cookie来实现,用户在A服务器上登陆成功,在用户的浏览器上添加一个加密的cookie,当用户访问B服务器时,检查 有无Session,若是有固然没问题,若是没有,就去检验Cookie是否有效,Cookie有效的话就在B服务器上重建session。简单,高效, 服务器的压力减少了,由于session数据不存在服务器磁盘上。根本就不会出现session读取不到的问题。。 问题:网络请求占用不少。每次请求时,客户端都要经过cookie发送session数据给服务器,session中数据不能太多,浏览器对cookie 的大小存在限制。每一个浏览器限制是不一样的,好比:Firefox 和Safari容许cookie 4097个字节,Opera容许cookie4096个字节,IE容许cookie4095个字节,因此不适合高访问量的状况,由于高访问量的状况下,每 次请求浏览器都要发送session数据给服务器,一个cookie大小2k左右。