IndexedDB

新的技术--IndexedDB(下)

IndexedDB进阶使用方法,怎么使用游标获取全部数据,用IndexedDB来实现一个评论框

2018-08-21侠课岛    初级拔高       

前端/前端/客户端存储 8     0     3815

这一章的上半部分,我们介绍了有关 IndexedDB 包括 CRUD、主键、索引等基础的使用方法。在这一部分中我们将继续深入了解 IndexedDB 的进阶内容,并且结合一个实际的小例子来熟悉 IndexedDB 这个技术。

4.3 IndexedDB 进阶使用方法

上面我们介绍了 IndexedDB 基本的 CRUD 操作。不知道各位小伙伴感觉如何,有没有被 API 给吓到呢?当然别担心,相关的类库我们会在之后像大家介绍。但是原生 API 永远是万物之本,我们必须要好好学习,这样之后才会有更大发挥的空间。

由于 IndexedDB 内容复杂功能强大,仅仅是之前的基本用法只能完成很基本的任务。这一小节,我们讲介绍 IndexedDB 的进阶使用方法。

使用游标获取全部数据

在实际的开发中,拉取所有数据用列表展示是非常常见的需求。在 IndexedDB 中,并没有 .length 或者 select(*) 的方法,要获取全部数据需要依靠游标。游标使用,我们可以理解成类似 generator,每一次游标会获取一条数据,当我们使用 continue 的方法时就会继续获取下一条数据,直到最后。

在讲解示例代码前,我们先增加一下对象存储中的数据。现在的 Person 中有五条数据了。

下面我们将对上面的数据进行一个全部的抽取。在使用游标前,我们需要通过 objectStore.openCursor 方法来打开游标,在 onsuccess 事件中进行具体的逻辑操作。最后在事务的 oncomplete 事件中,对结果进行整理和输出。

var open = indexedDB.open('db1', 2)
var db;

open.onsuccess = function(e){
  var db = e.target.result
  var resArr = []
  // 这里开启事务,传入的是一个数组,也就是说我们可以对多个对象存储进行操作
  var trans = db.transaction(['Person'], 'readwrite')
  // 获取具体的对象存储
  var Person = trans.objectStore('Person')
  // 在使用游标前,我们要开启游标
  var cursor  = Person.openCursor()
  // 在游标的 onsuccess 事件中进行具体操作
  cursor.onsuccess = function(e){
    var res = e.target.result
    if(res){
      resArr.push(res.value)
      res.continue()
    }else{
      console.log('数据抽取完毕')
    }
  }

  trans.oncomplete = function(e){
    console.dir(resArr)
  }
}

同样地,我们执行代码来查看效果。在最后的数组中,可以看到全部被抽出的数据。

条件的设置

在上面介绍了全部抽取的方法之后,肯定会有小伙伴想进行范围的检索。IndexedDB 也提供了范围的检索方法,不过与上面不同的是,范围的检索是在索引上进行的。因为检索的部分概念比较多而且略微复杂,所以我们直接上例子来进行讲解。

这一次我们的例子就是查找上面数据中 id 在 2-5 之间的数。那么在建立起事务之后,使用 IDBKeyRange 方法来指定范围,最后在把它放到索引的游标上即可。

var open = indexedDB.open('db1', 2)
var db;

open.onsuccess = function(e){
  var db = e.target.result
  var resArr = []
  // 这里开启事务,传入的是一个数组,也就是说我们可以对多个对象存储进行操作
  var trans = db.transaction(['Person'], 'readwrite')
  // 获取具体的对象存储
  var Person = trans.objectStore('Person')
  // 创建 id 游标
  var index = Person.index('id')
  // 设定查询的范围,注意是设置在 index 上的
  var range = IDBKeyRange.bound(2, 5)
  // 在索引的游标上使用范围,查询部分的用法与之前相同
  index.openCursor(range).onsuccess = function(e){
    var res = e.target.result
    if(res){
      resArr.push(res.value)
      res.continue()
    }else{
      console.log('数据抽取完毕')
    }    
  }

  trans.oncomplete = function(e){
    console.dir(resArr)
  }
}

在 Chrome 中输入上述代码,可以看到 id 为 2-5 的数据都被抽取出来了。

IDBKeyRange 除了我们在代码账中使用的 bound 方法外,还有其他几个方法。 编号 方法 说明
1 bound(start, end, boolean, boolean) 设置起始、终止范围,后面两个布尔值分别为起始和终止的开闭区间。默认为闭区间,即 false。
2 upperBound(end, boolean) 设置一个终止范围,布尔值设置开闭区间。举个例子,upperBound(5) 即为所有小于 5 的值。
3 lowerBound(start, boolean) 设置一个起始范围,布尔值设置开闭区间。举个例子,lowerBound(5) 即为所有大于 5 的值。
4 only(value) 查询指定的值。 only(5) 即查询所有为 5 的值。
5 includes(key) 检查所查询的值是否在查询的范围内。一般配合 bound 一起使用。

至此,对于 IndexedDB 的常用方法以及功能就介绍到这里。更多更详细的使用方法,我们可以参考 MDN 上有关 IndexedDB 的文档。

4.4 练手小例子——评论框

作为这一章的练手例子,我们打算使用 IndexedDB 来实现一个评论框。照例,我们来看一下流程。

那么根据上面的流程,我们需要实现下面几个功能。

  1. 全部数据的拉取以及展示
  2. 新的评论插入的逻辑,以及插入后展示
  3. 搜索结果以及展示逻辑

本教程图文或视频等内容版权归侠课岛所有,任何机构、媒体、网站或个人未经本网协议授权不得转载、转贴或以其他方式复制发布或发表。

评价

8

本课评分:
  •     非常好
难易程度:
  •     适中的
|
教程
粉丝
主页

签到有礼

已签到2天,连续签到7天即可领取7天全站VIP

  • 1
    +2 金币
  • 2
    +3 金币
  • 3
    +5 金币
  • 6
    +7 金币
  • 5
    +6 金币
  • 4
    暖心福利
    自选分类VIP ×1天
  • 7
    惊喜大礼

    自选分类VIP ×3天 +20金币
  • 持续签到 +8 金币

金币可以用来做什么?