截断会议室数据库表时如何解决错误

时间:2019-05-14 15:48:15

标签: android android-sqlite android-room

我想截断数据库中的所有表。我正在使用房间持久性库。我在单击按钮时调用truncateDatabase()方法。它有时可以成功完成工作,但有时会产生错误。我进行了很多搜索,但是有关此问题的资源很少。请帮助我解决问题。

我尝试了两种方法:

  1. 调用db.clearAllTables();
  2. 使用sql查询删除db.settingsDao()。deleteAll();

SettingsDao.class文件:

@Dao
 public interface SettingsDao {
    ... 
    @Query("DELETE FROM settings")
    void deleteAll();
    ...
}

这是AppDatabase文件的代码:

 @Database(entities = {Settings.class, ....}, version = 1, exportSchema = false)
public abstract class AppDatabase extends RoomDatabase {
    private static final String TAG = "AppDatabase";
    public static String DATABASE_NAME = ....;

    public abstract SettingsDao settingsDao();
    ....

    public static AppDatabase instance;

    public static synchronized AppDatabase getInstance(Context context) {
        if (instance == null) {
            instance = Room.databaseBuilder(context.getApplicationContext(),
                    AppDatabase.class, DATABASE_NAME)
                    .fallbackToDestructiveMigration()
                    .addCallback(roomCallback)
                    .build();
        }
        return instance;
    }

    .....

    public void truncateDatabase() {
        Log.d(TAG, "Truncate Database");
        if (isOpen()) {
            Log.d(TAG, "Database is opened");
            new TruncateAndInitializeAsyncTask(instance).execute();
        }
    }

    private class TruncateAndInitializeAsyncTask extends AsyncTask<Void, 
Void, Void> {
        AppDatabase db;

        private TruncateAndInitializeAsyncTask(AppDatabase db) {
            this.db = db;
        }

        @Override
        protected Void doInBackground(Void... voids) {
            Log.d(TAG, "Truncate tables from database "+isOpen()+db.isOpen());
            if (isOpen()) {
                Log.d(TAG, "Database is opened "+db.isOpen());
//                db.clearAllTables();
                try {
                    db.settingsDao().deleteAll();
                    ....
                }catch (Exception e){
                    e.printStackTrace();
                }
            }
            return null;
        }

        @Override
        protected void onPostExecute(Void aVoid) {
            super.onPostExecute(aVoid);
            ....
        }
    }
}

Logcat错误为:

D/AppDatabase: Truncate Database
D/AppDatabase: Database is opened
D/AppDatabase: Truncate tables from database truetrue
D/AppDatabase: Database is opened true
E/SQLiteLog: (1) no such table: room_table_modification_log
E/ROOM: Cannot run invalidation tracker. Is the db closed?
android.database.sqlite.SQLiteException: no such table: room_table_modification_log (code 1): , while compiling: INSERT OR IGNORE INTO room_table_modification_log VALUES(3, 0)
at android.database.sqlite.SQLiteConnection.nativePrepareStatement(Native Method)
    at android.database.sqlite.SQLiteConnection.acquirePreparedStatement(SQLiteConnection.java:889)
    at android.database.sqlite.SQLiteConnection.prepare(SQLiteConnection.java:500)
    at android.database.sqlite.SQLiteSession.prepare(SQLiteSession.java:588)
    at android.database.sqlite.SQLiteProgram.<init>(SQLiteProgram.java:58)
    at android.database.sqlite.SQLiteStatement.<init>(SQLiteStatement.java:31)
    at android.database.sqlite.SQLiteDatabase.executeSql(SQLiteDatabase.java:1678)
    at android.database.sqlite.SQLiteDatabase.execSQL(SQLiteDatabase.java:1608)
    at androidx.sqlite.db.framework.FrameworkSQLiteDatabase.execSQL(FrameworkSQLiteDatabase.java:242)
    at androidx.room.InvalidationTracker.startTrackingTable(InvalidationTracker.java:231)
    at androidx.room.InvalidationTracker.syncTriggers(InvalidationTracker.java:518)
    at androidx.room.RoomDatabase.beginTransaction(RoomDatabase.java:329)
    at ....Database.Dao.SettingsDao_Impl.deleteAll(SettingsDao_Impl.java:130)
    at ....Database.AppDatabase$TruncateAndInitializeAsyncTask.doInBackground(AppDatabase.java:336)
    at ....Database.AppDatabase$TruncateAndInitializeAsyncTask.doInBackground(AppDatabase.java:321)
    at android.os.AsyncTask$2.call(AsyncTask.java:333)
    at java.util.concurrent.FutureTask.run(FutureTask.java:266)
    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:245)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636)
    at java.lang.Thread.run(Thread.java:764)
