search
Homephp教程php手册PHP session与cookie
PHP session与cookieJun 13, 2016 am 10:56 AM
cookiephpsessionandprincipleserveruserend

PHP SESSION原理

session是在服务器端保持用户会话数据的一种方法,对应的cookie是在客户端保持用户数据。HTTP协议是一种无状态协议,服务器响应完后就失去了与浏览器的联系,cookie引入浏览器,使得数据跨越页面交换。

首先客户端和服务器端建立一一联系,每个客户端都有一个唯一标识,这样服务器才能识别出来。建议唯一标识的方法有两种:cookie或者通过GET方式指定。默认配置的PHP使用session的时会建立一个名叫”PHPSESSID”的cookie(可以通过php.ini修改session.name值指定),如果客户端禁用cookie,你也可以指定通过GET方式把session id传到服务器(修改php.ini中session.use_trans_sid等参数)。

客户端将session id传递到服务器,服务器根据session id找到对应的文件,读取的时候对文件内容进行反序列化就得到session的值,保存的时候先序列化再写入。

事实就是这样,如果服务器不支持session或者你想自定义session,完全可以DIY,通过PHP的uniqid生成永不重复的session id,然后找个地方存储session的内容即可,还可以把session存储在MySQL数据库中。

所谓的session其实就是客户端一个session id,服务器端一个session file,新建session时,告诉服务器要生成一个cookie以及准备好session文件,要不然你的session内容怎么存;读取session时告诉服务器,赶紧根据session id把session文件反序列化。

session影响系统性能

session在大访问量网站上确实影响系统性能,影响性能的原因之一由文件系统设计造成,在同一个目录下超过10000个文件时,文件的定位将非常耗时,PHP支持session目录hash,我们可以通过修改php.ini中session.save_path =“2;/path/to/session/dir”,那么session将存储在两级子目录中,每个目录有16个子目录[0~f],不过好像PHPsession不支持创建目录,你需要事先把那么些目录创建好 。

还有一个问题就是小文件的效率问题,一般我们的session数据都不会太大(1~2K),如果有大量这样1~2K的文件在磁盘上,IO效率肯定会很差。可以通过缓存memcache和mysql数据库提供效率。

session的同步

前端可能有很多台服务器,用户在A服务器上登录了,种下了session信息,然后访问网站的某些页面没准跳到B服务器上去了,如果这个时候B服务器上没有session信息又没有做特殊处理,可能就会出问题了。

session同步有很多种,如果你是存储在memcached或者MySQL中,那就很容易了,指定到同样的位置即可,如果是文件形式的,你可以用NFS统一存储。

(NFS是Network File System的简写,即网络文件系统.网络文件系统是FreeBSD支持的文件系统中的一种,也被称为NFS. NFS允许一个系统在网络上与他人共享目录和文件。通过使用NFS,用户和程序可以像访问本地文件一样访问远端系统上的文件。)

还有一种方式是通过加密的cookie来实现,用户在A服务器上登录成功,在用户的浏览器上种上一个加密的cookie,当用户访问B服务器时,检查有无session,如果有当然没问题,如果没有,就去检验cookie是否有效,cookie有效的话就在B服务器上重建session。这种方法其实很有用,如果网站有很多个子频道,服务器也不在一个机房,session没办法同步又想做统一登录那就太有用了。

当然还有一种方法就是在负载均衡那一层保持会话,把访问者绑定在某个服务器上,他的所有访问都在那个服务器上就不需要session同步了。


session_start();

if(isset($_SESSION['test_sess'])){

     $_SESSION['test_sess']++;

}else{

     $_SESSION['test_sess'] = 0;

}

echo$_SESSION['test_sess'];

?>;

第一次请求服务器:

GET/test.php HTTP/1.1

