Closed TokenYangForever closed 6 years ago
try { sessionStorage.setItem('private_test', 1); } catch (e) { //无痕模式 }
* 我们会另外定义一个NameStorage对象,在原生storage失效时使用:
// 隐私模式下面,把临时值存到window.name中去 function NameStorage(type) { this.store = NameStorage[type]; }
Object.assign(NameStorage.prototype, { getItem: function(key) { return this.store[key]; }, setItem: function(key, value) { this.store[key] = value; this._saveNameValue(); }, removeItem: function(key) { delete this.store[key]; this._saveNameValue(); }, clear: function() { this.store = {}; this._saveNameValue(); }, _saveNameValue: function() { var ret = { session: NameStorage.session, local: NameStorage.local }
window.name = JSON.stringify(ret); }
});
* 上面会把所有的local和session数据存储到`window.name`上去,然后在每个页面启动时,调用一下keepName方法,把window.name的数据拿下来放到NameStorage上面。这时候,只需要调用`new NameStorage('local')`来代替localStorage进行操作就行了
function keepName () { if (keepName.done) { return; }
var ret; if (window.name) { try { ret = JSON.parse(window.name); } catch (e) { ret = {}; } } if (!_.isPlainObject(ret)) { ret = {}; } if (!ret.session) { ret.session = {}; } if (!ret.local) { ret.local = {}; } NameStorage.session = ret.session; NameStorage.local = ret.local; keepName.done = true;
}
#### 另外一些补充 * 无痕模式下,localStorage和sessionStorage的报错信息是:`QuotaExceededError`,code为22,这个其实是storage存储空间用完了报的错,就比如当前浏览器storage内存为5mb,你已经存储了5mb的数据后,再进行setItem操作就会报这个错误。 * 所以我猜想无痕模式下,浏览器是把storage的内存先清空,然后再设置最大值为0,这样调用setItem就直接报错了。 * 另外无痕模式下cookie是可以使用的,大概因为cookie是跟服务器有关,而storage是属于浏览器的特性吧。 * 最后还有一种情况,就是无痕模式下打开了某个页面,然后把浏览器关闭再打开,这个时候会打开访问的页面,但是window.name已经丢失了,所以就拿不到以前存储的数据了。这种情况只能页面做容错处理了。
前言
解决方案
// 隐私模式下面,把临时值存到window.name中去 function NameStorage(type) { this.store = NameStorage[type]; }
Object.assign(NameStorage.prototype, { getItem: function(key) { return this.store[key]; }, setItem: function(key, value) { this.store[key] = value; this._saveNameValue(); }, removeItem: function(key) { delete this.store[key]; this._saveNameValue(); }, clear: function() { this.store = {}; this._saveNameValue(); }, _saveNameValue: function() { var ret = { session: NameStorage.session, local: NameStorage.local }
});
function keepName () { if (keepName.done) { return; }
}