W/System.err:     java.lang.IllegalStateException: The database '/data/user/0/.../databases/MONEY_MANAGER_DB' is not open.
W/System.err:     at android.database.sqlite.SQLiteDatabase.throwIfNotOpenLocked(SQLiteDatabase.java:2188)
W/System.err:     at android.database.sqlite.SQLiteDatabase.createSession(SQLiteDatabase.java:367)
W/System.err:     at android.database.sqlite.SQLiteDatabase$1.initialValue(SQLiteDatabase.java:86)
E/SQLiteLog: (1) no such table: room_table_modification_log
W/System.err:     at android.database.sqlite.SQLiteDatabase$1.initialValue(SQLiteDatabase.java:84)
W/System.err:     at java.lang.ThreadLocal.setInitialValue(ThreadLocal.java:180)
W/System.err:     at java.lang.ThreadLocal.get(ThreadLocal.java:170)
W/System.err:     at android.database.sqlite.SQLiteDatabase.getThreadSession(SQLiteDatabase.java:361)
W/System.err:     at android.database.sqlite.SQLiteProgram.getSession(SQLiteProgram.java:101)
W/System.err:     at android.database.sqlite.SQLiteStatement.executeUpdateDelete(SQLiteStatement.java:64)
W/System.err:     at androidx.sqlite.db.framework.FrameworkSQLiteStatement.executeUpdateDelete(FrameworkSQLiteStatement.java:46)
W/System.err:     at ....Database.Dao.SettingsDao_Impl.deleteAll(SettingsDao_Impl.java:132)
W/System.err:     at com....Database.AppDatabase$TruncateAndInitializeAsyncTask.doInBackground(AppDatabase.java:336)
W/System.err:     at com.....Database.AppDatabase$TruncateAndInitializeAsyncTask.doInBackground(AppDatabase.java:321)
W/System.err:     at android.os.AsyncTask$2.call(AsyncTask.java:333)
W/System.err:     at java.util.concurrent.FutureTask.run(FutureTask.java:266)
W/System.err:     at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:245)
W/System.err:     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162)
W/System.err:     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636)
E/ROOM: Cannot run invalidation tracker. Is the db closed?
android.database.sqlite.SQLiteException: no such table: room_table_modification_log (code 1): , while compiling: SELECT * FROM room_table_modification_log WHERE invalidated = 1;
        at android.database.sqlite.SQLiteConnection.nativePrepareStatement(Native Method)
    at android.database.sqlite.SQLiteConnection.acquirePreparedStatement(SQLiteConnection.java:889)
    at android.database.sqlite.SQLiteConnection.prepare(SQLiteConnection.java:500)
    at android.database.sqlite.SQLiteSession.prepare(SQLiteSession.java:588)
    at android.database.sqlite.SQLiteProgram.<init>(SQLiteProgram.java:58)
    at android.database.sqlite.SQLiteQuery.<init>(SQLiteQuery.java:37)
    at android.database.sqlite.SQLiteDirectCursorDriver.query(SQLiteDirectCursorDriver.java:44)
    at android.database.sqlite.SQLiteDatabase.rawQueryWithFactory(SQLiteDatabase.java:1318)
    at android.database.sqlite.SQLiteDatabase.rawQueryWithFactory(SQLiteDatabase.java:1293)
    at androidx.sqlite.db.framework.FrameworkSQLiteDatabase.query(FrameworkSQLiteDatabase.java:161)
    at androidx.room.RoomDatabase.query(RoomDatabase.java:305)
    at androidx.room.InvalidationTracker$1.checkUpdatedTable(InvalidationTracker.java:428)
    at androidx.room.InvalidationTracker$1.run(InvalidationTracker.java:400)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636)
    at java.lang.Thread.run(Thread.java:764)

0 个答案:

没有答案