Accept:*/*

Referer:http://localhost/

Accept-Language:zh-cn

Accept-Encoding:gzip, deflate

User-Agent: Mozilla/4.0 (compatible; MSIE6.0; Windows NT 5.1; SV1; Maxthon; .NET CLR 1.1.4322)

Host:localhost

Connection:Keep-Alive

服务器第一次返回:

HTTP/1.1200 OK

Date:Fri, 26 Aug 2005 07:44:22 GMT

Server:Apache/2.0.54 (Win32) SVN/1.2.1 PHP/5.0.4 DAV/2

X-Powered-By:PHP/5.0.4

Set-Cookie:PHPSESSID=bmmc3mfc94ncdr15ujitjogma3; path=/

Expires:Thu, 19 Nov 1981 08:52:00 GMT

Cache-Control: no-store, no-cache,must-revalidate, post-check=0, pre-check=0

Pragma:no-cache

Content-Length:1

Keep-Alive:timeout=15, max=99

Connection:Keep-Alive

Content-Type:text/html; charset=utf-8

Content-Language:Off

第二次请求服务器:

GET/test.php HTTP/1.1

Accept:*/*

Referer:http://localhost/

Accept-Language:zh-cn

Accept-Encoding:gzip, deflate

User-Agent: Mozilla/4.0 (compatible; MSIE6.0; Windows NT 5.1; SV1; Maxthon; .NET CLR 1.1.4322)

Host:localhost

Connection:Keep-Alive

Cookie: PHPSESSID=bmmc3mfc94ncdr15ujitjogma3

服务器第二次返回:

HTTP/1.1200 OK

Date:Fri, 26 Aug 2005 07:44:23 GMT

Server:Apache/2.0.54 (Win32) SVN/1.2.1 PHP/5.0.4 DAV/2

X-Powered-By:PHP/5.0.4

Set-Cookie:PHPSESSID=bmmc3mfc94ncdr15ujitjogma3; path=/

Expires:Thu, 19 Nov 1981 08:52:00 GMT

Cache-Control: no-store, no-cache,must-revalidate, post-check=0, pre-check=0

Pragma:no-cache

Content-Length:1

Keep-Alive:timeout=15, max=98

Connection:Keep-Alive

Content-Type:text/html; charset=utf-8

Content-Language:Off

仔细对比这些输出,第二次请求比第一次请求多出来的就是:

Cookie:PHPSESSID=bmmc3mfc94ncdr15ujitjogma3

这个header将会向服务器发送一个cookie信息,告诉服务器我有一个cookie,名字叫PHPSESSID,内容是bmmc3mfc94ncdr15ujitjogma3。

这个cookie是怎么来的呢?看第一次服务器返回的信息里边有:

Set-Cookie:PHPSESSID=bmmc3mfc94ncdr15ujitjogma3; path=/

这是服务器向客户端浏览器写一个cookie,名字是PHPSESSID,值是bmmc3mfc94ncdr15ujitjogma3,这个值实际就是所谓的session_id。

继续看第二次向服务器发出的请求,仍然向服务器发送了PHPSESSID这个cookie

可以得到以下结论:

1、只要使用了session,就会通过cookie的方式向客户端浏览器发送session

2、每次向服务器发出请求的时候,本地浏览器会把cookie附带在请求信息中

COOKIE

    cookie 是一种在远程浏览器端储存数据并以此来跟踪和识别用户的机制。

PHP在http 协议的头信息里发送cookie,因此setcookie()函数必须在其它信息被输出到浏览器前调用。

原理.

a.服务器通过随着响应发送一个http 的Set-Cookie 头,在客户机中设置一个cookie(多个cookie 要多个头)。

   b.客户端自动向服务器端发送一个http 的cookie 头,服务器接收读取。

     HTTP/1.x 200 OK

     X-Powered-By: PHP/5.2.1

  Set-Cookie:TestCookie=something from somewhere; path=/

     Expires: Thu, 19 Nov 2007 18:52:00 GMT

     Cache-Control: no-store, no-cache,must-revalidate,      post-check=0,pre-check=0

   Pragma: no-cache

   Content-type: text/html

 这一行实现了cookie 功能,收到这行后

 Set-Cookie: TestCookie=something fromsomewhere; path=/

