基于Http的无状态问题,咱们在浏览网页并登录某一个网点进行一次会话操做时,浏览器并不能知道是哪一个客户端访问请求,传统的解决方法是在地址栏中添加url参数向下一个页面传送用户信息,可是这样多个参数传递比较麻烦,并且经过get方式传递url请求参数并不安全,容易被抓包形成信息安全问题。而对应这种问题,咱们通常采用Cookie和Session来更好地解决Http网络传输用户信息无状态的问题。git
传统方式传递url参数示例代码以上传GitHub地址,这里就不过多解释:github
https://github.com/devyf/JavaWorkSpace/tree/master/Cookie_Session_0201web
Cookie是一个保存在客户端的简单的文本文件,它保存了该客户访问这个Web文档时的信息,至关于一个凭证。跨域
浏览器第一次访问Web服务器时,会把自身的参数信息传递给服务器,服务器这时会建立一个Cookie用来保存浏览器发送过来的客户参数信息,封装在Cookie里面,并将封装好该浏览器客户信息的Cookie返回给浏览器,表示服务器已经确认收到你的请求了,浏览器确认收到服务器给到的带有本地参数信息的Cookie以后,在下一次发送访问请求时,只须要传送以前对应的Cookie便可。Cookie内部储存值也是以key,value键值对的形式存储。浏览器
对于Cookie在浏览器的保存用户信息以下,Set-Cookie在保存对应的浏览器信息,第二次访问的时候能够看到请求中已经包含了Cookie信息,Cookie中保存了客户端用户名信息。安全
① 建立一个Cookie,并设置name,value来保存信息,同时返回给response对象,在下一个页面无需传递url参数信息;服务器
② 在展现页面(下一个须要获取参数页面)经过请求request对象拿到Cookies序列,找到对应的cookie,取出value;cookie
在实际项目过程当中使用Cookie来存储中文url参数可能会遇到乱码问题,这时须要咱们先对Cookie存储的中文字符进行编码,取用的时候再以相同的编码进行解码;网络
Tomcat7中不支持中文,Tomcat8已经能够支持,不用再编码、解码:session
编码:
解码:
修改Cookie中存储的值有两种方式:
第一种方式:
拿到原来的Cookie,设置它的value,使用cookie.setValue(“stringValue”);
第二种方式:
建立一个新的Cookie,使用修改键值对的形式,给原来相同的name的value赋值新的newValue值,
Cookie从建立Cookie对象时就在浏览器的请求头中产生,直到关闭浏览器页面后消失,同时咱们也能够本身去设置Cookie的存在时间。
方法:cookie.setMaxAge(int second);
例如:cookie.setMaxAge(60 * 60 * 24 * 7); //一周
其中正数表明多少秒,为0表明删除该Cookie,负数表明关闭浏览器。
/cookie/email 在这个路径下保存的cookie;
/cookie2/list 这个路径不能拿到上层的cookie信息;
/cookie/show 这个路径能够拿到上层(/cookie/email)的cookie信息
cookie默认只存在当前路径的位置中
解决上述问题能够在/cookie/email的Servlet中设置Cookie的Path路径为/,表示路径能够为任何路径都可以访问:
如在ListServlet中改变了它的请求url地址,则在对应的/cookie2/list中不能获取cookie中保存的用户参数信息,而其它页面不受影响:
页面参数获取以下:
在设置了cookie的Path为”/”以后,对应参数信息就能够获取了:
就咱们使用百度的时候(登陆一次,在全部的地方均可以使用):
news.baidu.com
doc.baidu.com
Music.baidu.com
跨域对二级域名跨域的方式
实现代码:cookie.setDomain(".baidu.com")
优势:
Cookie解决了Web浏览器之间无状态(客户端数据不能共享)的问题,能够自由设置保存的时长;
缺点:
存在于客户端浏览器,F12能够查看用户信息,不安全;
Cookie大小有限制,限制在4KB之内;
一台服务器在一个客户端最多能保存20个Cookie;
一个浏览器最多能够保存300个Cookie;
Cookie不能操做对象;
定义:
在计算机中,尤为是在网络应用中,Session称为“会话控制”。Session对象存储特定用户会话所需的属性及配置信息。当用户在应用程序的Web页之间跳转时,存储在Session对象中的变量将不会丢失,而是在整个用户会话中一直存在下去。
浏览器在第一次向服务器发送请求时会携带用户名和密码等参数信息传送给服务器端,这时服务器会返回一个jsessionId(保存在Cookie中)给浏览器,下一次浏览器再次访问服务器的时候,就可使用这个jsessionId去服务器端拿到对应的session中的数据。若是找到对应的session就取这个session中的Object对象,没有就建立一个session。
理解Session:
① Session是把数据保存到服务器端;
② Session的底层依然是使用Cookie,创建在Cookie存储的基础上来存用户信息
① 从前台request请求对象中获取HttpSession对象,用来存储用户信息;
HttpSession session = req.getSession();
若是有session,那么直接拿到session
若是没有session,建立一个session,再拿到这个session
HttpSession session = req.getSession(boolean value);
value:true -> 若是有直接拿,若是没有建立一个
value:false ->若是有直接拿,若是没有返回null
② 下层页面Servelet获取前面建立的Session以后,从以前的Session获取以前传入的对应key取出的Object值;
使用session.removeAttribute(String name)能够删除存储在Session对象中的数据,根据对应的key删除Session中的一条记录,对应前一个Servlet页面删除,后一个页面就不能取出对应的值了,返回null;
对应页面:
除此以外,还可使用session.invalidate()方法销毁整个Session对象;
存入对象:
取出对象:
展现效果:
Session从建立Session对象时就在浏览器中产生,直到关闭浏览器页面后消失。
Session有超时时间,默认为30分钟,从咱们没有操做页面开始计算,30分钟后Session中存储的对象会失效。
设置Session的超时失效时间:
① 自定义Session的超时时间,可使用session.setMaxInactiveInterval(Integer interval)方法;
② 咱们通常比较经常使用的方式会在web.xml中进行配置Session的过时时间(单位分钟);
注意:若是设置为负数,会直接关闭浏览器;
重写URL
http://localhost/session/single;jsessionid=372EC71FF0939E7C74B533B071714C5E
resp.encodeURL("路径") -->资源重写解决这个问题
工做中咱们有可能会作上传的功能。上传的时候颇有可能咱们会使用flash组件。
Flash组件有一个问题:session丢失,这个时候就须要将jsessionid手动进行传递提交
注意:
① 不少网站/系统登录就是使用session;
② Session有一个问题:因此内容都保存服务器内存里面,服务器内存有很大负担,慎用。
优势:
Session把信息存储在服务器中,经过Cookie向浏览器请求头信息中暴露一个jSessionId,底层经过Cookie来存储jSessionId;
由于没有暴露用户信息,相对Cookie安全性更高;
Session能够存储Object对象,通常用于存储用户登录信息;
缺点:
Session是存储在服务器中,若是过多存入Session对象,会形成服务器内存压力过大;
在某些禁用Cookie的场景使用较为麻烦。