会话管理
会话是指某人打开浏览器,访问当前应用中的多个页面,然后关闭浏览器离开应用的这个过程。
cookie
Cookie
是一个客户端会话技术,是由服务器端创建,放在响应头发送到客户端保存,用于存储少量数据,因为存放在客户端中,容易被人编造伪造,不是很安全。一般不用于存储重要信息。它是通过键值对传递信息的。
Cookie
是保存在客户端的数据,所以如果不做设定,默认情况下是跟着客户端一起消失,如果设置
setMaxAge()
,将会以设置的数值为主,时间到了将会自动消失
![](https://img-blog.csdnimg.cn/97b3fc5439324a7e9108a8d215b5fb4b.png)
Cookie
是服务器通知客户端保存键値对的一种技术
客戶端有了
Cookie
后,每次请求都发送给服务器
每个
Cookie
的大小不能超过
4kB
,超过这个限制
cookie
中无法存储该数据
Cookie
应用场景
Cookie
能使站点跟踪特定访问者的访问次数、最后访问时间和访问者进入站点的路径
Cookie
能告诉在线广告商广告被点击的次数,从而可以更精确的投放广告
Cookie
有效期限未到时,
Cookie
能使用户在不键入密码和用户名的情况下进入曾经浏览过的一些
站点
Cookie
能帮助站点统计用户个人资料以实现各种各样的个性化服务
安全性能差,容易信息泄露
基础编程
添加
cookie
Cookie ck1 = new Cookie("username", username); //创建cookie对象,注意cookie中只
能存放字符串,其它数据可以转换为字符串进行存储,默认maxAge为-1,表示采用内存cookie
response.addCookie(ck1); //将cookie发送到客户端
读取
cookie
Cookie[] cks = request.getCookies();//获取当前应用可以访问的所有cookie
String username = null;
for (Cookie ck : cks) { //遍历所有的cookie,根据名称查找对应的存储数据
if ("username".equals(ck.getName())) {
username = ck.getValue();
}
}
Cookie
与
Session
的区别
Session
是保存在服务端的,有一个唯一标识
session.getId()
。在服务端保存
Session
的方法很多,内存、数据库、文件都有。集群的时候也要考虑Session
的转移,在大型的网站,一般会有专门的Session服务器集群,用来保存用户会话,这个时候
Session
信息都是放在内存的,使用一些缓存服务比如Memcached
之类的来放
Session
。
Cookie
作用于每次
HTTP
请求的时候,客户端都会发送相应的
Cookie
信息到服务端。
Cookie
原理
对于
Cookie
的实现原理是基于
HTTP
协议的,其中设计
HTTP
协议中的两个请求头信息分别为:响应头 set-cookie、请求头
cookie
[response.addCookie]
当要发送
Cookie
的时候会有一个响应头
set-cookie
,里面放着数据,当将来浏览器在请求服务器资源的时候,会通过一个cookie
头把
cookie
的数据携带到服务器资源里面来请求
Cookie
限制性
cookie
存储大小一般为
4kB
,存储个数一般
20-53
个,视浏览器的不同。
Cookie
编程基础
void setValue(String newValue) cookie
创建后设置一个新的值。
String getName()
返回
Cookie
的名字。名字和值是关心的两个部分
String getValue()
返回
Cookie
的值
具体的
cookie
可以分为内存
cookie
和文件
cookie
,
Cookie ck=new
Cookie("username","zhangsan")
时默认
maxAge
为
-1
表示内存
cookie
,内存
cookie
在浏览器窗口关
闭后会自动消失;如果需要使用文件
cookie
则需要设置
maxAge
,参数为正整数
void setMaxAge(int expiry)
以秒计算,设置
Cookie
过期时间。注意这个值是
cookie
将要存在的最大时
间,而不是
cookie
现在的存在时间。负值表示当浏览器关闭时,
Cookie
将会被删除。零值则是要删除该
Cookie
int getMaxAge()
返回
Cookie
过期之前的最大时间,以秒计算。
文件
cookie
不受当前窗口是否关闭的影响
void setComment(String purpose)
设置
cookie
中注释。
Cookie
[]
cks
=
request
.
getCookies
();
//
获取当前应用可以访问的所有
cookie
String
username
=
null
;
for
(
Cookie ck
:
cks
) {
//
遍历所有的
cookie
,根据名称查找对应的存储数据
if
(
"username"
.
equals
(
ck
.
getName
())) {
username
=
ck
.
getValue
();
}
}
Cookie ck
=
new
Cookie
(
"name"
,
"wangwu"
);
ck
.
setMaxAge
(
15
*
24
*
60
*
60
);
//
需要存储
15
天,例如
15
天免登录
response
.
addCookie
(
ck
);
String getComment()
返回
cookie
中注释,如果没有注释的话将返回空值
String getDomain()
返回
cookie
中
Cookie
适用的域名。使用
getDomain()
方法可以指示浏览器把
Cookie
返回给同 一域内的其他服务器
,
而通常
Cookie
只返回给与发送它的服务器名字完全相同的服务器。注意
域名必须以点开始,如
.yesky.com
)
void setDomain(String pattern)
设置
cookie
中
Cookie
适用的域名
String getPath()
返回
Cookie
适用的路径。如果不指定路径,
Cookie
将返回给当前页面所在目录及其子目
录下 的所有页面
void setPath(String uri)
指定
Cookie
适用的路径。
其它方法
boolean getSecure()
如果浏览器通过安全协议发送
cookies
将返回
true
值,如果浏览器使用标准协议则
返回
false
值。
int getVersion()
返回
Cookie
所遵从的协议版本。
void setSecure(boolean flag)
指出浏览器使用的安全协议,例如
HTTPS
或
SSL
。
void setVersion(int v)
设置
Cookie
所遵从的协议版本。
Cookie
通讯过程
Cookie
在通讯中会经历
4
个过程:
浏览器发送请求
服务端接收请求,并返回响应,在报文头中包含
set-cookie
的字段
浏览器接收响应后将
Cookie
存储,并在之后的请求中都会带上
cookie
的信息
服务端接收请求,并返回响应。
Cookie
属性
Cookie
的属性有:
key/value
、
Expires
、
Domain
、
path
、
Secure
、
HttpOnly
Key/value
键值对,
cookie
按照键值对的模式存储信息
Expires
过期时间,设置某个时间后,
cookie
会失效
Domain
指定
Cookie
的域名作用域
Path
是
Cookie
生成的路径
Secure
只有在
HTTPS
模式下,服务端才会响应
cookie
信息
HttpOnly
设为
true
后,只能通过
http
访问,不能通过
document.cookie
获取设定为
httponly
的键
值,防止
xss
读取
cookie
maxAge
标准用法
Cookie ck=new Cookie("name","wangwu");
// ck.setMaxAge(15*24*60*60);//
需要存储
15
天,例如
15
天免登录
ck.setMaxAge(0); //
删除
cookie
response.addCookie(ck);
基于语法
cookie.setMaxAge(60)
;
单位为秒。
当
maxAge >0
时
Cookie
将在
maxAge
秒后自动失效
当
maxAge =0
时
Cookie
将立刻删除
Cookie
当
maxAge =-1
时
Cookie
的时间过期后
cookie
依然存在在浏览器上,将存在一段时间或重启浏览器
自动消失。
HttpServletResponse
提供的
Cookie
操作只有一个
addCookie
,如果要修改
Cookie
只能用一个同名的
Cookie
进行覆盖。
客户端发送的
cookie
时,只会提交
name
和
value
属性,其他属性是不可读的。也不会被提交。即服务端无法判断Cookie
是否过期,获取域名信息等。如在服务端通过
cookie.getMaxAge()
获取过期时间,读取 的是一个只读属性,值永远为-1
。
中文问题
在
Cookie
是中不能直接传输中文,如果想要传输中文的话,首先要在发送
Cookie
前先使用
URL
将中文进
行编码,然后将编码后的数据发送到客户端
获取
Cookie
的时候要将获取的数据进行
URL
解码
常见问题
Session
是在服务端保存的一个数据结构,用来跟踪用户的状态,这个数据可以保存在集群、数据
库、文件中 Cookie是客户端保存用户信息的一种机制,用来记录用户的一些信息,也是实现
Session
的一种方 式。
Cookie
运行在客户端,
Session
运行在服务端,对吗?
不完全正确。
Cookie
是运行在客户端,有客户端进行管理;
Session
虽然是运行在服务器端,但是
sessionID
作为一个
Cookie
是存储在客户端的。
浏览器禁止
Cookie
,
Cookie
就不能用了,但
Session
不会受浏览器影响,对吗?
错。浏览器禁止
Cookie
,
Cookie
确实不能用了,
Session
会受浏览器端的影响。很简单的实验,在
登录一个网站后,清空浏览器的
Cookie
和隐私数据,单机后台的连接,就会因为丢失
Cookie
而退
出。当然,有办法通过
URL
传递
Session
。
String
content
=
"
服务器传送的
Cookie"
;
content
=
URLEncoder
.
encode
(
value
,
"UTF-8"
);
Cookie cookie
=
new
Cookie
(
"memo"
,
content
);
cookie
.
setMaxAge
(
1000
);
//
设置
Maximum Age
过期时间
s,
默认是
-1,
关闭浏览器失效
cookie
.
setPath
(
request
.
getContextPath
());
//
设置
cookie
路径为当前项目路径
response
.
addCookie
(
cookie
);
//
添加
cookie
String
val
=
""
;
Cookie
[]
cookies
=
request
.
getCookies
();
//
获取
cookie
数组
if
(
cookies
!=
null
&&
cookies
.
length
>
0
) {
for
(
Cookie cookie
:
cookies
) {
//
遍历数组
if
(
cookie
.
getName
().
equals
(
"memo"
)) {
val
=
cookie
.
getValue
();
val
=
URLDecoder
.
decode
(
rediskt
,
"UTF-8"
);
break
;
}
}
}
浏览器关闭后,
Cookie
和
Session
都消失了,对吗?
错。存储在内存中额
Cookie
确实会随着浏览器的关闭而消失,但存储在硬盘上的不会。更顽固的
是
Flash Cookie
,不过现在很多系统优化软件和新版浏览器都已经支持删除
Flash Cookie
。百度采
用了这样的技术记忆用户:
Session
在浏览器关闭后也不会消失,除非正常退出,代码中使用了显
示的
unset
删除
Session
。否则
Session
可能被回收,也有可能永远残留在系统中。
Session
比
Cookie
更安全吗? 不应该大量使用
Cookie
吗?
错误。
Cookie
确实可能存在一些不安全因素,但和
JavaScript
一样,即使突破前端验证,还有后端
保障安全。一切都还要看设计,尤其是涉及提权的时候,特别需要注意。通常情况下,
Cookie
和
Session
是绑定的,获得
Cookie
就相当于获得了
Session
,客户端把劫持的
Cookie
原封不动地传给
服务器,服务器收到后,原封不动地验证
Session
,若
Session
存在,就实现了
Cookie
和
Session
的
绑定过程。因此,不存在
Session
比
Cookie
更安全这种说法。如果说不安全,也是由于代码不安
全,错误地把用作身份验证的
Cookie
作为权限验证来使用。
Session
是创建在服务器上的,应该少用
Session
而多用
Cookie
,对吗?
错。
Cookie
可以提高用户体验,但会加大网络之间的数据传输量,应尽量在
Cookie
中仅保存必要
的数据。
如果把别人机器上的
Cookie
文件复制到我的电脑上(假设使用相同的浏览器),是不是能够登录别人的
帐号呢?如何防范?
是的。这属于
Cookie
劫持的一种做法。要避免这种情况,需要在
Cookie
中针对
IP
、
UA
等加上特殊
的校验信息,然后和服务器端进行比对。
在
IE
浏览器下登录某网站,换成
Firefox
浏览器是否仍然是未登录状态?使用
IE
登录了腾讯网站后,为什
么使用
Firefox
能保持登录状态?
不同浏览器使用不同的
Cookie
管理机制,无法实现公用
Cookie
。如果使用
IE
登录腾讯网站,使用
Firefox
也能登录,这是由于在安装腾讯
QQ
软件时,你的电脑上同时安装了针对这两个浏览器的插
件,可以识别本地已登录
QQ
号码进而自动登录。本质上,不属于共用
Cookie
的范畴。