菜单

前端的数据库:IndexedDB入门

2019年10月11日 - 前端知识
前端的数据库:IndexedDB入门

后面一个的数据库:IndexedDB入门

2014/12/27 · 未分类 · IndexedDB

本文由 伯乐在线 –
cucr
翻译,黄利民
校稿。未经许可,禁绝转发!
西班牙语出处:www.codemag.com。迎接参预翻译组。

应用程序供给多少。对超越八分之四Web应用程序来讲,数据在劳务器端组织和管制,顾客端通过互联网乞求获取。随着浏览器变得越发有能力,由此可挑选在浏览器存储和垄断应用程序数据。

本文向您介绍名称叫IndexedDB的浏览器端文书档案数据库。使用lndexedDB,你能够通过惯于在劳动器端数据库差非常少一样的点子成立、读取、更新和删除一大波的记录。请使用本文中可专门的学业的代码版本去体验,完整的源代码能够通过GitHub库找到。

读到本课程的末梢时,你将熟练IndexedDB的基本概念以致如何实现叁个应用IndexedDB实践总体的CRUD操作的模块化JavaScript应用程序。让大家有些亲昵IndexedDB并最初吧。

什么是IndexedDB

平日的话,有三种区别类型的数据库:关系型和文书档案型(也叫做NoSQL或对象)。关周详据库如SQL
Server,MySQL,Oracle的多寡存款和储蓄在表中。文书档案数据库如MongoDB,CouchDB,Redis将数据集作为个人对象存款和储蓄。IndexedDB是多少个文书档案数据库,它在一丝一毫内停放浏览器中的一个沙盒情状中(强制依据(浏览器)同源攻略)。图1展现了IndexedDB的数码,体现了数据库的组织

图片 1

图1:开荒者工具查看八个object
store

全套的IndexedDB API请参照他事他说加以考察完整文书档案

深深深入分析HTML5中的IndexedDB索引数据库,html5indexeddb

那篇小说重要介绍了尖锐分析HTML5中的IndexedDB索引数据库,满含事务锁等基本成效的相关应用示例,需求的恋人能够参谋下

介绍 IndexedDB是HTML5 WEB数据库,允许HTML5
WEB应用在顾客浏览器端存款和储蓄数据。对于利用来讲IndexedDB非常有力、有用,能够在顾客端的chrome,IE,Firefox等WEB浏览器中寄放多量数目,上边简介一下IndexedDB的基本概念。
 
什么是IndexedDB IndexedDB,HTML5新的数据存储,能够在客商端存款和储蓄、操作数据,能够使利用加载地越来越快,越来越好地响应。它分裂于关系型数据库,具有数据表、记录。它影响着大家规划和创建应用程序的艺术。IndexedDB
创造有数据类型和省略的JavaScript漫长对象的object,各个object能够有目录,使其立见成效地询问和遍历整个集结。本文为你提供了什么样在Web应用程序中应用IndexedDB的忠实事例。
 
开始 大家需求在实行前包蕴下前边置代码

JavaScript
Code复制内容到剪贴板

  1. var indexedDB = window.indexedDB || window.mozIndexedDB || window.webkitIndexedDB || window.msIndexedDB;
      
  2.     
  3. //prefixes of window.IDB objects   
  4. var IDBTransaction = window.IDBTransaction || window.webkitIDBTransaction || window.msIDBTransaction;
      
  5. var IDBKeyRange = window.IDBKeyRange || window.webkitIDBKeyRange || window.msIDBKeyRange
      
  6.     
  7. if (!indexedDB) {   
  8. alert(“Your browser doesn’t support a stable version of IndexedDB.”)
      
  9. }  

 
打开IndexedDB 在创设数据库以前,大家首先必要为数据库创建数量,要是大家有如下的客商新闻:

JavaScript
Code复制内容到剪贴板

  1. var userData = [   
  2. { id: “1”, name: “Tapas”, age: 33, email: “[email protected]” },
      
  3. { id: “2”, name: “Bidulata”, age: 55, email: “[email protected]” }
      
  4. ];  

近日大家须要用open()方法展开我们的数据库:

JavaScript
Code复制内容到剪贴板

  1. var db;   
  2. var request = indexedDB.open(“databaseName”, 1);   
  3.     
  4. request.onerror = function(e) {   
  5. console.log(“error: “, e);   
  6. };   
  7.     
  8. request.onsuccess = function(e) {   
  9. db = request.result;   
  10. console.log(“success: “+ db);   
  11. };   
  12. request.onupgradeneeded = function(e) {   
  13.     
  14. }  

如上所示,大家已经开荒了名字为”databaseName”,钦定版本号的数据库,open()方法有七个参数:
1.率先个参数是数据库名称,它会检查测验名为”databaseName”的数据库是或不是业已存在,倘若存在则展开它,不然创设新的数据库。
2.次之个参数是数据库的本子,用于客商更新数据库结构。
 
onSuccess处理 发生成功事件时“onSuccess”被触发,假诺具备成功的伸手都在这管理,大家得以经过赋值给db变量保存要求的结果供以往使用。
 
onerror的管理程序 发出错误事件时“onerror”被触发,如若张开数据库的经过中败诉。
 
Onupgradeneeded管理程序 尽管你想翻新数据库(创制,删除或涂改数据库),那么您不可能不贯彻onupgradeneeded管理程序,令你能够在数据库中做别的更改。
在“onupgradeneeded”管理程序中是足以改造数据库的构造的独一地方。
 
创设和增多数据到表:
IndexedDB使用对象存储来囤积数据,实际不是由此表。
每当二个值存款和储蓄在指标存款和储蓄中,它与三个键相关联。
它同意大家创造的此外对象存款和储蓄索引。
索引允许大家访谈存储在对象存储中的值。
上边包车型客车代码展现了怎么着创制对象存款和储蓄并插入预先策动好的数目:

JavaScript
Code复制内容到剪贴板

  1. request.onupgradeneeded = function(event) {   
  2. var objectStore = event.target.result.createObjectStore(“users”, {keyPath: “id”});
      
  3. for (var i in userData) {   
  4. objectStore.add(userData[i]);    
  5. }   
  6. }  

小编们运用createObjectStore()方法创立三个指标存储。 此方法接受五个参数:

JavaScript
Code复制内容到剪贴板

  1. function Add() {   
  2. var request = db.transaction([“users”], “readwrite”).objectStore(“users”)
      
  3. .add({ id: “3”, name: “Gautam”, age: 30, email: “[email protected]” });
      
  4.     
  5. request.onsuccess = function(e) {   
  6. alert(“Gautam has been added to the database.”);   
  7. };   
  8.     
  9. request.onerror = function(e) {   
  10. alert(“Unable to add the information.”);    
  11. }   
  12.     
  13. }  

事先大家在数据库中做任何的CRUD操作(读,写,修改),必得选用专业。
该transaction()方法是用来钦点我们想要实行事务管理的目的存款和储蓄。
transaction()方法接受3个参数(第四个和第四个是可选的)。
第三个是我们要管理的指标存储的列表,第一个钦定我们是还是不是要只读/读写,第多个是本子变化。
 
从表中读取数据 get()方法用于从指标存储中找找数据。
大家事先早就设置对象的id作为的keyPath,所以get()方法将寻觅具有同样id值的目的。
上边包车型客车代码将回到大家命名称为“Bidulata”的靶子:

