こんにちは。きんくまです。
今回はAIRを使ってDBに挑戦してみようと思います。
私のDBスペックは、DBは業務で全く使ったことがなく、ちょびっと知識をかじったぐらい。
↓今回つくるやつ。テキスト入力欄にSQL文を書いてSQL実行ボタンを押すと一覧が表示されます。
今回の参考書です。
>> SQLの書き方のツボとコツがゼッタイにわかるドリル本―最初からそう教えてくれればいいのに!
>> Adobe AIR クックブック ―プロフェッショナルに学ぶRIAプログラミングの実践
データベースって何?
・簡単にいうと、表組みデータ(エクセルみたいの)。
・それを検索しやすくしたもの。
だと理解。
AIRには、データベースのSQLiteを使うことができるので、それを使って学習してみようと
思いました。
データベースを使う方法
1)データベースを作る(SQLiteの場合は1つのファイル)
2)データベースに接続する
3)テーブルを作る(1つのデータベースにいくつでも作れる)
4)テーブルにデータを挿入・更新・検索する
となります。それで、これをためせるプログラムを作りました。
AIR本を参考にいろいろと書き加えました。
Flex4が出てネット上でもニュースになってるので、
家にあったもののほとんど使ってなかったFlex3を使ってみました。
なんでmxmlです。
table情報を取得する方法がAIR本に載ってなかったので、ASDocから調べたらなんかできました。
loadSchema()やってから、getSchemaResult()やるみたい。
普通のSQLだとtable情報を調べるのもSQL文を書くんだけど、AIRはちょっとばかし
勝手が違うみたい。
■データベースのユーティリティクラス(ArrayCollectionをArrayに変更すれば普通のflaでも使用できます)
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 | package { import flash.data.SQLConnection; import flash.data.SQLResult; import flash.data.SQLSchemaResult; import flash.data.SQLStatement; import flash.data.SQLTableSchema; import flash.events.Event; import flash.events.EventDispatcher; import flash.events.SQLErrorEvent; import flash.events.SQLEvent; import flash.filesystem.File; import mx.collections.ArrayCollection; public class DBUtil extends EventDispatcher { private var _myDB:File; private var _isOpen: Boolean = false ; private var _dbConn:SQLConnection; private var _resultArrayCollection:ArrayCollection; public static const ASYNC_CONNECT_COMPLETE: String = "async_connect_complete" ; public static const ASYNC_SQL_COMPLETE: String = "async_sql_complete" ; public static const SCHEMA_COMPLETE: String = "schema_complete" ; public function get myDB():File { return _myDB; } public function get isOpen(): Boolean { return _isOpen; } public function get resultArrayCollection():ArrayCollection { return _resultArrayCollection; } public function DBUtil() { createLocalDB(); } public function createLocalDB(): void { var folder:File = File.applicationStorageDirectory.resolvePath( 'db' ); folder.createDirectory(); _myDB = folder.resolvePath( 'myDBFile.db' ); openLocalDB(_myDB, true ); } public function openLocalDB(dbFile:File, isAsync: Boolean ): void { _dbConn = new SQLConnection(); if (isAsync){ _dbConn.openAsync(dbFile); _dbConn.addEventListener(SQLEvent.OPEN, sqlOpenHD); _dbConn.addEventListener(SQLErrorEvent.ERROR, sqlOpenErrorHD); } else { try { _dbConn.open(dbFile); } catch (e:SQLErrorEvent){ trace ( 'SQL Error: ' + e.error.message); trace ( 'SQL Error Detail: ' + e.error.details); } } } public function sqlOpenHD(e:SQLEvent): void { _isOpen = true ; dispatchEvent( new Event(ASYNC_CONNECT_COMPLETE)); } public function sqlOpenErrorHD(e:SQLErrorEvent): void { _dbConn.removeEventListener(SQLEvent.OPEN, sqlOpenHD); _dbConn.removeEventListener(SQLErrorEvent.ERROR, sqlOpenErrorHD); //trace('SQL Error: ' + e.error.message); //trace('SQL Error Detail: ' + e.error.details); dispatchEvent(e); } public function sqlExcuteErrorHD(e:SQLErrorEvent): void { var state:SQLStatement = e.target as SQLStatement; state.removeEventListener(SQLEvent.RESULT, sqlStatementResultHD); state.removeEventListener(SQLErrorEvent.ERROR, sqlExcuteErrorHD); //trace('SQL Error: ' + e.error.message); //trace('SQL Error Detail: ' + e.error.details); dispatchEvent(e); } public function executeSQLState(sqlText: String ): void { if (isOpen == false ){ throw new Error( 'DB is not connected.' ); return ; } var state:SQLStatement = new SQLStatement(); state.sqlConnection = _dbConn; state.text = sqlText; state.addEventListener(SQLEvent.RESULT, sqlStatementResultHD); state.addEventListener(SQLErrorEvent.ERROR, sqlExcuteErrorHD); state.execute(); } private function sqlStatementResultHD(e:SQLEvent): void { var state:SQLStatement = e.target as SQLStatement; state.removeEventListener(SQLEvent.RESULT, sqlStatementResultHD); state.removeEventListener(SQLErrorEvent.ERROR, sqlExcuteErrorHD); var result:SQLResult = state.getResult(); var temp: Array = result.data is Array ? result.data : [{rows:result.rowsAffected}]; _resultArrayCollection = new ArrayCollection(temp); dispatchEvent( new Event(ASYNC_SQL_COMPLETE)); } public function getTableInfo(): void { _dbConn.addEventListener(SQLEvent.SCHEMA, sqlSchemaCompHD); _dbConn.addEventListener(SQLErrorEvent.ERROR, sqlSchemaErrorHD); _dbConn.loadSchema(); } private function sqlSchemaCompHD(e:SQLEvent): void { _dbConn.removeEventListener(SQLEvent.SCHEMA, sqlSchemaCompHD); _dbConn.removeEventListener(SQLErrorEvent.ERROR, sqlSchemaErrorHD); var result:SQLSchemaResult = _dbConn.getSchemaResult(); var tables: Array = result.tables; var temp: Array = []; for each ( var tableSchema:SQLTableSchema in tables){ temp.push({ database:tableSchema.database, name:tableSchema.name, sql:tableSchema.sql, columns:tableSchema.columns.length }); } _resultArrayCollection = new ArrayCollection(temp); dispatchEvent( new Event(SCHEMA_COMPLETE)); } private function sqlSchemaErrorHD(e:SQLErrorEvent): void { _dbConn.removeEventListener(SQLEvent.SCHEMA, sqlSchemaCompHD); _dbConn.removeEventListener(SQLErrorEvent.ERROR, sqlSchemaErrorHD); //trace('SQL Error: ' + e.error.message); //trace('SQL Error Detail: ' + e.error.details); dispatchEvent(e); } } } |
■そして、これを使う用のMXML
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 | <?xml version= "1.0" encoding= "utf-8" ?> <mx:WindowedApplication xmlns:mx= "http://www.adobe.com/2006/mxml" layout= "absolute" width= "620" height= "420" > <mx:Script> <![CDATA[ import mx.controls.Alert; import mx.collections.ArrayCollection; private var _dbUtil:DBUtil; [Bindable] private var _myResultAC:ArrayCollection; private function init(): void { excuteBtn.addEventListener(MouseEvent.CLICK, excuteSQLBtnClickHD); tableInfoBtn.addEventListener(MouseEvent.CLICK, tableInfoBtnClickHD); _dbUtil = new DBUtil(); _dbUtil.addEventListener(DBUtil.ASYNC_CONNECT_COMPLETE, dbAsyncCompHD); } private function tableInfoBtnClickHD(e:MouseEvent): void { _dbUtil.addEventListener(DBUtil.SCHEMA_COMPLETE, dbSchemaCompHD); _dbUtil.addEventListener(SQLErrorEvent.ERROR, dbSchemaErrorHD); _dbUtil.getTableInfo(); } private function dbSchemaErrorHD(e:SQLErrorEvent): void { _dbUtil.removeEventListener(DBUtil.SCHEMA_COMPLETE, dbSchemaCompHD); _dbUtil.removeEventListener(SQLErrorEvent.ERROR, dbSchemaErrorHD); Alert.show(e.error.message + '\n' + e.error.details); } private function dbSchemaCompHD(e:Event): void { _dbUtil.removeEventListener(DBUtil.SCHEMA_COMPLETE, dbSchemaCompHD); _dbUtil.removeEventListener(SQLErrorEvent.ERROR, dbSchemaErrorHD); _myResultAC = _dbUtil.resultArrayCollection; //Alert.show('table schema read complete'); } private function excuteSQLBtnClickHD(e:MouseEvent): void { _dbUtil.addEventListener(DBUtil.ASYNC_SQL_COMPLETE, dbSQLCompleteHD); _dbUtil.addEventListener(SQLErrorEvent.ERROR, dbSQLErrorHD); _dbUtil.executeSQLState(sqlInputTxt.text); } private function dbSQLErrorHD(e:SQLErrorEvent): void { _dbUtil.removeEventListener(DBUtil.ASYNC_SQL_COMPLETE, dbSQLCompleteHD); _dbUtil.removeEventListener(SQLErrorEvent.ERROR, dbSQLErrorHD); Alert.show(e.error.message + '\n' + e.error.details); } private function dbSQLCompleteHD(e:Event): void { _dbUtil.removeEventListener(DBUtil.ASYNC_SQL_COMPLETE, dbSQLCompleteHD); _dbUtil.removeEventListener(SQLErrorEvent.ERROR, dbSQLErrorHD); _myResultAC = _dbUtil.resultArrayCollection; //Alert.show('SQL excuted !'); } private function dbAsyncCompHD(e:Event): void { Alert.show( "SQL connection complete !" ); } ]]> </mx:Script> <mx:Panel x= "0" y= "0" width= "588" height= "388" layout= "absolute" title= "SQLTest" initialize= "init();" > <mx:DataGrid x= "10" y= "111" width= "548" height= "227" id= "myDG" dataProvider= "{_myResultAC}" /> <mx:Button x= "10" y= "81" label = "SQL実行" id= "excuteBtn" /> <mx:Button x= "88" y= "81" label = "table情報" id= "tableInfoBtn" /> <mx:TextArea x= "10" y= "10" width= "548" height= "63" id= "sqlInputTxt" wordWrap= "true" editable= "true" /> </mx:Panel> </mx:WindowedApplication> |
解説
1)データベースを作る(SQLiteの場合は1つのファイル)
2)データベースに接続する
の部分は、
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 | public function createLocalDB(): void { var folder:File = File.applicationStorageDirectory.resolvePath( 'db' ); folder.createDirectory(); _myDB = folder.resolvePath( 'myDBFile.db' ); openLocalDB(_myDB, true ); } public function openLocalDB(dbFile:File, isAsync: Boolean ): void { _dbConn = new SQLConnection(); if (isAsync){ _dbConn.openAsync(dbFile); _dbConn.addEventListener(SQLEvent.OPEN, sqlOpenHD); _dbConn.addEventListener(SQLErrorEvent.ERROR, sqlOpenErrorHD); } else { try { _dbConn.open(dbFile); } catch (e:SQLErrorEvent){ trace ( 'SQL Error: ' + e.error.message); trace ( 'SQL Error Detail: ' + e.error.details); } } } |
で、1つのDB用のファイル(myDBFile.db)を作って、同期か非同期で開くという感じです。
mxmlの方は起動したら、すでにここまでやってある状態にしました。
3)テーブルを作る(1つのデータベースにいくつでも作れる)
はテキスト入力欄に
CREATE TALBE test1( id INTEGER PRIMARY KEY, name TEXT, phone TEXT );
とか入力して、SQL実行ボタンを押せばテーブルが作成されます。
それで、ここでもAIR仕様があって、AIRのSQLiteでは使用可能な型がちょびっと変わってるみたいです。
>> ローカルデータベースでの SQL サポート – Adobe® Flex™ 3.2 リファレンスガイド データ型のサポート
SQL本によれば、INT型とかVARCHAR型とかいうのがあるみたいなんですけど、
AIRのSQLiteだとINTEGER型、TEXT型というふうになっとります。
tableをうまく作成したら、table情報ボタンをおします。そしたら、↓の画面のようになったらOK
4)テーブルにデータを挿入・更新・検索する
テーブルができたんで、データをいれてみましょう。
INSERT INTO test1 VALUES(null, '佐藤', '0123-45-6789');
とやってSQL実行ボタンをおして、エラーがでなければ成功
データを確認します。
SELECT * FROM test1;
とやって、一覧がでてきたらOKです。
注意点
AIRのSQLは他のSQLとは違う部分があるので、SQL文がうまく通らないなあと
思ったときは、下の仕様書のページで確認してみたほうがよさそうです。
■ 自作iPhoneアプリ 好評発売中!
・フォルメモ - シンプルなフォルダつきメモ帳
・ジッピー電卓 - 消費税や割引もサクサク計算!
■ LINEスタンプ作りました!
毎日使える。とぼけたウサギ