我需要在客户端存储一些数据,而这些数据太大而无法将其存储在 cookie 中。LocalStorage 似乎是这样做的完美方式,但问题是我将使用它的网站有一些部分可以在 https 上工作,而其他部分只能在 http 上工作,因为本地存储无法从你用 http 设置的 https 访问数据这似乎不再是一个可行的解决方案。
知道是否有任何解决方案吗?还有其他选择吗?
我需要在客户端存储一些数据,而这些数据太大而无法将其存储在 cookie 中。LocalStorage 似乎是这样做的完美方式,但问题是我将使用它的网站有一些部分可以在 https 上工作,而其他部分只能在 http 上工作,因为本地存储无法从你用 http 设置的 https 访问数据这似乎不再是一个可行的解决方案。
知道是否有任何解决方案吗?还有其他选择吗?
将所有数据存储在一个域上,例如https://my.domain.org/
.
https
协议上,只需使用localStorage.setItem('key', 'value')
来保存数据。http
协议上,嵌入一个https
框架,并用于postMessage
保存数据:演示: http: //jsfiddle.net/gK7ce/4/(帮助页面位于http://jsfiddle.net/gK7ce/3/)。
// Script at https://my.domain.org/postMessage
window.addEventListener('message', function(event) {
// Domain restriction (to not leak variables to any page..)
if (event.origin == 'http://my.domain.org' ||
event.origin == 'https://my.domain.org') {
var data = JSON.parse(event.data);
if ('setItem' in data) {
localStorage.setItem(data.setItem, data.value);
} else if ('getItem' in data) {
var gotItem = localStorage.getItem(data.getItem);
// See below
event.source.postMessage(
'#localStorage#' + data.identifier +
(gotItem === null ? 'null#' : '#' + gotItem),
event.origin
);
} else if ('removeItem' in data) {
localStorage.removeItem(data.removeItem);
}
}
}, false);
在 http(s) 页面上,可以按如下方式嵌入框架(替换https://my.mydomain.com
为实际 URL。请注意,您可以简单地获取对框架的引用,并使用src
属性):
<iframe name="myPostMessage" src="https://my.domain.org/postMessage" style="display:none;"></iframe>
// Example: Set the data
function LSsetItem(key, value) {
var obj = {
setItem: key,
value: value
};
frames['myPostMessage'].postMessage(JSON.stringify(obj), 'https://my.domain.com');
}
LSsetItem('key', 'value');
请注意,该方法是异步的,因为postMessage
. 该getItem
方法的实现必须以不同的方式实现:
var callbacks = {};
window.addEventListener('message', function(event) {
if (event.source === frames['myPostMessage']) {
var data = /^#localStorage#(\d+)(null)?#([\S\s]*)/.exec(event.data);
if (data) {
if (callbacks[data[1]]) {
// null and "null" are distinguished by our pattern
callbacks[data[1]](data[2] === 'null' ? null : data[3]);
}
delete callbacks[data[1]];
}
}
}, false);
function LSgetItem(key, callback) {
var identifier = new Date().getTime();
var obj = {
identifier: identifier,
getItem: key
};
callbacks[identifier] = callback;
frames['myPostMessage'].postMessage(JSON.stringify(obj), 'https://my.domain.com');
}
// Usage:
LSgetItem('key', function(value) {
console.log('Value: ' + value);
});
请注意,每个回调都存储在哈希中。每条消息还包含一个标识符,以便接收消息的窗口调用正确的相应回调。
为了完整起见,LSremoveItem
方法如下:
function LSremoveItem(key) {
var obj = {
removeItem: key
};
frames['myPostMessage'].postMessage(JSON.stringify(obj), 'https://my.domain.com');
}