JavaScript
Code复制内容到剪贴板

  1. function Read() {   
  2. var objectStore = db.transaction([“users”]).objectStore(“users”);
      
  3. var request = objectStore.get(“2”);   
  4. request.onerror = function(event) {   
  5. alert(“Unable to retrieve data from database!”);   
  6. };   
  7. request.onsuccess = function(event) {    
  8. if(request.result) {   
  9. alert(“Name: ” + request.result.name + “, Age: ” + request.result.age + “, Email: ” + request.result.email);
      
  10. } else {   
  11. alert(“Bidulata couldn’t be found in your database!”);    
  12. }   
  13. };   
  14. }  

 
从表中读取全体数据
上边包车型客车点子搜索表中的全部数据。
这里大家选取游标来搜索对象存款和储蓄中的全部数据:

JavaScript
Code复制内容到剪贴板

  1. function ReadAll() {   
  2. var objectStore = db.transaction(“users”).objectStore(“users”); 
      
  3. var req = objectStore.openCursor();   
  4. req.onsuccess = function(event) {   
  5. db.close();   
  6. var res = event.target.result;   
  7. if (res) {   
  8. alert(“Key ” + res.key + ” is ” + res.value.name + “, Age: ” + res.value.age + “, Email: ” + res.value.email);
      
  9. res.continue();   
  10. }   
  11. };   
  12. req.onerror = function (e) {   
  13. console.log(“Error Getting: “, e);   
  14. };    
  15. }  

该openCursor()用于遍历数据库中的八个记录。
在continue()函数中承接读取下一条记下。
删除表中的笔录 上边包车型地铁章程从指标中除去记录。

JavaScript
Code复制内容到剪贴板

  1. function Remove() {    
  2. var request = db.transaction([“users”], “readwrite”).objectStore(“users”).delete(“1”);
      
  3. request.onsuccess = function(event) {   
  4. alert(“Tapas’s entry has been removed from your database.”);   
  5. };   
  6. }  

我们要将对象的keyPath作为参数字传送递给delete()方法。
 
最终代码
上面包车型地铁主意从指标源中删除一条记下:

JavaScript
Code复制内容到剪贴板

  1. <!DOCTYPE html>  
  2. <head>  
  3. <meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″ />  
  4. <title>IndexedDB</title>  
  5. <script type=”text/javascript”>  
  6. var indexedDB = window.indexedDB || window.mozIndexedDB || window.webkitIndexedDB || window.msIndexedDB;
      
  7.     
  8. //prefixes of window.IDB objects   
  9. var IDBTransaction = window.IDBTransaction || window.webkitIDBTransaction || window.msIDBTransaction;
      
  10. var IDBKeyRange = window.IDBKeyRange || window.webkitIDBKeyRange || window.msIDBKeyRange
      
  11.     
  12. if (!indexedDB) {   
  13. alert(“Your browser doesn’t support a stable version of IndexedDB.”)
      
  14. }   
  15. var customerData = [   
  16. { id: “1”, name: “Tapas”, age: 33, email: “[email protected]” },
      
  17. { id: “2”, name: “Bidulata”, age: 55, email: “[email protected]” }
      
  18. ];   
  19. var db;   
  20. var request = indexedDB.open(“newDatabase”, 1);   
  21.     
  22. request.onerror = function(e) {   
  23. console.log(“error: “, e);   
  24. };   
  25.     
  26. request.onsuccess = function(e) {   
  27. db = request.result;   
  28. console.log(“success: “+ db);   
  29. };   
  30.     
  31. request.onupgradeneeded = function(event) {   
  32.     
  33. }   
  34. request.onupgradeneeded = function(event) {   
  35. var objectStore = event.target.result.createObjectStore(“users”, {keyPath: “id”});
      
  36. for (var i in userData) {   
  37. objectStore.add(userData[i]);    
  38. }   
  39. }   
  40. function Add() {   
  41. var request = db.transaction([“users”], “readwrite”)
      
  42. .objectStore(“users”)   
  43. .add({ id: “3”, name: “Gautam”, age: 30, email: “[email protected]” });
      
  44.     
  45. request.onsuccess = function(e) {   
  46. alert(“Gautam has been added to the database.”);   
  47. };   
  48.     
  49. request.onerror = function(e) {   
  50. alert(“Unable to add the information.”);    
  51. }   
  52.     
  53. }   
  54. function Read() {   
  55. var objectStore = db.transaction(“users”).objectStore(“users”);
      
  56. var request = objectStore.get(“2”);   
  57. request.onerror = function(event) {   
  58. alert(“Unable to retrieve data from database!”);   
  59. };   
  60. request.onsuccess = function(event) {    
  61. if(request.result) {   
  62. alert(“Name: ” + request.result.name + “, Age: ” + request.result.age + “, Email: ” + request.result.email);
      
  63. } else {   
  64. alert(“Bidulata couldn’t be found in your database!”);    
  65. }   
  66. };   
  67. }   
  68. function ReadAll() {   
  69. var objectStore = db.transaction(“users”).objectStore(“users”); 
      
  70. var req = objectStore.openCursor();   
  71. req.onsuccess = function(event) {   
  72. db.close();   
  73. var res = event.target.result;   
  74. if (res) {   
  75. alert(“Key ” + res.key + ” is ” + res.value.name + “, Age: ” + res.value.age + “, Email: ” + res.value.email);
      
  76. res.continue();   
  77. }   
  78. };   
  79. req.onerror = function (e) {   
  80. console.log(“Error Getting: “, e);   
  81. };    
  82. }   
  83. function Remove() {    
  84. var request = db.transaction([“users”], “readwrite”).objectStore(“users”).delete(“1”);
      
  85. request.onsuccess = function(event) {   
  86. alert(“Tapas’s entry has been removed from your database.”);   
  87. };   
  88. }   
  89. </script>  
  90. </head>  
  91.     
  92. <body>  
  93. <button onclick=”Add()”>Add record</button>  
  94. <button onclick=”Remove()”>Delete record</button>  
  95. <button onclick=”Read()”>Retrieve single record</button>  
  96. <button onclick=”ReadAll()”>Retrieve all records</button>  
  97. </body>  
  98. </html>  

localStorage是不带lock功效的。那么要落成前端的多中国少年共产党享并且需求lock作用那就供给运用其余本积累方式,举例indexedDB。indededDB使用的是事务处理的建制,那实在正是lock成效。
  做那些测量检验必要先轻松的包装下indexedDB的操作,因为indexedDB的连年相比费心,何况多少个测量试验页面都亟待用到

JavaScript
Code复制内容到剪贴板

  1. //db.js   
  2. //封装事务操作   
  3. IDBDatabase.prototype.doTransaction=function(f){   
  4.   f(this.transaction([“Obj”],”readwrite”).objectStore(“Obj”));   
  5. };   
  6. //连接数据库,成功后调用main函数   
  7. (function(){   
  8.   //张开数据库   
  9.   var cn=indexedDB.open(“TestDB”,1);   
  10.   //创立数量对象   
  11.   cn.onupgradeneeded=function(e){   
  12.     e.target.result.createObjectStore(“Obj”);   
  13.   };   
  14.   //数据库连接成功   
  15.   cn.onsuccess=function(e){   
  16.     main(e.target.result);   
  17.   };   
  18. })();   
  19.   接着是七个测量试验页面   
  20. <script src=”db.js”></script>  
  21. <script>  
  22. //a.html   
  23. function main(e){   
  24.   (function callee(){   
  25.     //开头几个政工   
  26.     e.doTransaction(function(e){   
  27.       e.put(1,”test”); //设置test的值为1   
  28.       e.put(2,”test”); //设置test的值为2   
  29.     });   
  30.     setTimeout(callee);   
  31.   })();   
  32. };   
  33. </script>  
  34. <script src=”db.js”></script>  
  35. <script>  
  36. //b.html   
  37. function main(e){   
  38.   (function callee(){   
  39.     //开头贰个作业   
  40.     e.doTransaction(function(e){   
  41.       //获取test的值   
  42.       e.get(“test”).onsuccess=function(e){   
  43.         console.log(e.target.result);   
  44.       };   
  45.     });   
  46.     setTimeout(callee);   
  47.   })();   
  48. };   
  49. </script>  

