我正在为我玩的纸牌游戏deck building application工作。我使用localStorage来保存和检索套牌。它似乎在Chrome中完美运行,但在Firefox中,它的运行方式并不可靠。
在FF中,一开始似乎一切正常,甲板甚至会在重新加载时继续存在。但是,如果我添加第二个套牌并重新加载,它只会找到第一个套牌。如果我删除第一个牌组,它就不会再找到任何东西了。
所有本地存储交互都在scripts / vault.js中,我将在下面重现。我做错了吗?
vault = {};
vault.makeKey = function (s) {
return "deck:" + s;
};
vault.friendlyName = function(s) {
if (s.indexOf("deck:") === 0) {
return s.substring(5);
} else {
return s;
}
};
vault.store = function (deck, name) {
if (!window.localStorage) {
alert("This browser doesn't support local storage. You will be unable to save decks.");
return;
}
var key = vault.makeKey(name);
localStorage.setItem(key, deck.export());
};
vault.retrieve = function (key) {
deck.import(localStorage[key]);
};
vault.getDecks = function () {
var keys = Object.keys(localStorage),
out = [],
i,
k,
name = "";
for (i = 0; i < keys.length; i++) {
k = keys[i];
name = vault.friendlyName(k);
if (name !== k && localStorage[k]) {
out.push({name: name, key: k});
}
}
out.sort(function (a, b) {
return a.name > b.name ? 1 : -1;
});
return out;
};
vault.deleteDeck = function (key) {
localStorage.removeItem(key);
};
基本上,似乎在某些时候localStorage中的密钥被冻结了#39;缺乏更好的术语; localStorage在我操作时会表现正常,但是一旦我刷新页面,它似乎就会恢复到被冻结的状态。
答案 0 :(得分:4)
我遇到过这个问题几次,起初我没有注意到为什么它只是无法读取localStorage,但我认为我找到了解决方案。
localStorage操作都是同步的,不同的浏览器有一些关于它们如何处理它们的怪癖。
在您的情况下,问题似乎是您在DOM准备好之前尝试读取localStorage。我用Firebug尝试了它,我在vault.js文件的开头添加了一个断点并重新加载页面,当代码中断时,我检查dom-tab并找到localStorage属性,它就是 - 存储的完整列表值。当我删除断点并重新加载页面时,一旦页面加载,它们就全部消失了。
这可能是Firefox或其他浏览器中的错误,只是更快地初始化localStorage。
因此,作为您的问题的解决方案:尝试在DOM准备就绪后从localStorage获取密钥。
答案 1 :(得分:3)
虽然这是一篇很老的帖子,但我认为我的发现可能有所帮助。我也遇到了同样的问题,所以我经历了这个帖子,试过这个,这是我注意到的,在firefox中如果你尝试在window.load之前用localstorage做任何事情(甚至是localStorage.getItem),它将删除所有内容它,你什么都没有。所以无论你想做什么设置或得到什么,都要在window.load之后再做。
像这样的东西
$( window ).load(function() {
//do whatever you want to do with localstorage
});
BTW我试图在document.ready之前使用localStorage进行一些操作,然后才失败。
答案 2 :(得分:0)
我一直在玩延迟,注意到一些奇怪的行为。
据我所知,似乎如果你在所有JavaScript完成执行之前触摸localStorage,包括JS执行setTimeout,localStorage对于该pageview将显示为空白。例如:
$(window).load(function () {
console.log("Waiting 10000ms", new Date());
setTimeout(setDeckSelect, 10000);
});
Firebug的控制台:
Waiting 10000ms Date {Thu Dec 13 2012 10:35:48 GMT-0500 (Eastern Standard Time)}
exec.js (line 191)
getDecks Date {Thu Dec 13 2012 10:35:58 GMT-0500 (Eastern Standard Time)}
vault.js (line 23)
>>> localStorage
0 items in Storage
我以为我可能会做些什么,但到目前为止,我的理论都被证明是错误的。不过,我注意到了一件奇怪的事情。无论我等多久,如果我先尝试查看套牌,它都会失败并且本地存储将为空:
>>> vault.getDecks()
[]
>>> localStorage
0 items in Storage
但如果我按相反的顺序做那些......
>>> localStorage
8 items in Storage deck:dfs=
"{"identity":"MakingNews","cards":{}}", deck:ngrngfrn= "{"identity":"BuildingaBetterWorld","cards":{}}", deck:sdfgshsh= "{"identity":"MakingNews","cards":{}}", deck:sdfgdgdfg= "{"identity":"MakingNews","cards":{}}", deck:dfgdfgas= "{"identity":"EngineeringtheFuture","cards":{}}", deck:sdfsga= "{"identity":"MakingNews","cards":{}}", deck:gdgd= "{"identity":"MakingNews","cards":{}}", deck:gfsdfgsdfg= "{"identity":"BuildingaBetterWorld","cards":{}}"
>>> vault.getDecks()
[Object { name= "dfgdfgas", key= "deck:dfgdfgas"}, Object { name= "dfs", key= "deck:dfs"}, Object { name= "gdgd", key= "deck:gdgd"}, Object { name= "gfsdfgsdfg", key= "deck:gfsdfgsdfg"}, Object { name= "ngrngfrn", key= "deck:ngrngfrn"}, Object { name= "sdfgdgdfg", key= "deck:sdfgdgdfg"}, Object { name= "sdfgshsh", key= "deck:sdfgshsh"}, Object { name= "sdfsga", key= "deck:sdfsga"}]
如果我在函数中记录localStorage,它也可以正常工作:
vault.getDecks = function () {
console.log(localStorage);
var keys = Object.keys(localStorage),
out = [],
i,
k,
name = "";
for (i = 0; i < keys.length; i++) {
k = keys[i];
name = vault.friendlyName(k);
if (name !== k && localStorage[k]) {
out.push({name: name, key: k});
}
}
out.sort(function (a, b) {
return a.name > b.name ? 1 : -1;
});
return out;
};
它有效。如果我取消它,但是......
vault.getDecks = function () {
// console.log(localStorage);
void localStorage;
var keys = Object.keys(localStorage),
out = [],
i,
k,
name = "";
for (i = 0; i < keys.length; i++) {
k = keys[i];
name = vault.friendlyName(k);
if (name !== k && localStorage[k]) {
out.push({name: name, key: k});
}
}
out.sort(function (a, b) {
return a.name > b.name ? 1 : -1;
});
return out;
};
它不起作用。如果我删除void关键字并且只将localStorage作为一个语句使用它也不起作用。
我不知道为什么,但是console.log(localstorage)似乎确实解决了这个问题,我可以随时调用localStorage。
真的很奇怪。
编辑:我找到了一个更好的解决方案。调用localStorage的'length'属性也可以。
vault.getDecks = function () {
//Weird hack to make FF load localStorage correctly...
localStorage.length;
var keys = Object.keys(localStorage),
out = [],
i,
k,
name = "";
for (i = 0; i < keys.length; i++) {
k = keys[i];
name = vault.friendlyName(k);
if (name !== k && localStorage[k]) {
out.push({name: name, key: k});
}
}
out.sort(function (a, b) {
return a.name > b.name ? 1 : -1;
});
return out;
};
这有点好,因为它没有记录任何内容......
答案 3 :(得分:0)
在此发布此信息是为了帮助可能正在经历我现在所经历的任何人。
如果使用 Firefox,刷新页面后,您需要关闭并重新打开开发工具才能看到新的 localStorage 项。
当页面刷新时,显示之前存在的 localStorage 项目。如果关闭并重新打开开发工具,您可以看到新的集合。从那时起(直到下一次刷新)所做的任何更改都将实时更新。
绝对一个 Firefox 开发工具错误。
我在这里报告了错误:https://bugzilla.mozilla.org/show_bug.cgi?id=1706710
// 5 分钟后编辑 我现在无法重现它。我不确定,但我认为这可能是由于 Firefox 更新造成的。它在我写完错误报告时更新了。我真的在 Firefox 87 中发现了一个在我更新前 10 分钟在 Firefox 88 中修复的错误吗?!!如果再次发生,将在此处报告。
答案 4 :(得分:-2)
•确保在所有html页面中始终提供localStorage数据: o域(本地上下文)必须相同。 o确保保持&lt;&lt;脚本&gt;&gt;所有Html文件中的标签相同, o(仅限Firefox)确保onPageLoad在所有JavaScript文件中保持相同(在html文件中添加),即确保向PageLoadEvent添加相同的函数。