web-dev-qa-db-ja.com

存在しない場合はsqlitedbに列を追加します-flex / air sqlite?

私が取り組んできたflex/airアプリがあります。これは、アプリケーションの最初の起動時に作成されたローカルsqliteデータベースを使用します。

アプリケーションにいくつかの機能を追加しましたが、その過程でデータベーステーブルの1つに新しいフィールドを追加する必要がありました。私の質問は、アプリケーションに、既存のテーブルにある1つの新しいフィールドを作成させる方法です。

これはテーブルを作成する行です

stmt.text = "CREATE TABLE IF NOT EXISTS tbl_status ("+"status_id INTEGER PRIMARY KEY AUTOINCREMENT,"+" status_status TEXT)";

そして、status_defaultフィールドを追加したいと思います。

ありがとう!

ありがとう-MPelletier

指定したコードを追加しましたが、フィールドは追加されていますが、次にアプリを再起動すると、エラーが発生します-「status_default」はすでに存在します。

では、指定した行にある種のIF NOT EXISTSステートメントを追加するにはどうすればよいですか?

12
Adam
_ALTER TABLE tbl_status ADD COLUMN status_default TEXT;
_

http://www.sqlite.org/lang_altertable.html

そうは言っても、SQLiteでの列の追加には制限があります。テーブルの最後の列の後以外に列を追加することはできません。

列がすでに存在するかどうかの確認に関しては、PRAGMA table_info(tbl_status);はテーブルのさまざまな列をリストしたテーブルを返します。

拡張機能:

私はデータベース設計で、どの変更が必要かを区別できる戦略を使用してきました。このためには、1つのフィールド(整数、DBInfoと呼びます)を持つ新しいテーブル(SchemaVersionと呼びます)が必要になります。または、SQLiteには_user_version_という内部値もあります。これは PRAGMA コマンドで設定できます。コードは、プログラムの起動時にスキーマのバージョン番号を確認し、それに応じて一度に1つのバージョンで変更を適用できます。

UpdateDBSchema()という名前の関数があるとします。この関数は、データベーススキーマのバージョンをチェックし、DBInfoが存在しないことを処理し、データベースがバージョン0にあることを確認します。この関数の残りの部分は、ループ(または利用可能な他の構造)にネストされた、異なるバージョンの大きなスイッチである可能性があります選択したプラットフォームに)。

したがって、この最初のバージョンでは、UpgradeDBVersion0To1()関数を使用して、この新しいテーブル(DBInfo)を作成し、_status_default_フィールドを追加して、SchemaVersionをに設定します。 1.コードに、最新のスキーマバージョンを示す定数(たとえば_LATEST_DB_VERSION_)を追加し、1に設定します。こうすることで、コードとデータベースにスキーマバージョンがあり、同期する必要があることがわかります。それらが等しくない場合、それら。

スキーマに別の変更を加える必要がある場合は、_LATEST_DB_VERSION_定数を2に設定し、必要な変更を実行する新しいUpgradeDBVersion1To2()関数を作成します。

そうすれば、プログラムを簡単に移植したり、古いデータベースに接続してアップグレードしたりすることができます。

32
MPelletier

私はこれが古い質問であることを知っています...しかし。

私はAdobeAIRのSQLite実装でこの正確な問題にぶつかりました。 PRAGMAコマンドを使用して解決できると思いましたが、Adobe Airの実装ではPRAGMAコマンドがサポートされていないため、別の方法が必要です。

私がしたこと、ここで共有する価値があると思ったのは、これです:

var sql:SQLStatement = new SQLStatement();
sql.sqlConnection = pp_db.dbConn;
sql.text = "SELECT NewField FROM TheTable";
sql.addEventListener(SQLEvent.RESULT, function(evt:SQLEvent):void {
});

sql.addEventListener(SQLErrorEvent.ERROR, function(err:SQLErrorEvent):void {
    var sql:SQLStatement = new SQLStatement();
    sql.sqlConnection = pp_db.dbConn;
    sql.text = "ALTER TABLE TheTable ADD COLUMN NewField NUMERIC;";
    sql.execute();
    sql.addEventListener(SQLEvent.RESULT, function (evt:SQLEvent):void {
    });
});
sql.execute();

それが誰かを助けることを願っています。

3
stevesweets

私はこの質問からの答えを使用して同様の問題を解決しました: SQLiteに存在しない場合はALTER TABLE ADD COLUMN

組み込みのuser_versionパラメーターを使用して、更新を追跡します。次を使用して設定します。

PRAGMA user_version = 1

を使用して取得します

PRAGMA user_version

したがって、基本的にuser_version(デフォルトでは0)を取得し、0かどうかを確認します。はいの場合は、更新を実行して1に設定します。今後さらに更新がある場合は、1かどうかを確認し、更新を実行して0に設定します。等々...

0
Eternal21

場合によっては、コマンドを実行して「列の重複」の例外が発生します。ただの迅速な解決策であり、完璧ではありません。

0
Seraphim's