把localStorage换来了indexedDB事务管理。可是结果就分裂

图片 2

测量试验的时候b.html中可能不会及时有出口,因为indexedDB正忙着管理a.html东西,b.html事务丢在了专门的学问丢队列中等待。但是无论怎么样,输出结果也不会是1以此值。因为indexedDB的细微管理单位是事情,而不是localStorage这样以表达式为单位。那样假设把lock和unlock之间要求管理的事物放入叁个事情中就可以兑现。其他,浏览器对indexedDB的支撑不及localStorage,所以使用时还得思考浏览器包容。

那篇小说首要介绍了深远剖析HTML5中的IndexedDB索引数据库,满含事务锁等基本功效的连带使…

规划规范

IndexedDB的架构很像在有的盛行的劳务器端NOSQL数据库完结中的设计规范类型。面向对象数据经过object
stores(对象仓库)实行长久化,全部操作基于央求同期在作业限制内试行。事件生命周期令你能够支配数据库的安插,错误通过荒谬冒泡来使用API管理。

对象宾馆

object
store是IndexedDB数据库的底蕴。借使您使用过关周详据库,日常能够将object
store等价于二个多少库表。Object
stores包括二个或多个目录,在store中遵守一对键/值操作,那提供一种高效稳定数据的方法。

当你安排一个object
store,你不可能不为store选取二个键。键在store中能够以“in-line”或“out-of-line”的方法存在。in-line键通过在数额对象上引用path来维系它在object
store的独一性。为了证明那或多或少,想想二个回顾电子邮件地址属性Person对象。您能够配备你的store使用in-line键emailAddress,它能保障store(悠久化对象中的数据)的独一性。别的,out-of-line键通过单独于数据的值识别独一性。在此种状态下,你能够把out-of-line键比作一个子弹头值,它(整数值)在关周密据库中担当记录的主键。

图1显得了职责数据保存在职务的object
store,它利用in-line键。在这里个案例中,键对应于对象的ID值。

传闻事务

分化于一些价值观的关周详据库的完成,每三个对数据库操作是在二个政工的上下文中实践的。事务限制叁回影响叁个或多少个object
stores,你通过传播一个object store名字的数组到创立工作限制的函数来定义。

成立工作的第一个参数是职业格局。当呼吁叁个事务时,必得决定是遵循只读依旧读写格局诉求访谈。事务是财富密集型的,所以假使您无需改造data
store中的数据,你只须要以只读情势对object stores集合进行呼吁访谈。

清单2演示了怎么使用拾壹分的形式开创贰个工作,并在这里片小说的 Implementing
Database-Specific Code
 部分进行了详尽座谈。

基于乞请

直至这里,有三个再三出现的核心,您或者曾经注意到。对数据库的历次操作,描述为通过多个伸手展开数据库,访谈三个object
store,再持续。IndexedDB
API天生是根据央浼的,那也是API异步性情提醒。对于你在数据库实行的每一遍操作,你不可能不首先为这么些操作创造叁个哀求。当呼吁完毕,你能够响应由诉求结果爆发的风波和不当。

正文达成的代码,演示了什么样利用央求打开数据库,创制七个业务,读取object
store的内容,写入object store,清空object store。

开拓数据库的央浼生命周期

IndexedDB使用事件生命周期管理数据库的开发和配备操作。图2示范了一个开采的伸手在束手就禽的条件下发出upgrade
need事件。

图片 3

图2:IndexedDB张开诉求的生命周期

具有与数据库的相互起头于一个展开的乞求。试图张开数据库时,您务必传递三个被呼吁数据库的版本号的整数值。在展开必要时,浏览器相比你传入的用于张开诉求的版本号与实际数据库的版本号。假诺所央求的版本号高于浏览器中当前的版本号(也许今后未有存在的数据库),upgrade
needed事件触发。在uprade
need事件之间,你有空子通过丰富或移除stores,键和索引来垄断(monopoly)object stores。

即使所央求的数据库版本号和浏览器的当下版本号一样,可能晋级进程一呵而就,三个展开的数据库将回到给调用者。

不当冒泡

当然,临时候,乞求恐怕不会按预期实现。IndexedDB
API通过荒谬冒泡效果来帮忙追踪和管制不当。假使叁个一定的伏乞碰着错误,你能够品尝在央求对象上处理错误,恐怕您能够允许错误通过调用栈冒泡向上传递。那一个冒泡性情,使得你没有要求为各种乞求完结特定错误处理操作,而是能够挑选只在三个越来越高档别上增添错误处理,它给你多少个机遇,保持您的错误管理代码简洁。本文中完毕的事例,是在三个高档别管理错误,以便更加细粒度操作发生的另外不当冒泡到通用的错误处理逻辑。

浏览器扶植

可能在付出Web应用程序最重大的标题是:“浏览器是不是帮忙本人想要做的?“就算浏览器对IndexedDB的支撑在继承拉长,选拔率并不是大家所梦想的那样广泛。图3显示了caniuse.com网址的报告,支持IndexedDB的为66%多一丝丝。最新版本的银狐,Chrome,Opera,Safar,iOS
Safari,和Android完全帮忙IndexedDB,Internet
Explorer和HUAWEI部分援助。就算这么些列表的拥护者是高兴的,但它并未有告诉全数有趣的事。

图片 4

图3:浏览器对IndexedDB的扶植,来自caniuse.com

唯有可怜新本子的Safari和iOS Safari
帮忙IndexedDB。据caniuse.com展现,那只占大致0.01%的大地浏览器接纳。IndexedDB不是三个您感到能够道理当然是那样的获得援助的今世Web
API,然则你将连忙会如此以为。

另一种接纳

浏览器协助本地数据库实际不是从IndexedDB才早先落到实处,它是在WebSQL贯彻之后的一种新措施。类似IndexedDB,WebSQL是三个顾客端数据库,但它看作三个关周密据库的达成,使用结构化查询语言(SQL)与数据库通讯。WebSQL的野史充满了曲折,但底线是平素不主流的浏览器商家对WebSQL继续帮忙。

万一WebSQL实际上是叁个吐弃的手艺,为啥还要提它呢?风趣的是,WebSQL在浏览器里得到稳步的支撑。Chrome,
Safari, iOS Safari, and
Android 浏览器都扶助。别的,实际不是那个浏览器的最新版本才提供支撑,大多这一个新式最棒的浏览器以前的版本也可以支撑。好玩的是,假诺您为WebSQL加多帮衬来协助IndexedDB,你猛然意识,多数浏览器商家和本子成为支撑浏览器内置数据库的某种化身。

