トップ » 技術記事 » API で覚える Adobe AIR(3) - データベースAPI(SQLite)を使ってみよう

API で覚える Adobe AIR(3) - データベースAPI(SQLite)を使ってみよう

タグ: ActionScript AIR SQLite

Adobe AIR が話題になっています。Adobe AIR を使えば、これまで使ってきた Web アプリケーションの技術、HTML/JavaScript や Flash/Flex を利用して、デスクトップアプリケーションを作ることができます。今回から、数回にわたって、Adobe AIR の API をテーマにして、AIR の各機能を紹介していきます。3回目の今回は、ローカルデータベース(SQLite)の扱いについて見ていきます。

Adobe AIRで使えるデータベースは SQLite

Adobe AIRではデータベースも利用できます。データベースとして利用できるのは、SQLiteでこれを利用することで、データの取扱いがずいぶん楽になります。

SQLiteは、組込用途に特化したデータベースです。1つのファイルが1つのデータベースと対応しているので、中小規模のデータを扱う場合には、威力を発揮します。また、SQLite は、SQL92のサブセットをサポートしますので、高度な条件を指定したデータの抽出などが可能です。

ここでは、ある程度データベースや、SQL の知識があるものとして説明しますが、それほど難しいことはしないので、SQL を知らない人でも、プログラムを読みながら使い方の感覚を掴んでいただければと思います。

SQLiteの利用手順を確認しよう

データベースを利用するためには、いくつかの処理ごとにイベントハンドラを定義し、処理を実行していきます。以下は、その手順ごとに箇条書きしたものです。

  • (1) データベースと接続する
  • (2) SQLを実行する
  • (3) 実行結果を処理する
SQLエディタの制作

では、手順を確認できるように、SQLiteを扱うサンプルプログラムを作ってみたいと思います。このアプリケーションは、アプリケーションごとのディレクトリに、test.db というデータベースファイルを作り、ここに適当なデータを挿入し、その内容を表示するものです。

また、画面の上部にSQLを入力し、SQL実行ボタンを押すと、実行結果を画面の下部に表示します。これを利用して、ちょっとしたSQLの実行テストを行うことができるようになっています。

http://aoikujira.com/demo/hakkaku/rc/20080504_sqltools.png

データベースとの接続

SQLiteはファイルにデータベースを構築します。そこで、データベースファイルを指定するために、データベースと接続するために、Fileオブジェクトを作成します。

そして、データベースと接続するのですが、データベースと接続が完了すると、イベントが起きて、接続完了を通知するようになっています。そこで、SQLConnection オブジェクトを作成したら、データベースと接続が完了した時のイベントハンドラを定義し、 openAsync() メソッドでデータベースとの接続を開始します。

// データベースファイルの指定
var a_file = new air.File("app-storage:/test.db");
// 非同期でデータベースと接続する
conn = new air.SQLConnection();
conn.addEventListener(air.SQLEvent.OPEN, onDBOpen);
conn.addEventListener(air.SQLErrorEvent.ERROR, onDBError);
conn.openAsync(a_file);

// 接続完了の時のイベント
function onDBOpen(event) {
    log_txt.value= "接続成功です";
}
// 接続エラー時のイベント
function onDBError(event) {
    log_txt.value = "失敗:"+event.error.details;
}

SQL文の実行

ここで作るプログラムでは、テーブルの作成、データの挿入、データの表示と、 SQL文を繰り返し実行することになるので、共通の関数execSQL()としてまとめています。

引数には、SQL文と、SQLの実行成功したときに実行する関数を指定します。

SQLの実行を行う場合も、データベースの接続と同じようにして、データベースからの結果を得るためのイベントハンドラを定義してから、実行を行います。

// SQLの実行
function execSQL(sql, closure) {
    if (!conn.connected) return;
    log_txt.value = "SQL=" + sql;
    // SQL文を実行するために SQLStatement のオブジェクトを作る
    stmt = new air.SQLStatement();
    stmt.sqlConnection = conn;
    stmt.addEventListener(air.SQLEvent.RESULT, closure);
    stmt.addEventListener(air.SQLErrorEvent.ERROR, onDBError);
    stmt.text = sql;
    stmt.execute();
}

以下は、この関数を呼び出す例で、データの表示ボタンを押した時に行うイベントハンドラです。実行したいSQLと、SQLの実行が成功したときの処理を指定します。以下は、SQLのSELECT文(データの抽出)を実行する場合です。


var sql = "SELECT * FROM score;";
execSQL(sql, showResult);

実行結果を取得する方法

そして、SELECT 文など、実行結果を表示する場合を見ていきましょう。SQLStatement で、SQL文が実行された後、 getResult()メソッドで結果(SQLResultオブジェクト)を得ることができます。

SQLResult の data プロパティで結果を取り出すことができます。 result.data は、Array型で、その各要素であるresult.data[n] が、 Object型になっています。

そのため、全ての値を取り出すには、for .. in 構文などを利用して以下のように記述できます。

function showResult(event) {
    var s = "";
    var result = stmt.getResult();
    if (result.data == null) {
        log_txt.value = "結果:" + result.complete;
        return;
    }
    for (var i = 0; i < result.data.length; i++) {
        var o = result.data[i];
        for (var col in o) {
            s += col + ":" + o[col] + "\n";
            air.trace(s);
        }
        s += "---\n";
    }
    log_txt.value = s;
}

