2013-11-21 55 views
3

我正在創建一個數據庫,引用另一個數據庫中的鍵的過程。從本質上講,我有一個數據導入,我想保持與將會更改的數據分開,但如果可能,我想通過FOREIGN KEY引用其他密鑰。據我所知,我需要首先附加數據庫才能實現這一點。這裏是德相關的代碼至今:Android與SQLiteOpenHelper ATTACH sqlite數據庫

public class LogDatabaseHelper extends SQLiteOpenHelper { 

    private static final String DATABASE_NAME = "log.db"; 
    private static final int DATABASE_VERSION = 1; 
    private String namesDb; 

    public LogDatabaseHelper(Context context) { 
     super(context, DATABASE_NAME, null, DATABASE_VERSION); 
     namesDb=getNamesDbPath(); 

    } 

    @Override 
    public void onCreate(SQLiteDatabase db) { 
     db.execSQL("ATTACH DATABASE ? AS names",new String[]{namesDb}); 
     StringBuilder query=new StringBuilder(); 
     query.append("CREATE TABLE log ("); 
    } 
} 

然而,這似乎並沒有工作,因爲我得到了以下錯誤:

11-21 17:35:58.176: E/SQLiteLog(9984): (1) statement aborts at 5: [ATTACH DATABASE ? AS names] cannot ATTACH database within transaction 
11-21 17:35:58.176: D/AndroidRuntime(9984): Shutting down VM 
11-21 17:35:58.176: W/dalvikvm(9984): threadid=1: thread exiting with uncaught exception (group=0x41a21700) 
11-21 17:35:58.191: E/AndroidRuntime(9984): FATAL EXCEPTION: main 
11-21 17:35:58.191: E/AndroidRuntime(9984): android.database.sqlite.SQLiteException: cannot ATTACH database within transaction (code 1) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteConnection.nativeExecuteForChangedRowCount(Native Method) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteConnection.executeForChangedRowCount(SQLiteConnection.java:734) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteSession.executeForChangedRowCount(SQLiteSession.java:754) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteStatement.executeUpdateDelete(SQLiteStatement.java:64) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteDatabase.executeSql(SQLiteDatabase.java:1674) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteDatabase.execSQL(SQLiteDatabase.java:1603) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at com.kd7uiy.hamfinder.LogDatabaseHelper.onCreate(LogDatabaseHelper.java:27) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteOpenHelper.getDatabaseLocked(SQLiteOpenHelper.java:252) 
11-21 17:35:58.191: E/AndroidRuntime(9984):  at android.database.sqlite.SQLiteOpenHelper.getWritableDatabase(SQLiteOpenHelper.java:164) 

我怎樣才能使這項工作?

+1

您可能需要跳過'SQLiteOpenHelper'或分叉它。在後一種情況下,要麼刪除包裝'onCreate()'的標準事務(自己處理它),要麼讓自己有機會在任何事務邊界之外運行'ATTACH'。 – CommonsWare

回答

4

我想出了一種方法來使它工作,我並不特別自豪,但它做到了。如果您在連接數據庫時無法進行事務處理,請先結束事務。

db.setTransactionSuccessful(); 
db.endTransaction(); 
db.execSQL("ATTACH DATABASE ? AS names",new String[]{namesDb}); 
db.beginTransaction(); 
+0

您是否能夠與附加的數據庫進行交互?我也是這樣做的,但是當我引用附加的數據庫時,我得到一個*沒有這樣的表*錯誤(例如:'SELECT * FROM names.mytable'。 – Phil

+0

我最終拒絕了這個,轉而採用完全不同的方式但是,我回到它,我會讓你知道,如果它的工作... – PearsonArtPhoto

+0

這是行不通的。我在onUpgrade()上使用此代碼,我得到這個錯誤「如果我不使用「db.setTransactionSuccessful()」,「db.endTransaction()」,「db.beginTransaction()」,那麼出現這個錯誤「無法在數據庫中附加數據庫」交易「 –

0

我有同樣的問題時,我想連接數據庫,同時更新數據庫,我所做的只是改變一個靜態全局變量時的onUpdate()被調用,右後this.getReadableDatabase()或this.getWritableDatabase ()(實際上是調用onCreate/onUpdate方法的函數)我檢查全局變量的值並運行包含attach函數的整個代碼。這樣你就不用在onCreate()或onUpgrade()方法中附加內容,而是在執行它們之後。

我不確定這種方法在指定的情況下是否可用,但我只是想我會提及如果別人碰到這個問題,我會如何解決它。

+0

我在onUpgrade()方法中有同樣的問題,我嘗試了很多解決方案但沒有成功。請詳細說明。 –