于是,固然你的应用程序真正须要一个客商端数据库,你想要达到的最高等其他应用恐怕,当IndexedDB不可用时,或然你的应用程序大概看起来供给采用选择WebSQL来支撑客商端数据架构。固然文档数据库和关全面据库处理数据有明显的差别,但借使您有科学的虚幻,就足以行使本地数据库创设二个应用程序。

IndexedDB是或不是切合本身的应用程序?

前天最主要的主题材料:“IndexedDB是不是切合自个儿的应用程序?“像在这里在此以前同样,答案是任其自流的:“视情形而定。“首先当您绸缪在客商端保存数据时,你会思考HTML5当地存款和储蓄。本地存款和储蓄获得大面积浏览器的支撑,有丰富便于使用的API。轻便有其优势,但其瑕疵是无力回天支撑复杂的追寻战略,存款和储蓄大批量的数目,并提供工作帮忙。

IndexedDB是七个数据库。所以,当你想为客户端做出决定,思念你怎样在服务端选拔贰个持久化介质的数据库。你只怕会问本身某些难点来帮助调节客商端数据库是还是不是适合你的应用程序,包罗:

一旦你对当中的此外难题回复了“是的”,很有希望,IndexedDB是你的应用程序的三个很好的候选。

使用IndexedDB

后天,你曾经有机遇熟练了一部分的欧洲经济共同体概念,下一步是始于兑现基于IndexedDB的应用程序。第三个步骤需求统一IndexedDB在区别浏览器的完毕。您能够很轻便地丰富各类商家性子的精选的检查,相同的时间在window对象上把它们设置为官方对象同样的称号。上边包车型大巴清单展现了window.indexedDB,window.IDBTransaction,window.IDBKeyRange的最终结果是何许都被更新,它们被设置为对应的浏览器的一定达成。

JavaScript

window.indexedDB = window.indexedDB || window.mozIndexedDB ||
window.webkitIndexedDB || window.msIndexedDB; window.IDBTransaction =
window.IDBTransaction || window.webkitIDBTransaction ||
window.msIDBTransaction; window.IDBKeyRange = window.IDBKeyRange ||
window.webkitIDBKeyRange || window.msIDBKeyRange;

1
2
3
4
5
6
7
8
9
10
window.indexedDB = window.indexedDB ||
                   window.mozIndexedDB ||
                   window.webkitIndexedDB ||
                   window.msIndexedDB;
window.IDBTransaction = window.IDBTransaction ||
                   window.webkitIDBTransaction ||
                   window.msIDBTransaction;
window.IDBKeyRange = window.IDBKeyRange ||
                   window.webkitIDBKeyRange ||
                   window.msIDBKeyRange;

这段时间,每一个数据库相关的全局对象具有准确的版本,应用程序能够策画使用IndexedDB伊始专门的学业。

利用概述

在本教程中,您将学习怎样创造贰个行使IndexedDB存款和储蓄数据的模块化JavaScript应用程序。为了精通应用程序是哪些做事的,参谋图4,它叙述了职分应用程序处于空白状态。从此处您可认为列表增多新职分。图5出示了录入了多少个职责到系统的画面。图6突显怎么删除二个职务,图7显示了正在编写职责时的应用程序。

图片 5

图4:空白的任务应用程序

图片 6

图5:职务列表

图片 7

图6:删除义务

图片 8

图7:编辑职务
后天你通晓的应用程序的成效,下一步是开首为网址铺设基础。

铺设基础

以那件事例从落到实处那样一个模块开端,它承受从数据库读取数据,插入新的对象,更新现成对象,删除单个对象和提供在二个object
store删除全数指标的选项。那么些例子完毕的代码是通用的多寡访谈代码,您能够在任何object
store上接纳。

本条模块是由此贰个立刻推行函数表明式(IIFE)完结,它利用对象字面量来提供协会。上边包车型地铁代码是模块的摘要,表明了它的为主结构。

JavaScript

(function (window) { ‘use strict’; var db = { /* implementation here
*/ }; window.app = window.app || {}; window.app.db = db; }(window));

1
2
3
4
5
6
7
8
(function (window) {
    ‘use strict’;
    var db = {
        /* implementation here */
    };
    window.app = window.app || {};
    window.app.db = db;
}(window));

用那样的布局,能够使那个应用程序的持有逻辑封装在三个名称叫app的单对象上。另外,数据库相关的代码在一个誉为db的app子对象上。

本条模块的代码应用IIFE,通过传递window对象来保管模块的贴切范围。使用use
strict确定保障这几个函数的代码函数是遵照(javascript严俊形式)严峻编写翻译法则。db对象作为与数据库交互的持有函数的显要容器。最终,window对象检查app的实例是不是留存,假诺存在,模块使用当前实例,要是一纸空文,则开创三个新对象。一旦app对象成功再次来到或创建,db对象附加到app对象。

正文的其他部分将代码增加到db对象内(在implementation
here会
争辩),为应用程序提供特定于数据库的逻辑。因而,如您所见本文前面包车型地铁一对中定义的函数,想想父db对象活动,但全数任何职能都以db对象的积极分子。完整的数据库模块列表见清单2。

Implementing Database-Specific Code

对数据库的各种操作关联着七个先决条件,即有叁个开发的数据库。当数据库正在被张开时,通过检查数据库版本来判别数据库是或不是需求别的更换。下边包车型地铁代码显示了模块如何追踪当前版本,object
store名、某成员(保存了一旦数据库展开央求实现后的数据库当前实例)。

JavaScript

version: 1, objectStoreName: ‘tasks’, instance: {},

1
2
3
version: 1,
objectStoreName: ‘tasks’,
instance: {},

在此,数据库展开伏乞发生时,模块央浼版本1数据库。假诺数据库不设有,或许版本小于1,upgrade
needed事件在展开央求落成前触发。那一个模块被安装为只使用三个object
store,所以名字直接定义在这里处。最终,实例成员被创设,它用来保存一旦张开央求完成后的数据库当前实例。

接下去的操作是贯彻upgrade
needed事件的事件处理程序。在这地,检查当前object
store的名字来判断恳求的object store名是不是存在,如若子虚乌有,成立object
store。

JavaScript

upgrade: function (e) { var _db = e.target.result, names =
_db.objectStoreNames, name = db.objectStoreName; if
(!names.contains(name)) { _db.createObjectStore( name, { keyPath: ‘id’,
autoIncrement: true }); } },

1
2
3
4
5
6
7
8
9
10
11
12
13
14
upgrade: function (e) {
    var
        _db = e.target.result,
        names = _db.objectStoreNames,
        name = db.objectStoreName;
    if (!names.contains(name)) {
        _db.createObjectStore(
            name,
            {
                keyPath: ‘id’,
                autoIncrement: true
            });
    }
},

在这里个事件管理程序里,通过事件参数e.target.result来访问数据库。当前的object
store名称的列表在_db.objectStoreName的字符串数组上。将来,假使object
store不设有,它是透过传递object
store名称和store的键的定义(自增,关联到数码的ID成员)来创立。

模块的下贰个效果是用来捕获错误,错误在模块不相同的恳求创造时冒泡。

JavaScript

errorHandler: function (error) { window.alert(‘error: ‘ +
error.target.code); debugger; },

1
2
3
4
errorHandler: function (error) {
    window.alert(‘error: ‘ + error.target.code);
    debugger;
},

在这里,errorHandler在二个警报框展现其余错误。那么些函数是故意保持轻松,对开拓本人,当您读书运用IndexedDB,您能够很轻巧地看看其余不当(当他们产生时)。当你希图在生产情形使用那个模块,您需求在这里个函数中落到实处部分错误管理代码来和你的应用程序的上下文打交道。