つまり、上のプログラムで、result.data は次のような構造になっているということです。

result.data = [
  {id:1, name:"aaa", score:80},
  {id:2, name:"bbb", score:100},
  {id:3, name:"ccc", score:58},
  ..
];

完全なプログラム

以下が、完全なHTMLのソースです。

file:SQLiteEditor.html

<html><head><title>Test SQLite</title>
<meta http-equiv="content-type" content="text/html; charset=utf-8" />
</head>

<body bgcolor="#f0f0f0">
<!-- ui -->
<div>
    <div>サンプルを実行する</div>
    <input type="button" value="テーブル作成" onclick="sampleCreateTable()"/>

    <input type="button" value="ダミー挿入" onclick="sampleInsert()"/>
    <input type="button" value="データ表示" onclick="sampleSelect()"/>

    <br/>
    <textarea id="sql_txt" rows=12 cols=80></textarea><br/>
    <input type="button" value="SQL実行" onclick="execSQLClick()"/>

    <br/>
    <textarea id="log_txt" rows=12 cols=80></textarea><br/>
</div>
<!-- script -->
<script src="AIRAliases.js"></script>

<script>
function $(name) { return document.getElementById(name); }

// データベースファイルの指定
var a_file = new air.File("app-storage:/test.db");

// テキストフィールドの取得
var sql_txt = $("sql_txt");
var log_txt = $("log_txt");

// データベースと接続する
var conn; // 接続に使う変数    (SQLConnection)
var stmt; // SQL文の実行に使う (SQLStatement)

conn = new air.SQLConnection();
conn.addEventListener(air.SQLEvent.OPEN, onDBOpen);
conn.addEventListener(air.SQLErrorEvent.ERROR, onDBError);
conn.openAsync(a_file);

// 接続完了の時のイベント
function onDBOpen(event) {
    log_txt.value= "接続成功です";
}
// 接続エラー時のイベント
function onDBError(event) {
    log_txt.value = "失敗:"+event.error.details;
}
// SQLの実行
function execSQL(sql, closure) {
    if (!conn.connected) return;
    log_txt.value = "SQL=" + sql;
    // SQL文を実行するために SQLStatement のオブジェクトを作る
    stmt = new air.SQLStatement();
    stmt.sqlConnection = conn;
    stmt.addEventListener(air.SQLEvent.RESULT, closure);
    stmt.addEventListener(air.SQLErrorEvent.ERROR, onDBError);
    stmt.text = sql;
    stmt.execute();
}

// データベースからの結果の取得イベント
function showResult(event) {
    var s = "";
    var result = stmt.getResult();
    if (result.data == null) {
        log_txt.value = "結果:" + result.complete;
        return;
    }
    for (var i = 0; i < result.data.length; i++) {
        var o = result.data[i];
        for (var col in o) {
            s += col + ":" + o[col] + "\n";
            air.trace(s);
        }
        s += "---\n";
    }
    log_txt.value = s;
}

// SQLの実行ボタンを押したとき
function execSQLClick() {
    execSQL(sql_txt.value, showResult);
}

// サンプルを表示するボタンをクリックしたとき
var table = "score";
function sampleCreateTable() {
    var sample = "CREATE TABLE " + table + "(" +
        "  id INTEGER PRIMARY KEY," +
        "  name TEXT," +
        "  score INTEGER" +
        ");\n";
    sql_txt.value = sample;
    execSQLClick();
}
function sampleInsert() {
    var sample = "";
    for (var i = 0; i < 3; i++) {
        var r = Math.floor(Math.random() * 1000);
        sample += "INSERT INTO " + table +
            " (name,score) VALUES" +
            "('a" + r + "'," + r + ");\n";
    }
    sql_txt.value = sample;
    execSQLClick();
}
function sampleSelect() {
    var sample = "SELECT * FROM " + table + ";";
    sql_txt.value = sample;
    execSQLClick();
}

</script>
</body></html>
完全なプロジェクトファイル

完全なソースを含んだ、プロジェクトファイル一式を以下に置いておきます。参考にしてください。

http://aoikujira.com/demo/hakkaku/rc/20080504_sqlite-editor.zip

最後にAIR データベースのまとめ

SQLite を使ったデータベースは、1ファイル1データベースとなっており、非常に扱いやすいものになっています。アプリケーションの設定など、単純なデータなら、わざわざデータベースを使うまでもないかもしれません。しかし、ある程度大きなデータを扱う時や、データの検索が必要な場合などは、データベースを使うのが便利です。また、SQLite は、PHPやPerlなどからも利用できるフリーのデータベースなので、別のアプリケーションで作ったデータベースを、AIRで活用するといった使い方もできるかもしれません。

Series Navigation«ファイル関連APIを使ってみようAdobe AIRでクリップボードを操る»

執筆者紹介

クジラ飛行机

クジラ飛行机

くじらはんど(http://kujirahand/)にて、日本語プログラミング言語「なでしこ」(IPA未踏ユース採択)、テキスト音楽「サクラ」(OSPオンラインソフト大賞入賞)など多くのオンラインソフトを開発。著書に「Flexプロフェッショナルガイド」「なでしこ公式バイブル」、「一週間でマスターするActionScript3.0」など。

TrackBack URL :