21.HttpSession详解
【基本了解】
1.Session 表示会话,不止是所在javaweb中存在,只要是web开发,都有该机制
2.在java中对应的类型是:java.servlet.http.HttpSession,简称session会话
3.Cookie可以将会话状态保存在客户端,HttpSession可以将会话状态保存在服务器端。
4.HttpSession对象是一个会话级别的对象,一次会话对应一个HttpSession对象
5.一次会话:
"初步理解":用户打开浏览器,在浏览器上发送多次请求,直到最终关闭浏览器,表示一次完整的会话。
6.在会话进行过程中,web服务器一直为当前用户维护着一个会话对象/HttpSession
7.在web容器中,web容器维护了大量的HttpSession对象,web容器中有一个"session列表"
【重点】
为什么当前会话中的每一次请求可以获取到属于自己的会话对象?(Session的实现原理)
- 打开浏览器,在浏览器上首次发送请求
- 服务器会创建一个HttpSession对象,该对象代表一次会话。
- 服务器同时生成HttpSession对象对应的Cookie对象,并且Cookie对象的name是JSESSIONID,value是32位长度的字符串
- 服务器将Cookie的value和HttpSessoin对象绑定到session列表中
- 服务器将Cookie完整的发送给浏览器客户端
- 浏览器客户端将Cookie保存在缓存中,只要浏览器不关闭,Cookie不会消失
- 当再次发送请求的时候,会自动提交缓存中的Cookie
- 服务器接收到Cookie,会验证该Cookie的name确实是;JSESSIONID,然后获取该Cookie的value
- 通过Cookie的value去session列表中检索对应的session对象。
8.和HttpSession对象关联的Cookie的name是比较特殊的,在java中叫做:jsessionid
9.浏览器禁用cookie会出现的问题:
- 浏览器禁用Cookie,浏览器缓存中不再保存Cookie
- 导致在同一个会话中,浏览器无法获取到对应的会话对象
- 禁用Cookie之后,每一次获取的会话对象都是新的。
浏览器禁用Cookie之后,若还想拿到Session对象,必须使用URL重写机制:
http://localhost:8080/prj_servlet_15_war_exploded/acessMyselfSession;jsessionid=(Cookie的value字符串)
重写URL会给编程带来难度/复杂度,所以一般web站点不建议禁用Cookie。
10.浏览器关闭之后,服务器端对应的session对象会销毁吗。
- 浏览器关闭之后,服务器不会销毁session对象
- 因为B/S架构的系统基于HTTP协议,而HTTP协议是一种无连接/无状态的协议
- 什么是无连接/无状态?
* 请求瞬间浏览器和服务器之间的通道时打开的,请求响应结束后,通道关闭
* 这样做的目的是降低服务器的压力。
11.session对象在什么时候被销毁?
- web系统中引用了session超时的概念。
- 当很长一段时间(时间在xml中进行配置)没有用户再访问该session对象,此时session对象超时,web服务器会自动回收session对象
<session-config>
<session-timeout>120</session-timeout> //默认是30分钟
</session-config>
12.一次会话:
- 多数情况下看为:用户打开浏览器,在浏览器上发送多次请求,直到最终关闭浏览器,表示一次完整的会话。
- 本质上是:从session对象的创建,到最终sessoin对象超时之后被销毁。
13.HttpSession接口中的常用方法:
- void setAttribute(String name,Object value)
- Object getAttribute(String name)
- void removeAttribute(String name)
- void invalidate()
14.ServletContext、HttpSession、HttpServletRequest接口的对比
14.1 以上都是范围对象
ServletContext application; 是应用范围
HttpSession session; 是会话范围
HttpServletRequest request; 是请求范围
14.2 三个范围的排序:
appliacation>session>request
14.3
application完成跨会话共享数据、
session完成跨请求共享数据,但是这些请求必须在同一个会话当中。
request完成跨servlet共享数据,但是这些Servlet必须在同一个请求当中【转发】
14.4 使用原则:由小到大尝试。
例如:登录成功之后,已经登陆的状态需要保存起来,可以将登陆成功的这个状态保存到session对象中。
登陆成功状态不能保存到request范围中,因为一次请求对应一个新的request对象。
登陆成功状态也不能保存到appliacatoin范围中,因为登陆成功状态是属于会话级别的,不能所有的用户共享。
15.补充HttpServletRequest中的方法
- HttpSession session = request.getSessoin(); 获取session对象,若没有获取到session对象,则新建session对象
- HttpSession session = request.getSessoin(true); 获取session对象,若没有获取到session对象,则新建session对象
- HttpSession session = request.getSessoin(false);获取session对象,若没有获取到session对象,则返回null
16.会话对象记录会话状态
1.登陆
2.登陆后将此"已登陆"状态保存
3.实现"显示员工列表"功能
4.当点击"显示员工列表"功能的时候,验证用户是否已经登录,已登录显示,没有登录跳转到登录页面。
5.推出系统