簡単に言うと、ブラウザを閉じても保存しておきたいデータを格納するための仕組み。
他にもWebStorageやWebSQLなどがある。
今後は、IndexedDBが最も利用されるデータベースになる! ……らしい。
当エントリは、最近個人的に勉強を始めた「TypeScript」でIndexedDBを操作する方法をまとめる。
最後にコンパイルしたJavaScriptも載せておくので、TypeScriptに興味ない人はそちらを参照ください。
開発環境
- TypeScript 1.4
- Visual Studio Community 2013
- InternetExplorer 11 / Google Chrome 41
今回つくるモノ
今回IndexedDBを使うにあたり、以下のサイトを参考にさせていただいた。
▶ Indexed Database API について - へっぽこプログラマーの日記
そして、以下のような感じの超簡易的なレイアウトで、「登録」「更新」「削除」「全削除」「検索」「全検索」を行う。
開発メモ
- データベース名:library
- オブジェクトストア名:books
- インデックス名:index
- キー項目名:isbn
注意点
今回のサンプルにjQueryを使用している。VS Community 2013インストール直後だと、jQueryの型定義でアホほどエラーがでる。
そんなときは、TypeScriptのバージョンを1.4にしてください。
▶ TypeScript 1.4 for Visual Studio 2013 拡張機能
ちなみに、jQueryや型定義は、Nugetで「jQuery DifinitelyTyped」とか検索するとでてくる。
データベースの作成
// ベンタープレフィックス(webkit:Chrome、moz:FireFox)
var indexedDB = window.indexedDB;// || window.webkitIndexedDB;
// データベース接続
var db: IDBDatabase = null;
var request = indexedDB.open('library', 1);
// 接続成功(初回 or DBのバージョンが変わったとき)
request.onupgradeneeded = (event) => {
db = (<IDBRequest>event.target).result;
// オブジェクトストア作成(インデックスのキーとして'isbn'を指定)
var store = db.createObjectStore('books', { keyPath: 'isbn' });
// インデックスの作成
store.createIndex('index', 'isbn', false);
};
// 接続成功(すでにDBが存在する場合)
request.onsuccess = (event) => {
db = (<IDBRequest>event.target).result;
};
request.onerror = (event) => {
console.log(event.message);
};
ベンタープレフィックス対応のところで、
window.webkitIndexedDB
を使用すると、Property 'webkitIndexedDB' does not exist on type 'Window'.
というエラーが発生するため、コメントアウトしている。(コメントアウトした状態でも、ChromeでIndexedDB使えたけど…)onupgradeneeded
、onsuccess
のコールバックメソッド内で、JavaScriptならthis.result
やevent.target.result
と書けるが、TypeScriptの場合はそのまま書くとエラーになってしまうため、適切な型にキャストしている。型推論を使っているので、一見どんな型かわからないと思うので、補足しておく。
TypeScriptを使うときは、型に注意しないとエラーになっちゃうので!
変数名 | 型 |
---|---|
indexedDB | IDBFactory |
db | IDBDatabase |
request | IDBOpenDBRequest |
store | IDBObjectStore |
データ登録・更新
var trans = db.transaction('books', 'readwrite');
var store = trans.objectStore('books');
// 登録対象のデータ(BookInfoはInterfaceで定義)
var bookInfo: BookInfo = {
name: $('#name').val(),
description: $('#description').val(),
author: $('#author').val(),
isbn: $('#isbn').val()
};
// データ登録・更新
var request = store.put(bookInfo);
request.onsuccess = (event) => {
console.log('登録成功');
};
request.onerror = (event) => {
console.log('登録失敗:' + event.message);
};
トランザクションを開始し、データを登録・更新する処理。
13行目の
store.put(bookInfo)
>だが、IDBObjectStore.put()
を使うと、キーが存在する場合は更新、存在しない場合は登録と自動的に判断してくれる。IDBObjectStore.add()
もあるが、こちらはキーが存在すると重複エラー、存在しない場合は登録となる。似ているようでちょっと違うので要注意!
一応型も。。。
変数名 | 型 |
---|---|
trans | IDBTransaction |
store | IDBObjectStore |
request | IDBRequest |
bookInfo | ユーザ定義(BookInfo) |
データ検索
var key = $('#isbn').val();
var trans = db.transaction('books', 'readonly');
var store = trans.objectStore('books');
// データ取得
var request = store.get(key);
request.onsuccess = (event) => {
var result = <BookInfo>(<IDBRequest>event.target).result;
if (result) {
render(result);
} else {
console.log('対象データは存在しません。');
}
};
1行目の「key」が検索キーをテキストボックスから取得する。
この検索キーは、オブジェクトストア作成時に「keyPath」として指定したモノ。
7行目の「store.get(key)」でデータを取得する。
データが0件だった場合も、onsuccessコールバックが呼ばれるので注意。
12行目は、取得したデータ(result:BookInfo)を画面表示用のRenderメソッドに渡している。
型については、「データ登録・更新」と同じなので省略。
全データ取得
var trans = db.transaction('books', 'readonly');
var store = trans.objectStore('books');
// 全データ取得
var request = store.openCursor();
request.onsuccess = (event) => {
var cursor = <IDBCursorWithValue>(<IDBRequest>event.target).result;
if (cursor) {
render(cursor.value);
cursor.continue();
}
};
「データ検索」と違い、store.openCursorを使うことで一度に複数のデータを取得することができる。
openCursor(optionalKeyRange, optionalDirection)
の第1引数にIDBKeyRange
を渡すことで「1件目~10件目までを取得」といった範囲指定も可能。第2引数に'NEXT'や’PREV'などを渡すことで、取得する順番も指定できる。データ取得後の処理は、request.onsuccessが何度も呼ばれるイメージ。
transやstoreなどは、「データ登録・更新」と同じなので省略。
変数名 | 型 |
---|---|
cursor | IDBCursorWithValue |
データ削除
var key = $('#isbn').val();
var trans = db.transaction('books', 'readwrite');
var store = trans.objectStore('books');
// データ削除
var request = store.delete(key);
request.onsuccess = (event) => {
console.log('削除成功');
};
request.onerror = (event) => {
console.log('削除失敗:' + event.message);
};
「データ検索」に似ている。7行目の「store.delete(key)」で、データを削除する。
この削除するときのキーは、オブジェクトストア作成時に「keyPath」として指定したモノ。
型は他のと同じなので省略。
全データ削除
var trans = db.transaction('books', 'readwrite');
var store = trans.objectStore('books');
// 全データ削除
var request = store.clear();
request.onsuccess = (event) => {
console.log('全データ削除成功');
};
request.onerror = (event) => {
console.log('全データ削除失敗:' + event.message);
};
「データ削除」とほぼ同じ。
違うところは、5行目の
store.clear()
これでオブジェクトストア内のデータがすべて消える。※オブジェクトストアは削除されない。
型は(以下略
ソースコード(HTML+TypeScript+JavaScript)
参考サイト
わからないところは、MDNで型(IDBObjectStoreなど)を検索し、「Example」を入ればだいたいわかるのでオススメ。
以上
written by @bc_rikko
0 件のコメント :
コメントを投稿