今昔基础达成了,这一节的别的部分将演示怎么样促成对数据库实践一定操作。第三个要求检讨的函数是open函数。

JavaScript

open: function (callback) { var request = window.indexedDB.open(
db.objectStoreName, db.version); request.onerror = db.errorHandler;
request.onupgradeneeded = db.upgrade; request.onsuccess = function (e) {
db.instance = request.result; db.instance.onerror = db.errorHandler;
callback(); }; },

1
2
3
4
5
6
7
8
9
10
11
12
open: function (callback) {
    var request = window.indexedDB.open(
        db.objectStoreName, db.version);
    request.onerror = db.errorHandler;
    request.onupgradeneeded = db.upgrade;
    request.onsuccess = function (e) {
        db.instance = request.result;
        db.instance.onerror =
            db.errorHandler;
        callback();
    };
},

open函数试图展开数据库,然后奉行回调函数,告知数据库成功开发方可策动采纳。通过会见window.indexedDB调用open函数来创立张开央求。这几个函数接受你想张开的object
store的称呼和你想使用的数据库版本号。

只要央求的实例可用,第一步要拓宽的干活是安装错误管理程序和提拔函数。记住,当数据库被张开时,如若脚本需要比浏览器里越来越高版本的数据库(大概一旦数据库一纸空文),升级函数运行。可是,假若供给的数据库版本匹配当前数据库版本同不经常间没错误,success事件触发。

万一全勤成功,张开数据库的实例能够从呼吁实例的result属性拿到,那几个实例也缓存到模块的实例属性。然后,onerror事件设置到模块的errorHandler,作为今后别的须求的荒谬捕捉处理程序。最后,回调被实行来报告调用者,数据库已经开拓并且正确地配置,能够行使了。

下贰个要贯彻的函数是helper函数,它回到所诉求的object store。

JavaScript

getObjectStore: function (mode) { var txn, store; mode = mode ||
‘readonly’; txn = db.instance.transaction( [db.objectStoreName],
mode); store = txn.objectStore( db.objectStoreName); return store; },

1
2
3
4
5
6
7
8
9
getObjectStore: function (mode) {
    var txn, store;
    mode = mode || ‘readonly’;
    txn = db.instance.transaction(
        [db.objectStoreName], mode);
    store = txn.objectStore(
        db.objectStoreName);
    return store;
},

在这里边,getObjectStore接受mode参数,允许你决定store是以只读依然读写情势供给。对于这一个函数,默许mode是只读的。

各种针对object
store的操作都以在三个东西的前后文中推行的。事务央浼接受二个object
store名字的数组。这些函数此番被计划为只行使一个object
store,不过就算你供给在职业中操作七个object store,你要求传递四个object
store的名字到数组中。事务函数的第4个参数是多少个情势。

即使事情央浼可用,您就能够通过传递须求的object
store名字来调用objectStore函数以获得object
store实例的访问权。那几个模块的别的函数使用getObjectStore来赢得object
store的访谈权。

下一个贯彻的函数是save函数,试行插入或更新操作,它依照传入的数目是还是不是有四个ID值。

JavaScript

save: function (data, callback) { db.open(function () { var store,
request, mode = ‘readwrite’; store = db.getObjectStore(mode), request =
data.id ? store.put(data) : store.add(data); request.onsuccess =
callback; }); },

1
2
3
4
5
6
7
8
9
10
11
12
save: function (data, callback) {
    db.open(function () {
        var store, request,
            mode = ‘readwrite’;
 
        store = db.getObjectStore(mode),
        request = data.id ?
            store.put(data) :
            store.add(data);
        request.onsuccess = callback;
    });
},

save函数的五个参数分别是索要保留的数码对象实例和操作成功后须求试行的回调。读写格局用于将数据写入数据库,它被盛传到getObjectStore来博取object
store的贰个可写实例。然后,检查数据对象的ID成员是不是存在。假如存在ID值,数据必得革新,put函数被调用,它创设长久化伏乞。不然,倘使ID不设有,这是新数据,add央浼重临。最终,不管put也许add
央浼是或不是试行了,success事件处理程序要求设置在回调函数上,来报告调用脚本,一切进展顺遂。

下一节的代码在清单1所示。getAll函数首先展开数据库和访问object
store,它为store和cursor(游标)分别设置值。为数据库游标设置游标变量允许迭代object
store中的数据。data变量设置为多少个空数组,当做数据的容器,它回到给调用代码。

在store访问数据时,游标遍历数据库中的每条记下,会触发onsuccess事件管理程序。当每条记下探望时,store的多寡足以通过e.target.result事件参数得到。尽管实际数目从target.result的value属性中取得,首先要求在图谋访谈value属性前确定保证result是三个有效的值。假诺result存在,您能够增多result的值到数据数组,然后在result对象上调用continue函数来三回九转迭代object
store。最终,若无reuslt了,对store数据的迭代结束,相同的时间数据传递到回调,回调被试行。

这两天模块能够从data
store得到所有数据,下三个急需贯彻的函数是担负访谈单个记录。

JavaScript

get: function (id, callback) { id = parseInt(id); db.open(function () {
var store = db.getObjectStore(), request = store.get(id);
request.onsuccess = function (e){ callback(e.target.result); }; }); },

1
2
3
4
5
6
7
8
9
10
11
get: function (id, callback) {
    id = parseInt(id);
    db.open(function () {
        var
            store = db.getObjectStore(),
            request = store.get(id);
        request.onsuccess = function (e){
            callback(e.target.result);
        };
    });
},

get函数施行的第一步操作是将id参数的值转变为贰个整数。决意于函数被调用时,字符串或整数都可能传递给函数。那几个达成跳过了对假使所给的字符串不能调换来整数该如何是好的情事的管理。一旦贰个id值企图好了,数据库展开了和object
store能够访谈了。获取访谈get诉求出现了。央求成功时,通过传播e.target.result来实行回调。它(e.target.result)是通过调用get函数到手的单条记录。

以往保存和接纳操作已经现身了,该模块还索要从object store移除数量。

JavaScript

‘delete’: function (id, callback) { id = parseInt(id); db.open(function
() { var mode = ‘readwrite’, store, request; store =
db.getObjectStore(mode); request = store.delete(id); request.onsuccess =
callback; }); },

1
2
3
4
5
6
7
8
9
10
11
‘delete’: function (id, callback) {
    id = parseInt(id);
    db.open(function () {
        var
            mode = ‘readwrite’,
            store, request;
        store = db.getObjectStore(mode);
        request = store.delete(id);
        request.onsuccess = callback;
    });
},

delete函数的称谓用单引号,因为delete是JavaScript的保留字。那可以由你来决定。您能够选拔命名函数为del或任何名目,可是delete用在此个模块为了API尽只怕好的抒发。

传递给delete函数的参数是目的的id和一个回调函数。为了维持这些达成轻松,delete函数约定id的值为整数。您可以选用创建多少个更加硬朗的落到实处来拍卖id值无法分析成整数的不当例子的回调,但为了指点原因,代码示例是蓄意的。

若果id值能保障转变来三个板寸,数据库被张开,贰个可写的object
store得到,delete函数传入id值被调用。当呼吁成功时,将实施回调函数。

在一些境况下,您恐怕须求删除多少个object
store的全部的记录。在这里种境况下,您访谈store同有的时候间免去全体剧情。

