javascript - 当您在 Chrome 上删除数据库时,indexedDB 不会重置版本——错误或用户错误?

标签 javascript google-chrome firefox indexeddb

如果我将 buggy 设置为 true,以下代码将在 Chrome 35(但不是 Firefox 29)中抛出错误。

因为我是 indexedDB 的新手,所以我想问一下这是否应该起作用。如果我删除数据库并使用 version=1 再次打开它,是否应该调用我的 onupgradeneeded 回调?

<html>
  <head>
    <script type="text/javascript">
      var i = 1000;
      var buggy = true;
      function open() {
        var version = buggy ? 1 : 1001 - i;
        var request = indexedDB.open("test", version);
        var upgraded = false;
        request.onupgradeneeded = function() {
          upgraded = true;
          console.log("upgraded ok");
        }
        request.onsuccess = function() {
          if (!upgraded) {
            throw "Not upgraded";
          }
          console.log("open ok");
          if (--i != 0) { obliterate(); }
        }
        request.onerror = function() {
          throw "Error in open";
        }
      }

      function obliterate() {
        var request = indexedDB.deleteDatabase("test");
        request.onsuccess = function() {
          console.log("delete ok");
          open();
        }
        request.onerror = function(event) {
          throw "Error in obliterate.";
        }
      }

      obliterate();
    </script>
  </head>
  <body>
  </body>
</html>

在 Chrome 中,使用 buggy=true,我得到:

delete ok test.html:29
upgraded ok test.html:12
open ok test.html:18
delete ok test.html:29
Uncaught Not upgraded

在 Firefox 中它工作正常。

作为旁注,在 Chrome 和 Firefox 中,这运行得非常慢——大约需要 5-10 秒来创建和删除数据库一次。这是正常的/预期的吗?我做错了什么吗?

最佳答案

这是一个用户错误。

IndexedDB 中的删除在 Firefox 和 Chrome 中都非常快。我没有做过任何测量。但客观地说:在 SyncedDB 的测试套件中我在每个 测试之间删除并创建了一个数据库。目前有 67 个测试,它们的执行时间不到一秒。而数据库的删除和创建绝对不是测试中最耗时的部分。

您偶然发现的是 IndexedDB 工作原理的棘手部分之一。 IndexedDB 有数据库连接 的概念。与您的问题相关的部分是:

  • 您可以通过使用open 函数打开数据库来建立连接。该连接由您通过 open 获取的 IDBDatabase 表示。
  • 只要与数据库的连接处于打开状态,就不能删除数据库。
  • 当尝试删除数据库时,将针对连接到数据库的所有打开的 IDBDatabase 对象触发“versionchange”事件。该事件会将 newVersion 属性设置为 null

问题是您在 open 请求 onsuccess 事件处理程序中调用了您的 obliterate 函数。此时您正试图删除一个您有一个开放连接的数据库。这是有问题的,这就是为什么您的示例代码在 Chrome 中不起作用(Firefox 似乎超时连接并完成删除,尽管有很大的延迟)。

修复方法是在 onsuccess 事件处理程序中为 versionchange 事件附加一个监听器。在行 if (--i != 0) { obliterate(); 之后添加这个:

request.result.onversionchange = function(e) {
    if (e.newVersion === null) { // An attempt is made to delete the db
        e.target.close(); // Manually close our connection to the db
    }
};

插入这个你会看到 Firefox 和 Chrome 都不会很快创建和删除 tests 数据库。

关于javascript - 当您在 Chrome 上删除数据库时,indexedDB 不会重置版本——错误或用户错误?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24111035/

相关文章:

javascript - "Converting"javascript 变量(字符串)值转换为 PHP 变量

javascript - 可以在浏览器中检查 'available memory' 吗?

javascript - Bootstrap Accordion 对于 chrome 和 Mozilla 的不同行为

html - 表格格式问题 Chrome vs IE/FireFox

javascript - Firefox 中全屏 Bootstrap 轮播插件的问题

javascript - $.递延 : How to detect when every promise has been executed

Javascript 在单击时更改 div 内容

javascript - 有什么方法可以在 Chrome DevTools 中重新分配 const 吗?

javascript - Firefox 4.0.1 忽略过期的 HTTP header

javascript - 从 Chrome 扩展程序动态创建 Google 表格?