java - 使用SQLite的Android中的外键约束? 在删除级联

我有两个表:轨道和航点,一个轨道可以有很多航点,但一个航点只分配给一个轨道。

在点数表中,我有一个名为“trackidfk”的列,它在制作轨道时插入track_ID,但是我没有在此列上设置外键约束。

当我删除一条轨道时,我想删除指定的路标,这可能吗? 我读过有关使用触发器的内容,但我不认为它们在Android中受支持。

要创建航点表:

public void onCreate(SQLiteDatabase db) {
db.execSQL( "CREATE TABLE " + TABLE_NAME
+ " ("
+ _ID + " INTEGER PRIMARY KEY AUTOINCREMENT, "
+ LONGITUDE + " INTEGER,"
+ LATITUDE + " INTEGER,"
+ TIME + " INTEGER,"
+ TRACK_ID_FK + " INTEGER"
+ " );"
);
...
}


支持使用on delete cascade的外键约束,但您需要启用它们。

我刚刚将以下内容添加到我的SQLOpenHelper中,这似乎可以解决问题。

@Override
public void onOpen(SQLiteDatabase db) {
super.onOpen(db);
if (!db.isReadOnly()) {
// Enable foreign key constraints
db.execSQL("PRAGMA foreign_keys=ON;");
}
}

我将我的引用列声明如下。

mailbox_id INTEGER REFERENCES mailboxes ON DELETE CASCADE


由于Android 4.1(API 16)SQLiteDatabase支持:

public void setForeignKeyConstraintsEnabled (boolean enable)


正如e.shishkin的帖子从API 16开始说的那样你应该使用db.setForeignKeyConstraintsEnabled(boolean)在SqLiteOpenHelper.onConfigure(SqLiteDatabase)方法中启用外键约束

@Override

public void onConfigure(SQLiteDatabase db){

db.setForeignKeyConstraintsEnabled(true);

}


用更完整的答案回答问题永远不会过于陈旧。

@Override public void onOpen(SQLiteDatabase db) {
super.onOpen(db);
if (!db.isReadOnly()) {
setForeignKeyConstraintsEnabled(db);
}
mOpenHelperCallbacks.onOpen(mContext, db);
}
private void setForeignKeyConstraintsEnabled(SQLiteDatabase db) {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
setForeignKeyConstraintsEnabledPreJellyBean(db);
} else {
setForeignKeyConstraintsEnabledPostJellyBean(db);
}
}
private void setForeignKeyConstraintsEnabledPreJellyBean(SQLiteDatabase db) {
db.execSQL("PRAGMA foreign_keys=ON;");
}
@TargetApi(Build.VERSION_CODES.JELLY_BEAN)
private void setForeignKeyConstraintsEnabledPostJellyBean(SQLiteDatabase db) {
db.setForeignKeyConstraintsEnabled(true);
}


无论@phil提到什么都是好的。 但您可以使用其他可用的默认方法      数据库本身设置外键。 那就是setForeignKeyConstraintsEnabled(true)。

@Override
public void onOpen(SQLiteDatabase db) {
super.onOpen(db);
if (!db.isReadOnly()) {
// Enable foreign key constraints
db.execSQL("PRAGMA foreign_keys=ON;");
//(OR)
db.setForeignKeyConstraintsEnabled (true)
}
}

对于Docs,请参阅SQLiteDatabase.setForeignKeyConstraintsEnabled


我不认为SQLite支持开箱即用。 我在我的应用程序中所做的是:

创建交易

删除详细数据(示例中的航点)

删除主数据(示例中的轨道)

提交成功交易

这样我确定所有数据都被删除或没有。


android支持触发器,sqlite不支持这种类型的级联删除。 可以在此处找到在android上使用触发器的示例。 尽管像Thorsten所说的那样使用交易可能就像触发器一样容易。


android 1.6中的SQLite版本是3.5.9所以它不支持外键...

[http://www.sqlite.org/foreignkeys.html]“本文档描述了对SQLite版本3.6.19中引入的SQL外键约束的支持。”

在Froyo中它是SQLite版本3.6.22,所以......

编辑:看sqlite版本:adb shell sqlite3 -version


在Android 2.2及更高版本的SQLite中支持具有“on delete cascade”的外键。 但是在使用它们时要小心:有时在一列上触发一个外键时会报告错误,但真正的问题在于子表中的另一个列外键约束,或者其他一些表引用该表。

看起来SQLite在启动其中一个时会检查所有约束。 它实际上在文档中提到过。 DDL与DML约束检查。