JavaScript

deleteAll: function (callback) { db.open(function () { var mode, store,
request; mode = ‘readwrite’; store = db.getObjectStore(mode); request =
store.clear(); request.onsuccess = callback; }); }

1
2
3
4
5
6
7
8
9
deleteAll: function (callback) {
    db.open(function () {
        var mode, store, request;
        mode = ‘readwrite’;
        store = db.getObjectStore(mode);
        request = store.clear();
        request.onsuccess = callback;
    });
}

此处deleteAll函数担当张开数据库和做客object
store的一个可写实例。一旦store可用,三个新的央求通过调用clear函数来创设。一旦clear操作成功,回调函数被执行。

实施客户分界面特定代码

到现在有着特定于数据库的代码被封装在app.db模块中,客商分界面特定代码能够运用此模块来与数据库交互。客商分界面特定代码的完整清单(index.ui.js)能够在清单3中获得,完整的(index.html)页面包车型地铁HTML源代码能够在清单4中得到。

结论

乘机应用程序的供给的进步,你会发觉在客商端高效存款和储蓄大批量的数额的优势。IndexedDB是足以在浏览器中央直属机关接选拔且帮助异步事务的文档数据库完结。固然浏览器的支撑可能还是不能够维持,但在方便的状态下,集成IndexedDB的Web应用程序具备强有力的客商端数据的探访工夫。

在超过百分之五十景色下,全部针对IndexedDB编写的代码是天然基于须求和异步的。官方正式有同步API,但是这种IndexedDB只切合web
worker的上下文中使用。那篇小说宣布时,还并未有浏览器达成的共同格式的IndexedDB
API。

需求求力保代码在任何函数域外对商家特定的indexedDB, IDBTransaction, and
IDBKeyRange实例举行了标准化且使用了适度从紧格局。那允许你制止浏览器错误,当在strict
mode下分析脚本时,它不会容许你对这几个对象重新赋值。

您不能够不保证只传递正整数的版本号给数据库。传递到版本号的小数值会四舍五入。由此,借让你的数据库近期版本1,您计划访问1.2本子,upgrade-needed事件不会触发,因为版本号最后评估是同等的。

登时施行函数表明式(IIFE)有的时候叫做不一样的名字。不常能够见到这么的代码协会措施,它称作self-executing
anonymous functions(自施行无名氏函数)或self-invoked anonymous
functions(自调用无名函数)。为更为解释那一个名称相关的用意和意义,请阅读Ben
Alman的稿子Immediately Invoked Function Expression (IIFE) 。

Listing 1: Implementing the getAll function

JavaScript

getAll: function (callback) { db.open(function () { var store =
db.getObjectStore(), cursor = store.openCursor(), data = [];
cursor.onsuccess = function (e) { var result = e.target.result; if
(result && result !== null) { data.push(result.value);
result.continue(); } else { callback(data); } }; }); },

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
getAll: function (callback) {
 
    db.open(function () {
 
        var
            store = db.getObjectStore(),
            cursor = store.openCursor(),
            data = [];
 
        cursor.onsuccess = function (e) {
 
            var result = e.target.result;
 
            if (result &&
                result !== null) {
 
                data.push(result.value);
                result.continue();
 
            } else {
 
                callback(data);
            }
        };
 
    });
},

Listing 2: Full source for database-specific code
(index.db.js)

JavaScript

// index.db.js ; window.indexedDB = window.indexedDB ||
window.mozIndexedDB || window.webkitIndexedDB || window.msIndexedDB;
window.IDBTransaction = window.IDBTransaction ||
window.webkitIDBTransaction || window.msIDBTransaction;
window.IDBKeyRange = window.IDBKeyRange || window.webkitIDBKeyRange ||
window.msIDBKeyRange; (function(window){ ‘use strict’; var db = {
version: 1, // important: only use whole numbers! objectStoreName:
‘tasks’, instance: {}, upgrade: function (e) { var _db =
e.target.result, names = _db.objectStoreNames, name =
db.objectStoreName; if (!names.contains(name)) { _db.createObjectStore(
name, { keyPath: ‘id’, autoIncrement: true }); } }, errorHandler:
function (error) { window.alert(‘error: ‘ + error.target.code);
debugger; }, open: function (callback) { var request =
window.indexedDB.open( db.objectStoreName, db.version); request.onerror
= db.errorHandler; request.onupgradeneeded = db.upgrade;
request.onsuccess = function (e) { db.instance = request.result;
db.instance.onerror = db.errorHandler; callback(); }; }, getObjectStore:
function (mode) { var txn, store; mode = mode || ‘readonly’; txn =
db.instance.transaction( [db.objectStoreName], mode); store =
txn.objectStore( db.objectStoreName); return store; }, save: function
(data, callback) { db.open(function () { var store, request, mode =
‘readwrite’; store = db.getObjectStore(mode), request = data.id ?
store.put(data) : store.add(data); request.onsuccess = callback; }); },
getAll: function (callback) { db.open(function () { var store =
db.getObjectStore(), cursor = store.openCursor(), data = [];
cursor.onsuccess = function (e) { var result = e.target.result; if
(result && result !== null) { data.push(result.value);
result.continue(); } else { callback(data); } }; }); }, get: function
(id, callback) { id = parseInt(id); db.open(function () { var store =
db.getObjectStore(), request = store.get(id); request.onsuccess =
function (e){ callback(e.target.result); }; }); }, ‘delete’: function
(id, callback) { id = parseInt(id); db.open(function () { var mode =
‘readwrite’, store, request; store = db.getObjectStore(mode); request =
store.delete(id); request.onsuccess = callback; }); }, deleteAll:
function (callback) { db.open(function () { var mode, store, request;
mode = ‘readwrite’; store = db.getObjectStore(mode); request =
store.clear(); request.onsuccess = callback; }); } }; window.app =
window.app || {}; window.app.db = db; }(window));

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
// index.db.js
 
;
 
window.indexedDB = window.indexedDB ||
                   window.mozIndexedDB ||
                   window.webkitIndexedDB ||
                   window.msIndexedDB;
 
window.IDBTransaction = window.IDBTransaction ||
                   window.webkitIDBTransaction ||
                   window.msIDBTransaction;
 
window.IDBKeyRange = window.IDBKeyRange ||
                   window.webkitIDBKeyRange ||
                   window.msIDBKeyRange;
 