浏览器将在客户端的磁盘上创建一个cookie 文件。

下面的同样的效果:

setcookie('TestCookie','something   from somewhere','/');

header('Set-Cookie:TestCookie=something from somewhere; path=/')

常见问题解决:

1) 用 setcookie()时有错误提示,可能是因为调用setcookie()前面有输出或空格。

2) $_COOKIE 受magic_quotes_gpc 影响,可能自动转义。

3) 使用的时候,有必要测试用户是否支持cookie。

下面以用户登录为例分析session和cookie

HTTP协议是一种无状态协议,服务器响应完用户的请求,就失去了与浏览器的联系,PHP是如何实现session的。

用户第一次访问服务器时,因为没有session信息,需要登录验证,用户通过表单把用户名,密码,验证码等信息提交给服务器,服务器在验证用户的合法性之前先对数据进行预处理。通过到数据库验证,用户是合法的,这个时候服务器会给浏览器信息中包含Set-Cookie: PHPSESSID=bmmc3mfc94ncdr15ujitjogma3;这样的信息,这样浏览器会把信息写到本地文件中,其中PHPSESSID为唯一标识符。同时服务器也会在指定的文件把序列化的session信息保存在文件中。当用户再次请求时,浏览器会把对应cookie中的PHPSESSID也发送给服务器,服务器得到PHPSESSID,会到session文件中验证,如果验证成功,就直接登录。从而类似的可以实现数据在不同用户页面之前的传递。session中的值是key-value。

session影响系统性能

session在大访问量网站上确实影响系统性能,影响性能的原因之一由文件系统设计造成,在同一个目录下超过10000个文件时,文件的定位将非常耗时,PHP支持session目录hash,我们可以通过修改php.ini中session.save_path =“2;/path/to/session/dir”,那么session将存储在两级子目录中,每个目录有16个子目录[0~f],不过好像PHPsession不支持创建目录,你需要事先把那么些目录创建好 。

还有一个问题就是小文件的效率问题,一般我们的session数据都不会太大(1~2K),如果有大量这样1~2K的文件在磁盘上,IO效率肯定会很差。可以通过缓存memcache和mysql数据库提供效率。

session的同步

前端可能有很多台服务器,用户在A服务器上登录了,种下了session信息,然后访问网站的某些页面没准跳到B服务器上去了,如果这个时候B服务器上没有session信息又没有做特殊处理,可能就会出问题了。

session同步有很多种,如果你是存储在memcached或者MySQL中,那就很容易了,指定到同样的位置即可,如果是文件形式的,你可以用NFS统一存储。

(NFS是Network File System的简写,即网络文件系统.网络文件系统是FreeBSD支持的文件系统中的一种,也被称为NFS. NFS允许一个系统在网络上与他人共享目录和文件。通过使用NFS,用户和程序可以像访问本地文件一样访问远端系统上的文件。)

还有一种方式是通过加密的cookie来实现,用户在A服务器上登录成功,在用户的浏览器上种上一个加密的cookie,当用户访问B服务器时,检查有无session,如果有当然没问题,如果没有,就去检验cookie是否有效,cookie有效的话就在B服务器上重建session。这种方法其实很有用,如果网站有很多个子频道,服务器也不在一个机房,session没办法同步又想做统一登录那就太有用了。

还有一种方法就是在负载均衡那一层保持会话,把访问者绑定在某个服务器上,其他所有访问都在那个服务器上就不需要

 

Statement
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn
php怎么把负数转为正整数php怎么把负数转为正整数Apr 19, 2022 pm 08:59 PM

php把负数转为正整数的方法:1、使用abs()函数将负数转为正数,使用intval()函数对正数取整,转为正整数,语法“intval(abs($number))”;2、利用“~”位运算符将负数取反加一,语法“~$number + 1”。

php怎么实现几秒后执行一个函数php怎么实现几秒后执行一个函数Apr 24, 2022 pm 01:12 PM

