Fork me on GitHub

PHP中cookie的 path/domain参数

在PHP中用setcookie 来设置网站的cookie,该函数的用法如下:

bool setcookie ( string $name [, string $value [, int $expire = 0 [, string $path [, string$domain [, bool $secure = false [, bool $httponly = false ]]]]]])

setcookie() 参数详解:

参数 说明 举例
name cookie的名字 使用 $_COOKIE[‘cookiename’] 调用名为cookiename 的 cookie。
value cookie的值,存放在客户端,不要存放敏感数据 假定 name 是’cookiename’,可以通过$_COOKIE[‘cookiename’] 取得其值。
expire Cookie 过期的时间。这是个 Unix 时间戳,即从 Unix纪元开始的秒数。换而言之,通常用 time() 函数再加上秒数来设定 cookie 的失效期。或者用mktime()来实现。 time()+606024*30 将设定 cookie 30 天后失效。如果未设定,cookie 将会在会话结束后(一般是浏览器关闭)失效。
path Cookie 在服务器端的有效路径。 如果该参数设为 ‘/‘的话,cookie就在整个 domain 内有效,如果设为 ‘/foo/‘,cookie就只在 domain 下的 /foo/目录及其子目录内有效,例如 /foo/bar/。默认值为设定 cookie 的当前目录。
domain 该 cookie 有效的域名。 要使 cookie 能在如 example.com域名下的所有子域都有效的话,该参数应该设为 ‘.example.com’。虽然 . 并不必须的,但加上它会兼容更多的浏览器。如果该参数设为www.example.com 的话,就只在 www 子域内有效。细节见Cookie 规范中的 tail matching。
secure 指明cookie 是否仅通过安全的 HTTPS 连接传送。当设成 TRUE时,cookie 仅在安全的连接中被设置。默认值为FALSE。 0 或 1
httponly 设为true后,只能通过http访问,javascript无法访问;防止xss读取cookie;php5.2以上版本已支持HttpOnly参数的设置,同样也支持全局的HttpOnly的设置,在php.ini中,session.cookie_httponly=ture来开启全局的Cookie的HttpOnly属性 setcookie(“abc”, “test”,NULL, NULL, NULL, NULL, TRUE)

path参数

如下的目录结构:
coookie
├─child
│ └── child.php
└─father.php
father.php中的代码:

1
2
3
4
5
6
7
8
<?php
setcookie("father_set_0", "default", time()+24*3600);
setcookie("father_set_1", "/", time()+24*3600, "/");
setcookie("father_set_2", "/child/", time()+24*3600, "/child/");
setcookie("father_set_3", "/cookie/child/", time()+24*3600, "/cookie/child/");

echo '<pre>';
print_r($_COOKIE);

child.php中的代码:

1
2
3
4
5
6
7
8
9
<?php

setcookie("child_set_0", "default", time()+24*3600);
setcookie("child_set_1", "/", time()+24*3600,"/");
setcookie("child_set_2", "/child/", time()+24*3600, "/child");
setcookie("child_set_3", "/cookie/child/", time()+24*3600, "/cookie/child/");

echo '<pre>';
print_r($_COOKIE);

按father.php—>child.php—>father.php—>child.php的顺序访问页面,输入出结果如下:
第一次访问father.php:

father_first_view

初始状态下客户端没有相关的cookie记录,在上图中只有已收到的cookie,没有已发送的cookie,则打印$_COOKIE数组时是没有输出。
  从上面这点可以看出,页面的每次请求cookie的变化是:页面请求时浏览器发送客户端已有的cookie,服务器端接收cookie将其存入数组$_COOKIE数组中供程序使用;而在服务器端响应本次请求设置的cookie尚未发送到客户端时$_COOKIE数组中是没有记录的。

第一次访问child.php:

child_first_view

页面打印出的$_COOKIE数组中有两个值,分别是请求时发送的数据,一个页面只能访问路径设置为当前页面路径和父路径的cookie,不能访问兄弟路径的cookie。

第二次访问father.php:

father_second_view

这里就能看出来father.php虽然设置了三个cookie,但由于路径的原因浏览器请求时并没有发送其他子路径的cookie以至于不能读取。其中”child_set_1”是子路径下的页面设置的cookie,由于路径是本页面所在路径则能读取。

  还有一点值得注意的是,这次访问时没能打印出”child_set_0”的值,在child.php中”child_set_0”的路径是为空的,这点是默认为当前路径,而不是站点根目录的,所有子路径想设置cookie让父路径的页面访问则需要设置路径的。

第二次访问child.php:

child_second_view

没能打印出路径为”/child”的cookie,这点说明浏览器只发送“直系”路径关系的cookie值

总结:

  • 服务器端每次访问的cookie是每次请求头中发送给服务器端的
  • setcookie如果不设置路径,默认为当前页面的路径,父亲路径的页面是无法访问的
  • 客户端每次请求只发送当前路径下和“直系”关系的父路径的cookie(父路径的页面是不能访问子路径和兄弟路径的cookie的)

domain参数

第五个参数$domain,它决定了cookie的作用域。现在有如下3个域名,一个顶级域名、一个二级域名和一个三级域名:
① lotus.com
②blog.lotus.com
③test.blog.lotus.com
首先在①lotus.com域名下设置cookie,做四次测试,分别设置domain参数为空、lotus.com、blog.lotus.com与test.blog.lotus.com
√表示该域名下能取到cookie,×表示不能取到cookie

domain参数 lotus.com blog.lotus.com test.blog.lotus.com
setcookie(‘name’, ‘jason’, time()+100) × ×
setcookie(‘age’, ‘20’, time()+100,’/‘,’lotus.com’)
setcookie(‘birthday’, ‘19901106’, time()+100,’/‘,’blog.lotus.com’) × × ×
setcookie(‘sex’, ‘male’, time()+100,’/‘,’test.blog.lotus.com’) × × ×

②blog.lotus.com域名下设置cookie,测试条件同上,即domain参数为空,lotus.com,blog.lotus.com与test.blog.lotus.com

domain参数 lotus.com blog.lotus.com test.blog.lotus.com
setcookie(‘name’, ‘jason’, time()+100) × ×
setcookie(‘age’, ‘20’, time()+100,’/‘,’lotus.com’)
setcookie(‘birthday’, ‘19901106’, time()+100,’/‘,’blog.lotus.com’) ×
setcookie(‘sex’, ‘male’, time()+100,’/‘,’test.blog.lotus.com’) × × ×

③test.blog.lotus.com域名下设置cookie,测试条件同上

domain参数 lotus.com blog.lotus.com test.blog.lotus.com
setcookie(‘name’, ‘jason’, time()+100) × ×
setcookie(‘age’, ‘20’, time()+100,’/‘,’lotus.com’)
setcookie(‘birthday’, ‘19901106’, time()+100,’/‘,’blog.lotus.com’) ×
setcookie(‘sex’, ‘male’, time()+100,’/‘,’test.blog.lotus.com’) × ×

domain的设置,有两点要注意:
1.在setcookie中省略domain参数,那么domain默认为当前域名。
2.domain参数可以设置父域名以及自身,但不能设置其它域名,包括子域名,否则cookie不起作用。
那么cookie的作用域:
cookie的作用域是domain本身以及domain下的所有子域名。

轻轻的我走了,正如我轻轻的来