(function(window){
 
    ‘use strict’;
 
    var db = {
 
        version: 1, // important: only use whole numbers!
 
        objectStoreName: ‘tasks’,
 
        instance: {},
 
        upgrade: function (e) {
 
            var
                _db = e.target.result,
                names = _db.objectStoreNames,
                name = db.objectStoreName;
 
            if (!names.contains(name)) {
 
                _db.createObjectStore(
                    name,
                    {
                        keyPath: ‘id’,
                        autoIncrement: true
                    });
            }
        },
 
        errorHandler: function (error) {
            window.alert(‘error: ‘ + error.target.code);
            debugger;
        },
 
        open: function (callback) {
 
            var request = window.indexedDB.open(
                db.objectStoreName, db.version);
 
            request.onerror = db.errorHandler;
 
            request.onupgradeneeded = db.upgrade;
 
            request.onsuccess = function (e) {
 
                db.instance = request.result;
 
                db.instance.onerror =
                    db.errorHandler;
 
                callback();
            };
        },
 
        getObjectStore: function (mode) {
 
            var txn, store;
 
            mode = mode || ‘readonly’;
 
            txn = db.instance.transaction(
                [db.objectStoreName], mode);
 
            store = txn.objectStore(
                db.objectStoreName);
 
            return store;
        },
 
        save: function (data, callback) {
 
            db.open(function () {
 
                var store, request,
                    mode = ‘readwrite’;
 
                store = db.getObjectStore(mode),
 
                request = data.id ?
                    store.put(data) :
                    store.add(data);
 
                request.onsuccess = callback;
            });
        },
 
        getAll: function (callback) {
 
            db.open(function () {
 
                var
                    store = db.getObjectStore(),
                    cursor = store.openCursor(),
                    data = [];
 
                cursor.onsuccess = function (e) {
 
                    var result = e.target.result;
 
                    if (result &&
                        result !== null) {
 
                        data.push(result.value);
                        result.continue();
 
                    } else {
 
                        callback(data);
                    }
                };
 
            });
        },
 
        get: function (id, callback) {
 
            id = parseInt(id);
 
            db.open(function () {
 
                var
                    store = db.getObjectStore(),
                    request = store.get(id);
 
                request.onsuccess = function (e){
                    callback(e.target.result);
                };
            });
        },
 
        ‘delete’: function (id, callback) {
 
            id = parseInt(id);
 
            db.open(function () {
 
                var
                    mode = ‘readwrite’,
                    store, request;
 
                store = db.getObjectStore(mode);
 
                request = store.delete(id);
 
                request.onsuccess = callback;
            });
        },
 
        deleteAll: function (callback) {
 
            db.open(function () {
 
                var mode, store, request;
 
                mode = ‘readwrite’;
                store = db.getObjectStore(mode);
                request = store.clear();
 
                request.onsuccess = callback;
            });
 
        }
    };
 
    window.app = window.app || {};
    window.app.db = db;
 
}(window));

Listing 3: Full source for user interface-specific code
(index.ui.js)

JavaScript

