浏览器对象存储数据详解
前言
随着需求的发展,浏览器的功能正变的越来越强大,在本地存储数据可以极大的方便人们进行各种操作,如localStroage/sessionStroage等,下面我就记录在项目中碰到然后进行处理的方式,在以后如果有碰到相关或者有更深的理解,会进行补充。
Cookie
Cookie技术是客户端的解决方案,Cookie就是由服务器发给客户端的特殊信息,而这些信息以文本文件的方式存放在客户端,然后客户端每次向服务器发送请求的时候都会带上这些特殊的信息。因为HTTP是无状态的协议,因此当你下次访问时,为提高用户体验如不需要重新登陆,记录你的购物方式等,Cookie就会记录你的状态以帮助实现这些功能。
注意: cookie存在不可跨域名性。
document.cookie 获得一个字符串,该字符串包含所有的Cookie,每条cookie以分号分隔(即, key=value
键值对)。更详细的我们可以参考MDN介绍
封装的增删改查Cookie方法:
/* * 设置cookie / 如果键一样则进行覆盖(改) * @param name 键 * @param value 值 * @param delay 有效期(单位小时,缺省6小时) */ function setCookie(name, value, delay) { let exp = new Date(); exp.setTime(exp.getTime() + ( !!delay ? delay : 6 ) * 3600 * 1000 ) ; document.cookie = name + "=" + escape(value) + "; expires=" + exp.toGMTString(); } /* * 获取cookie * @param name * @return {*} */ function getCookie(name) { let ret = new RegExp(("(^| )"+name+"=([^;]*)(;|$)")); if(arr=document.cookie.match(reg)) return unescape(arr[2]); else return null; } /* * 删除cookie * @param name */ function delCookie(name) { let exp = new Date(); exp.setTime(exp.getTime() - 3); //设置为超时 let cval = getCookie(name); //获取值 if ( cval != null ) { document.cookie = name + "=" + cval + ";expires=" + exp.toGMTString(); } }
---------20180324 补充 ----------------
来个概念 :同源策略,它是由Netscape提出的一个著名的安全策略。同源是指,域名,协议,端口相同。
先说明下我碰到的情况,项目有两个端,一个医生端,一个病人端,二者的域名一样,而端口不一样。在登录的时候保存登录信息到cookie中(使用如上setCookie方法,目的是利用时效性),cookie的键名称是一样的,导致的问题是同一个浏览器同时登录两个端,后面登录的cookie会把前面登录的cookie覆盖了,然后导致数据请求接口出错了。当时我是凌乱的,因为cookie是遵循同源策略的,怎么会不同端口的cookie会被覆盖或者获取到呢? 经过我的排查,我觉的原因①我使用的是document.cookie,参考MDN我发现 ;domain=domain 部分有这么一句话: 如果没有定义,默认为当前文档位置的路径的域名部分。因此两个端的cookie是同一个域名,具体我们也可以通过“开发者工具”->"Application" -> "Cookie" ,发现Domain 字段都是127.0.0.1(在改了cookie键名称的情况下,有两个,否则覆盖)。②受到阮一峰老师文章的启发,我们可以通过设置document.cookie=xx 可以实现二级域名不同来实现共享Cookie ,我感觉原理是一样的。因此当我把cookie的键名称改为不同时,问题就解决了。
So最后结论是 cookie是遵循同源策略的,只是我们主动在浏览器端进行设置时使用document.cookie是会导致域名相同不同端口cookie是可以共享的。查看资料室发现阮一峰老师的一篇好文章 浏览器同源政策及其规避方法 。
localStorage和sessionStorage
在HTML 5 最开始时,本地存储有两种方式:一种是web Storage,另一种是web SQL。由于web SQL的实现是基于SQLite,它更倾向于DataBase方向,且W3C官方在2011年11月宣布不在维护web SQL规范,故其API接口目前已经不属于HTML 5的范畴。因此,目前我们常讲的HTML 5本地存储,多指的是web Storage。二者的存放数据大小为一般为5MB
二者的区别在于sessionStorage仅在当前会话有效,关闭页面或浏览器后清除,而localStorage永久有效,即使关闭了浏览器依然存在。
作用域不同: 不同浏览器无法共享localStorage或sessionStorage中的信息。相同浏览器的不同页面间可以共享相同的 localStorage(页面属于相同域名和端口),但是不同页面或标签页间无法共享sessionStorage的信息。需要注意的是,页面及标签页仅指顶级窗口,如果一个标签页包含多个iframe标签且他们属于同源页面,那么他们之间是可以共享sessionStorage的。
封装方法如下;
const SALT = '__admin__' export default { local: { get(key) { let strValue = localStorage.getItem(SALT + key) return JSON.parse(strValue) }, set(key, jsonValue) { var strValue = JSON.stringify(jsonValue) localStorage.setItem(SALT + key, strValue) }, remove(key) { localStorage.removeItem(SALT + key) }, removeAll() { localStorage.clear() } }, session: { get(key) { let strValue = sessionStorage.getItem(SALT + key) return JSON.parse(strValue) }, set(key, jsonValue) { var strValue = JSON.stringify(jsonValue) sessionStorage.setItem(SALT + key, strValue) }, remove(key) { sessionStorage.removeItem(SALT + key) }, removeAll() { sessionStorage.clear() } } }
浏览器缓存
浏览器缓存的优点: (1)减少网络宽带消耗 (2)降低服务器压力(3)减少网络延迟,加快页面打开速度。
1. 浏览器缓存的类别
强缓存:用户发送的请求,直接从客户端缓存中获取,不发送请求到服务器,不与服务器发生交互行为。
协商缓存: 用户发送的请求,发送到服务器后,由服务器判定是否从缓存中获取资源。
缓存的真面目: 我们以chrome为例, 输入chrome://cache,里面有很多的文件路径,可以点击进去,可以看到缓存的内容和表现形式。
2.浏览器缓存涉及到的HTTP信息
如expires/Cache-Control/Last-modified/Etag等字段,参考“参考文献”。有写的非常详细的内容
3.用户行为导致的浏览器缓存行为
4.原理
参考下文献,讲解的非常详细。
5.补充
jQuery中的$.ajax方法中,有cache参数/ifModified参数与缓存有关。
cache参数: 默认情况下,请求总是会被发出去,但浏览器有可能从它的缓存中调取数据。要禁止使用缓存结果,可以设置cache为false。
描述: (默认true, dataType为script和jsonp时默认为false) jQuery 1.2新功能,设置为false将不缓存此页面。
ifModified参数: (默认false) 仅在服务器数据改变时获取新数据。使用HTTP包 Last-Modified头信息判断。在jQuery 1.4中,它也会检查服务器指定的"etag"来确定数据没有被修改过。
更详细内容,可参考jQuery API 中文文档。
参考文献
https://www.cnblogs.com/shixiaomiao1122/p/7591556.html 彻底理解浏览器缓存机制
https://segmentfault.com/a/1190000011212929#articleHeader5 浏览器缓存-前端随笔