实现方法:1、使用“sleep(延迟秒数)”语句,可延迟执行函数若干秒;2、使用“time_nanosleep(延迟秒数,延迟纳秒数)”语句,可延迟执行函数若干秒和纳秒;3、使用“time_sleep_until(time()+7)”语句。

php怎么除以100保留两位小数php怎么除以100保留两位小数Apr 22, 2022 pm 06:23 PM

php除以100保留两位小数的方法:1、利用“/”运算符进行除法运算,语法“数值 / 100”;2、使用“number_format(除法结果, 2)”或“sprintf("%.2f",除法结果)”语句进行四舍五入的处理值,并保留两位小数。

php字符串有没有下标php字符串有没有下标Apr 24, 2022 am 11:49 AM

php字符串有下标。在PHP中,下标不仅可以应用于数组和对象,还可应用于字符串,利用字符串的下标和中括号“[]”可以访问指定索引位置的字符,并对该字符进行读写,语法“字符串名[下标值]”;字符串的下标值(索引值)只能是整数类型,起始值为0。

php怎么根据年月日判断是一年的第几天php怎么根据年月日判断是一年的第几天Apr 22, 2022 pm 05:02 PM

判断方法:1、使用“strtotime("年-月-日")”语句将给定的年月日转换为时间戳格式;2、用“date("z",时间戳)+1”语句计算指定时间戳是一年的第几天。date()返回的天数是从0开始计算的,因此真实天数需要在此基础上加1。

php怎么读取字符串后几个字符php怎么读取字符串后几个字符Apr 22, 2022 pm 08:31 PM

在php中,可以使用substr()函数来读取字符串后几个字符,只需要将该函数的第二个参数设置为负值,第三个参数省略即可;语法为“substr(字符串,-n)”,表示读取从字符串结尾处向前数第n个字符开始,直到字符串结尾的全部字符。

php怎么替换nbsp空格符php怎么替换nbsp空格符Apr 24, 2022 pm 02:55 PM

方法:1、用“str_replace(" ","其他字符",$str)”语句,可将nbsp符替换为其他字符;2、用“preg_replace("/(\s|\&nbsp\;||\xc2\xa0)/","其他字符",$str)”语句。

php怎么判断有没有小数点php怎么判断有没有小数点Apr 20, 2022 pm 08:12 PM

php判断有没有小数点的方法:1、使用“strpos(数字字符串,'.')”语法,如果返回小数点在字符串中第一次出现的位置,则有小数点;2、使用“strrpos(数字字符串,'.')”语句,如果返回小数点在字符串中最后一次出现的位置,则有。

See all articles

Hot AI Tools

Undresser.AI Undress

Undresser.AI Undress

AI-powered app for creating realistic nude photos

AI Clothes Remover

AI Clothes Remover

Online AI tool for removing clothes from photos.

Undress AI Tool

Undress AI Tool

Undress images for free

Clothoff.io

Clothoff.io

AI clothes remover

AI Hentai Generator

AI Hentai Generator

Generate AI Hentai for free.

Hot Article

Hot Tools

PhpStorm Mac version

PhpStorm Mac version

The latest (2018.2.1) professional PHP integrated development tool

MantisBT

MantisBT

Mantis is an easy-to-deploy web-based defect tracking tool designed to aid in product defect tracking. It requires PHP, MySQL and a web server. Check out our demo and hosting services.

SublimeText3 Linux new version

SublimeText3 Linux new version

SublimeText3 Linux latest version

SecLists

SecLists

SecLists is the ultimate security tester's companion. It is a collection of various types of lists that are frequently used during security assessments, all in one place. SecLists helps make security testing more efficient and productive by conveniently providing all the lists a security tester might need. List types include usernames, passwords, URLs, fuzzing payloads, sensitive data patterns, web shells, and more. The tester can simply pull this repository onto a new test machine and he will have access to every type of list he needs.

EditPlus Chinese cracked version

EditPlus Chinese cracked version

Small size, syntax highlighting, does not support code prompt function