indexedDB, который является новым в HTML5, позволяет разработчикам сохранять данные в веб-браузере. В результате ваше приложение работает как в сети, так и в автономном режиме с мощными средствами запросов. indexedDB отличается от традиционных реляционных баз данных тем, что он является objectStore
а не набором строк и столбцов. Вы просто создаете objectStore
в indexedDB и сохраняете объекты JavaScript в этом хранилище. Кроме того, очень легко выполнять CRUD-операции с сохраненными объектами. В этом руководстве дается обзор API indexedDB и объясняется, как его использовать для создания простого приложения блокнота.
Прежде чем мы начнем, обратите внимание, что спецификация indexedDB API еще не стабилизировалась. Но если на вашем компьютере установлена последняя версия Firefox или Google Chrome, то все в порядке. Чтобы узнать, какие версии браузера поддерживают API, смотрите таблицу совместимости .
В спецификации indexedDB есть два типа API: синхронный и асинхронный. Однако мы сосредоточимся на асинхронном API, так как в настоящее время это единственный API, который поддерживается браузерами. Асинхронный означает, что вы выполняете операцию с базой данных и получаете результат в обратном вызове через событие DOM.
В любом приложении для создания заметок есть четыре простых функции: создание, чтение, обновление и удаление. indexedDB предоставляет очень простые API для выполнения этих операций. Но прежде чем что-то делать, нам нужно создать базу данных и открыть ее.
Настройка:
Поскольку спецификация еще не стабилизирована, разные браузеры используют префиксы в своих реализациях. Таким образом, вы должны проверить правильно, чтобы убедиться, что браузер поддерживает indexedDB. Используйте следующий код, чтобы убедиться, что браузер поддерживает indexedDB.
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; if (! window.indexedDB) { alert («Извините! Ваш браузер не поддерживает IndexedDB»); }
Открытие / Создание базы данных:
Открытие базы данных indexedDB — это вопрос вызова indexedDB.open()
.
var request = window.indexedDB.open("notepad",1);
indexedDB.open()
принимает два параметра. Первый представляет имя базы данных. Если база данных еще не существует, она создает новую. Второй параметр — номер версии. Если вам необходимо обновить схему базы данных в будущем, вам нужно вызвать indexedDB.open()function
с номером версии, более высоким, чем предыдущий. В этом случае вам потребуется реализовать onupgradeneeded
вызов onupgradeneeded
где вы можете обновить схему базы данных и создать / удалить objectStores
.
Создание базы данных является первым шагом. Но для хранения чего-то вам нужно иметь objectStore
. Когда вы создаете базу данных, вы, вероятно, захотите создать и objectStore
. При первоначальном создании базы данных onupgradeneeded
обратный вызов, при котором вы можете создать objectStore
.
база данных var; var request = window.indexedDB.open ("блокнот", 1); request.onerror = function (event) { console.log (event.target.errorCode); }; request.onsuccess = function (event) { базы данных = request.result; }; request.onupgradeneeded = function (event) { var db = event.target.result; var objectStore = db.createObjectStore ("notes", {keyPath: "id", autoIncrement: true}); };
В приведенном выше примере кода мы вызываем indexedDB.open()
с блокнотом имени базы данных и номером версии 1. Метод возвращает IDBOpenDBRequest
. Когда запрос на открытие базы данных завершается успешно, вызывается обратный вызов request.onsuccess
. Свойство результата запроса является экземпляром IDBDatabase
который мы присваиваем переменной базе данных для дальнейшего использования.
Внутри обратного вызова onupgradeneeded
мы получаем ссылку на базу данных и используем ее для создания нового objectStore
именем notes
. createObjectStore()
также принимает второй параметр. В этом случае мы определили keyPath
именем id
который уникальным образом идентифицирует объект в нашем магазине. Кроме того, мы также хотим, чтобы идентификатор был autoIncrementing
.
Добавление / обновление элемента в storeStore:
Допустим, мы хотим сохранить записку в магазине. Объект должен иметь такие поля, как: заголовок, тело и дата создания. Для хранения объекта используйте следующий код:
var note = {title: «Test Note», тело: «Hello World!», дата: «01/04/2013»}; varaction = database.transaction (["notes"], "readwrite"); var objectStore =action.objectStore («заметки»); var request = objectStore.put (note); request.onsuccess = function (event) { // сделать что-то здесь };
database.transaction()
принимает массив в качестве первого параметра, который представляет имена objectStores
охватывающих эту транзакцию. Второй параметр определяет тип транзакции. Если вы не передадите второй аргумент, вы получите транзакцию только для чтения. Поскольку мы хотим добавить новый элемент, мы передаем readwrite
в качестве второго аргумента. В результате этого вызова мы получаем объект транзакции. objectStore
transaction.objectStore()
выбирает objectStore
для работы. Наконец, objectStore.put()
добавляет объект в хранилище. Вы также можете использовать objectStore.add()
для добавления объекта. Но первый обновит объект в хранилище, если мы попытаемся добавить новый объект с id
идентичным id
существующей записи.
Удаление товара из магазина:
Удалить объект из магазина довольно просто и понятно.
var request = database.transaction (["notes"], "readwrite") .objectStore ("notes"). delete (20); request.onsuccess = function (event) { // справиться с успехом };
Приведенный выше код удаляет объект из магазина с id
20.
Запрос всех объектов в магазине:
Для любого приложения, управляемого базой данных, очень часто отображаются все сохраненные записи. В indexedDB вы можете получить объекты, хранящиеся в хранилище, и перебирать их с помощью курсора.
var objectStore = database.transaction ("заметки"). objectStore ("заметки"); objectStore.openCursor (). onsuccess = function (event) { var cursor = event.target.result; if (курсор) { alert («Примечание ID:« + cursor.key + », Заголовок:« + cursor.value.title); cursor.continue (); } };
Приведенный выше код очень прост для понимания. Функция openCursor()
может принимать несколько аргументов. Вы можете контролировать диапазон возвращаемых результатов и направление итерации, передавая соответствующие параметры. Объект курсора является результатом запроса. cursor.continue()
должен вызываться, если вы ожидаете несколько объектов и хотите перебрать их. Это означает, что до тех пор, пока существует больше данных, onsuccess
вызов срабатывает при условии, что вы вызываете cursor.continue()
.
Итак, это все, что вы должны знать, прежде чем разрабатывать приложение блокнота с использованием indexedDB. Теперь я покажу, как создать приложение шаг за шагом.
Начальная разметка HTML:
<HTML> <head> <title> Простой блокнот с использованием indexedDB </ title> </ HEAD> <Тело> <div id = "container"> <h3 id = "heading"> Добавить заметку </ h3> <input type = "hidden" value = "0" id = "flag" /> <a href="#" id="add"> <img src = "add.png" onclick = "createNote (0)" /> Новый </a> <a href="#" id="back"> <img src = "back.png" onclick = "goBack ()" /> </a> <div id = "notes"> </ div> <div id = "editor" contenteditable = "true"> </ div> </ DIV> </ Body> </ Html>
Объяснение:
У нас есть два элемента: заметки и редактор. Первый используется для отображения списка существующих заметок, а второй — в качестве редактора для написания заметки. Div редактора изначально невидим. Когда пользователь нажимает кнопку « Добавить» , мы скрываем блок заметок и показываем блок редактора. Вы должны иметь в виду, что, устанавливая contenteditable="true"
мы делаем div редактируемым. У нас также есть скрытое поле ввода с флагом ID. Это будет использовано позже в уроке.
JavaScript:
<script type = "text / javascript"> база данных var; 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; if (! window.indexedDB) { alert («Извините! Ваш браузер не поддерживает IndexedDB»); } функция init () { var request = window.indexedDB.open ("блокнот", 1); request.onerror = function (event) { console.log (event.target.errorCode); }; request.onsuccess = function (event) { базы данных = request.result; showNotes (); }; request.onupgradeneeded = function (event) { var db = event.target.result; var objectStore = db.createObjectStore ("notes", {keyPath: "id", autoIncrement: true}); }; } функция createNote (id) { document.getElementById ( "Редактор") style.display = "блок". document.getElementById ( "Редактор") фокус (). document.getElementById ( "назад") style.display = "блок". document.getElementById ( "добавить") style.display = "нет". document.getElementById ( "Примечание") style.display = "нет". если (ParseInt (идентификатор)! = 0) { database.transaction ( "записки"). В ObjectStore ( "записки"). получить (ParseInt (идентификатор)) .onsuccess = функция (событие) { document.getElementById ( "Редактор") innerHTML = event.target.result.body. . Document.getElementById ( "флаг") значение = ID; }; } } function goBack () { var note = {}; note.body = document.getElementById ( "Редактор") innerHTML. note.title = GetTitle (note.body); note.date = GetDate (); var flag = parseInt (document.getElementById ("flag"). value); если (флаг! = 0) note.id = флаг; если (note.title.trim () === "") window.location.href = "index.html"; еще addNote (примечание); } function getDate () { переменная дата = новая дата (); var month = parseInt (date.getMonth ()) + 1; return date.getDate () + "/" + month + "/" + date.getFullYear (); } function getTitle (body) { var body = body.replace (/ (<([^>] +)>) / ig, ""); if (body.length> 20) body = body.substring (0,20) + "....."; возвращение тела; } function addNote (note) { varaction = database.transaction (["notes"], "readwrite"); var objectStore =action.objectStore («заметки»); var request = objectStore.put (note); request.onsuccess = function (event) { . Document.getElementById ( "флаг") значение = "0"; window.location.href = "index.html"; }; } function showNotes () { var notes = ""; var objectStore = database.transaction ("заметки"). objectStore ("заметки"); objectStore.openCursor (). onsuccess = function (event) { var cursor = event.target.result; if (курсор) { var link = "<a class="notelist" id=""+cursor.key+"" href="#">" + cursor.value.title + "</a>" + " <img class = "delete" src = "delete.png" height = "30px" id = "" + cursor.key + "" /> "; var listItem = "<li>" + link + "</ li>"; ноты = ноты + ListItem; cursor.continue (); } еще { document.getElementById ( "Примечания") innerHTML = "<уль>" + заметки + "</ UL>". registerEdit (); registerDelete (); } }; } function deleteNote (id) { var request = database.transaction (["notes"], "readwrite") .objectStore ( "записки") .delete (ID); request.onsuccess = function (event) { window.location.href = "index.html"; }; } function registerEdit () { var elements = document.getElementsByClassName ('notelist'); for (var i = 0, length = elements.length; i <length; i ++) { elements [i] .onclick = function (e) { createNote (this.id); } } } function registerDelete () { var deleteButtons = document.getElementsByClassName ('delete'); for (var i = 0, length = deleteButtons.length; i <длина; i ++) { deleteButtons [I] .onclick = функция (е) { deleteNote (ParseInt (this.id)); } } } window.addEventListener ("DOMContentLoaded", init, false); </ Скрипт>
Объяснение:
Метод init
выполняет необходимую инициализацию. Он создает / открывает базу данных, а также создает objectStore
при первом создании базы данных. После успешного открытия базы данных мы получаем ссылку на нее и сохраняем ее в переменной базы данных.
showNotes()
отображает список заметок, созданных пользователем. Мы начинаем транзакцию и получаем объекты заметки, которые присутствуют в магазине. Затем мы создаем неупорядоченный список заголовков заметок и, наконец, отображаем его в div с id
заметок. Мы также вызываем две функции registerEdit()
и registerDelete()
. Первая функция присоединяет прослушиватель события щелчка к заголовкам заметок, которые представляют собой простые ссылки, имеющие класс notelist, так что заметки можно редактировать, когда кто-то нажимает на заголовок. Последняя функция добавляет прослушиватель события щелчка к кнопкам удаления (простым изображениям), которые присутствуют рядом с заголовками заметок. Делая это, мы можем удалить заметку, когда кто-то нажимает на кнопку удаления. Функция deleteNote()
выполняет операцию удаления.
Функция createNote()
отображает редактор для создания новой заметки или обновления существующей. Он принимает один аргумент. Если это 0, мы знаем, что мы хотим создать новую заметку. В противном случае мы запускаем транзакцию, чтобы получить содержимое существующей заметки. Мы передаем id
заметки в objectStore.get()
и в onsuccess
тело заметки. Затем мы заполняем редактор извлеченным телом заметки. Кроме того, мы устанавливаем наш скрытый флаг ввода для идентификатора, который используется в функции goBack()
. Этот метод запускается, когда пользователь хочет вернуться после написания заметки. Здесь мы сохраняем заметку в магазине.
В функции goBack()
мы создаем новый объект и устанавливаем его свойства title, body и date. Название принимается за первые 20 символов тела. Затем выясните значение скрытого флага. Если это не 0, мы знаем, что хотим обновить существующую заметку. Поэтому мы устанавливаем свойство id
созданного объекта. В противном случае не требуется свойство id
поскольку объект будет новой записью в хранилище. В конце addNote()
функция addNote()
с объектом примечания в качестве аргумента. Функция addNote()
просто запускает транзакцию, которая добавляет / обновляет объект в хранилище. Если транзакция прошла успешно, мы возвращаем пользователя туда, где он / она может видеть список созданных заметок.
Вы можете попробовать демо-приложение здесь . Я протестировал приложение в Chrome 25 и Firefox 20.
indexedDB — отличный API в HTML5, и при использовании с кешем приложений он может быть очень мощным. У Mozilla есть некоторая интересная и очень полезная информация об indexedDB. Проверьте их, если хотите узнать больше.
Если вы не можете получить что-то, дайте мне знать в комментариях.