// index.ui.js ; (function ($, Modernizr, app) { ‘use strict’;
$(function(){ if(!Modernizr.indexeddb){
$(‘#unsupported-message’).show(); $(‘#ui-container’).hide(); return; }
var $deleteAllBtn = $(‘#delete-all-btn’), $titleText =
$(‘#title-text’), $notesText = $(‘#notes-text’), $idHidden =
$(‘#id-hidden’), $clearButton = $(‘#clear-button’), $saveButton =
$(‘#save-button’), $listContainer = $(‘#list-container’),
$noteTemplate = $(‘#note-template’), $emptyNote = $(‘#empty-note’);
var addNoTasksMessage = function(){ $listContainer.append(
$emptyNote.html()); }; var bindData = function (data) {
$listContainer.html(”); if(data.length === 0){ addNoTasksMessage();
return; } data.forEach(function (note) { var m = $noteTemplate.html(); m
= m.replace(/{ID}/g, note.id); m = m.replace(/{TITLE}/g, note.title);
$listContainer.append(m); }); }; var clearUI = function(){
$titleText.val(”).focus(); $notesText.val(”); $idHidden.val(”); }; //
select individual item $listContainer.on(‘click’, ‘a[data-id]’,
function (e) { var id, current; e.preventDefault(); current =
e.currentTarget; id = $(current).attr(‘data-id’); app.db.get(id,
function (note) { $titleText.val(note.title); $notesText.val(note.text);
$idHidden.val(note.id); }); return false; }); // delete item
$listContainer.on(‘click’, ‘i[data-id]’, function (e) { var id,
current; e.preventDefault(); current = e.currentTarget; id =
$(current).attr(‘data-id’); app.db.delete(id, function(){
app.db.getAll(bindData); clearUI(); }); return false; });
$clearButton.click(function(e){ e.preventDefault(); clearUI(); return
false; }); $saveButton.click(function (e) { var title =
$titleText.val(); if (title.length === 0) { return; } var note = {
title: title, text: $notesText.val() }; var id = $idHidden.val(); if(id
!== ”){ note.id = parseInt(id); } app.db.save(note, function(){
app.db.getAll(bindData); clearUI(); }); }); $deleteAllBtn.click(function
(e) { e.preventDefault(); app.db.deleteAll(function () {
$listContainer.html(”); addNoTasksMessage(); clearUI(); }); return
false; }); app.db.errorHandler = function (e) { window.alert(‘error: ‘ +
e.target.code); debugger; }; app.db.getAll(bindData); }); }(jQuery,
Modernizr, window.app));

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
// index.ui.js
 
;
 
(function ($, Modernizr, app) {
 
    ‘use strict’;
 
    $(function(){
 
        if(!Modernizr.indexeddb){
            $(‘#unsupported-message’).show();
            $(‘#ui-container’).hide();
            return;
        }
 
        var
          $deleteAllBtn = $(‘#delete-all-btn’),
          $titleText = $(‘#title-text’),
          $notesText = $(‘#notes-text’),
          $idHidden = $(‘#id-hidden’),
          $clearButton = $(‘#clear-button’),
          $saveButton = $(‘#save-button’),
          $listContainer = $(‘#list-container’),
          $noteTemplate = $(‘#note-template’),
          $emptyNote = $(‘#empty-note’);
 
        var addNoTasksMessage = function(){
            $listContainer.append(
                $emptyNote.html());
        };
 
        var bindData = function (data) {
 
            $listContainer.html(”);
 
            if(data.length === 0){
                addNoTasksMessage();
                return;
            }
 
            data.forEach(function (note) {
              var m = $noteTemplate.html();
              m = m.replace(/{ID}/g, note.id);
              m = m.replace(/{TITLE}/g, note.title);
              $listContainer.append(m);
            });
        };
 
        var clearUI = function(){
            $titleText.val(”).focus();
            $notesText.val(”);
            $idHidden.val(”);
        };
 
        // select individual item
        $listContainer.on(‘click’, ‘a[data-id]’,
 
            function (e) {
 
                var id, current;
 
                e.preventDefault();
 
                current = e.currentTarget;
                id = $(current).attr(‘data-id’);
 
                app.db.get(id, function (note) {
                    $titleText.val(note.title);
                    $notesText.val(note.text);
                    $idHidden.val(note.id);
                });
 
                return false;
            });
 
        // delete item
        $listContainer.on(‘click’, ‘i[data-id]’,
 
            function (e) {
 
                var id, current;
 
                e.preventDefault();
 
                current = e.currentTarget;
                id = $(current).attr(‘data-id’);
 
                app.db.delete(id, function(){
                    app.db.getAll(bindData);
                    clearUI();
                });
 
                return false;
        });
 
        $clearButton.click(function(e){
            e.preventDefault();
            clearUI();
            return false;
        });
 
        $saveButton.click(function (e) {
 
            var title = $titleText.val();
 
            if (title.length === 0) {
                return;
            }
 
            var note = {
                title: title,
                text: $notesText.val()
            };
 
            var id = $idHidden.val();
 
            if(id !== ”){
                note.id = parseInt(id);
            }
 
            app.db.save(note, function(){
                app.db.getAll(bindData);
                clearUI();
            });
        });
 
        $deleteAllBtn.click(function (e) {
 
            e.preventDefault();
 
            app.db.deleteAll(function () {
                $listContainer.html(”);
                addNoTasksMessage();
                clearUI();
            });
 
            return false;
        });
 
        app.db.errorHandler = function (e) {
            window.alert(‘error: ‘ + e.target.code);
            debugger;
        };
 
        app.db.getAll(bindData);
 
    });
 
}(jQuery, Modernizr, window.app));

Listing 3: Full HTML source (index.html)

JavaScript

<!doctype html> <html lang=”en-US”> <head> <meta
charset=”utf-8″> <meta http-equiv=”X-UA-Compatible”
content=”IE=edge”> <title>Introduction to
IndexedDB</title> <meta name=”description”
content=”Introduction to IndexedDB”> <meta name=”viewport”
content=”width=device-width, initial-scale=1″> <link
rel=”stylesheet”
href=”//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css”>
<link rel=”stylesheet” href=”//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/css/font-awesome.min.css” > <link
rel=”stylesheet” href=”//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/FontAwesome.otf” > <link
rel=”stylesheet” href=”//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.eot” > <link
rel=”stylesheet” href=”//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.svg” > <link
rel=”stylesheet” href=”//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.ttf” > <link
rel=”stylesheet” href=”//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.woff” > <style>
h1 { text-align: center; color:#999; } ul li { font-size: 1.35em;
margin-top: 1em; margin-bottom: 1em; } ul li.small { font-style: italic;
} footer { margin-top: 25px; border-top: 1px solid #eee; padding-top:
25px; } i[data-id] { cursor: pointer; color: #eee; }
i[data-id]:hover { color: #c75a6d; } .push-down { margin-top: 25px; }
#save-button { margin-left: 10px; } </style> <script
src=”//cdnjs.cloudflare.com/ajax/libs/modernizr%20/2.8.2/modernizr.min.js”
></script> </head> <body class=”container”>
<h1>Tasks</h1> <div id=”unsupported-message” class=”alert
alert-warning” style=”display:none;”> <b>Aww snap!</b>
Your browser does not support indexedDB. </div> <div
id=”ui-container” class=”row”> <div class=”col-sm-3″> <a
href=”#” id=”delete-all-btn” class=”btn-xs”> <i class=”fa
fa-trash-o”></i> Delete All</a> <hr/> <ul
id=”list-container” class=”list-unstyled”></ul> </div>
<div class=”col-sm-8 push-down”> <input type=”hidden”
id=”id-hidden” /> <input id=”title-text” type=”text”
class=”form-control” tabindex=”1″ placeholder=”title” autofocus
/><br /> <textarea id=”notes-text” class=”form-control”
tabindex=”2″ placeholder=”text”></textarea> <div
class=”pull-right push-down”> <a href=”#” id=”clear-button”
tabindex=”4″>Clear</a> <button id=”save-button” tabindex=”3″
class=”btn btn-default btn-primary”> <i class=”fa
fa-save”></i> Save</button> </div> </div>
</div> <footer class=”small text-muted text-center”>by <a
href=”” target=”_blank”>Craig
Shoemaker</a> <a href=””
target=”_blank”> <i class=”fa fa-twitter”></i></a>
</footer> <script id=”note-template” type=”text/template”>
<li> <i data-id=”{ID}” class=”fa fa-minus-circle”></i>
<a href=”#” data-id=”{ID}”>{TITLE}</a> </li>
</script> <script id=”empty-note” type=”text/template”>
<li class=”text-muted small”>No tasks</li> </script>
<script src=”//ajax.googleapis.com/ajax/libs
/jquery/1.11.1/jquery.min.js”></script> <script
src=”index.db.js” type=”text/javascript”></script> <script
src=”index.ui.js” type=”text/javascript”></script>
</body> </html>

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
<!doctype html>
<html lang="en-US">
    <head>
        <meta charset="utf-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <title>Introduction to IndexedDB</title>
        <meta name="description"
              content="Introduction to IndexedDB">
        <meta name="viewport"
              content="width=device-width, initial-scale=1">
        <link rel="stylesheet"
              href="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css">
        <link rel="stylesheet"
              href="//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/css/font-awesome.min.css" >
        <link rel="stylesheet"
              href="//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/FontAwesome.otf" >
        <link rel="stylesheet"
              href="//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.eot" >
        <link rel="stylesheet"
              href="//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.svg" >
        <link rel="stylesheet"
              href="//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.ttf" >
        <link rel="stylesheet"
              href="//cdnjs.cloudflare.com/ajax/libs
/font-awesome/4.1.0/fonts/fontawesome-webfont.woff" >
        <style>
            h1 {
                text-align: center;
                color:#999;
            }
 
            ul li {
                font-size: 1.35em;
                margin-top: 1em;
                margin-bottom: 1em;
            }
 
            ul li.small {
                font-style: italic;
            }
 
            footer {
                margin-top: 25px;
                border-top: 1px solid #eee;
                padding-top: 25px;
            }
 
            i[data-id] {
                cursor: pointer;
                color: #eee;
            }
 
            i[data-id]:hover {
                color: #c75a6d;
            }
 
            .push-down {
                margin-top: 25px;
            }
 
            #save-button {
                margin-left: 10px;
            }
        </style>
        <script src="//cdnjs.cloudflare.com/ajax/libs/modernizr
/2.8.2/modernizr.min.js" ></script>
    </head>
    <body class="container">
        <h1>Tasks</h1>
        <div id="unsupported-message"
             class="alert alert-warning"
             style="display:none;">
            <b>Aww snap!</b> Your browser does not support indexedDB.
        </div>
        <div id="ui-container" class="row">
            <div class="col-sm-3">
 
                <a href="#" id="delete-all-btn" class="btn-xs">
                    <i class="fa fa-trash-o"></i> Delete All</a>
 
                <hr/>
 
                <ul id="list-container" class="list-unstyled"></ul>
 
            </div>
            <div class="col-sm-8 push-down">
 
                <input type="hidden" id="id-hidden" />
 
                <input
                       id="title-text"
                       type="text"
                       class="form-control"
                       tabindex="1"
                       placeholder="title"
                       autofocus /><br />
 
                <textarea
                          id="notes-text"
                          class="form-control"
                          tabindex="2"
                          placeholder="text"></textarea>
 
                <div class="pull-right push-down">
 
                    <a href="#" id="clear-button" tabindex="4">Clear</a>
 
                    <button id="save-button"
                            tabindex="3"
                            class="btn btn-default btn-primary">
                                <i class="fa fa-save"></i> Save</button>
                </div>
            </div>
        </div>
        <footer class="small text-muted text-center">by
            <a href="http://craigshoemaker.net" target="_blank">Craig Shoemaker</a>
            <a href="http://twitter.com/craigshoemaker" target="_blank">
                <i class="fa fa-twitter"></i></a>
        </footer>
        <script id="note-template" type="text/template">
            <li>
                <i data-id="{ID}" class="fa fa-minus-circle"></i>
                <a href="#" data-id="{ID}">{TITLE}</a>
            </li>
        </script>
        <script id="empty-note" type="text/template">
            <li class="text-muted small">No tasks</li>
        </script>
        <script src="//ajax.googleapis.com/ajax/libs
/jquery/1.11.1/jquery.min.js"></script>
        <script src="index.db.js" type="text/javascript"></script>
        <script src="index.ui.js" type="text/javascript"></script>
    </body>
</html>

赞 1 收藏
评论

至于作者:cucr

图片 9

今日头条新浪:@hop_ping
个人主页 ·
笔者的篇章 ·
17

图片 10

相关文章

发表评论

电子邮件地址不会被公开。 必填项已用*标注

网站地图xml地图