房间持久性错误
Room Persistance Error
我有一个在生产模式下使用 Room 持久性的应用程序。似乎当我尝试更新 table 我在某些设备上出现以下错误:我与数据库的连接一直打开,只有在销毁时我才释放数据库。
这是我的服务,每 12 小时运行一次
这是服务:https://gist.github.com/anonymous/8fac7650b34aa19229d5f6b91d2454d4
资料库:
https://gist.github.com/anonymous/70c524c1e8eb5e7ed893131a9c685b5b
应用数据库
https://gist.github.com/anonymous/ccb20853054fa5d453592fd2653a4dc4
错误:
java.lang.IllegalStateException:
at android.database.sqlite.SQLiteDatabase.throwIfNotOpenLocked
(SQLiteDatabase.java:2199)
at android.database.sqlite.SQLiteDatabase.createSession
(SQLiteDatabase.java:379)
at android.database.sqlite.SQLiteDatabase.initialValue
(SQLiteDatabase.java:92)
at android.database.sqlite.SQLiteDatabase.initialValue
(SQLiteDatabase.java:89)
at java.lang.ThreadLocal$Values.getAfterMiss (ThreadLocal.java:430)
at java.lang.ThreadLocal.get (ThreadLocal.java:65)
at android.database.sqlite.SQLiteDatabase.getThreadSession
(SQLiteDatabase.java:373)
at android.database.sqlite.SQLiteProgram.getSession (SQLiteProgram.java:101)
at android.database.sqlite.SQLiteStatement.executeUpdateDelete
(SQLiteStatement.java:64)
at android.arch.persistence.db.framework.FrameworkSQLiteStatement.executeUpdateDelete (FrameworkSQLiteStatement.java:75)
at android.arch.persistence.room.EntityDeletionOrUpdateAdapter.handle (EntityDeletionOrUpdateAdapter.java:69)
at mbc.analytics.sdk.room.dao.TimeDao_Impl.updateTimeModel (TimeDao_Impl.java:122)
at mbc.analytics.sdk.room.database.DatabaseRepository.createTimeEntity (DatabaseRepository.java:211)
at mbc.analytics.sdk.room.database.DatabaseRepository.createAppEntity (DatabaseRepository.java:56)
at mbc.analytics.sdk.services.LollipopService.getStats (LollipopService.java:202)
at mbc.analytics.sdk.services.LollipopService.access0 (LollipopService.java:39)
at mbc.analytics.sdk.services.LollipopService.run (LollipopService.java:153)
at java.util.concurrent.ThreadPoolExecutor.runWorker (ThreadPoolExecutor.java:1112)
at java.util.concurrent.ThreadPoolExecutor$Worker.run (ThreadPoolExecutor.java:587)
at java.lang.Thread.run (Thread.java:818)
DatabaseRepository
正在结束对 Room.databaseBuilder()
的调用。由于这是使用单例实现的,因此您将在对 databaseRepository.databaseClose();
的调用中关闭数据库,但不会再次打开。在您的代码中创建新的 DatabaseRepository
没有帮助,因为 AppDatabase.getAppDatabase(ctx);
将 return 同一个关闭的数据库。
因此,可能的解决方案是:
- 删除对
databaseRepository.databaseClose();
的调用,因为该服务 运行 与您的其他活动位于同一个 Application
内,并且数据库是(并且应该)共享的。 这是我认为的首选解决方案。
- 另一种方法是
DatabaseRepository#databaseClose()
也通过调用 AppDatabase.destroyInstance();
销毁数据库对象。对我来说,这可能会带来其他问题,例如并发问题、保留对旧数据库对象的引用(例如在 activity 中)等
第二个代码,不推荐解决方案:
public void databaseClose() {
if (db.isOpen()) {
db.close();
AppDatabase.destroyInstance();
}
}
我有一个在生产模式下使用 Room 持久性的应用程序。似乎当我尝试更新 table 我在某些设备上出现以下错误:我与数据库的连接一直打开,只有在销毁时我才释放数据库。
这是我的服务,每 12 小时运行一次
这是服务:https://gist.github.com/anonymous/8fac7650b34aa19229d5f6b91d2454d4 资料库: https://gist.github.com/anonymous/70c524c1e8eb5e7ed893131a9c685b5b 应用数据库 https://gist.github.com/anonymous/ccb20853054fa5d453592fd2653a4dc4
错误:
java.lang.IllegalStateException:
at android.database.sqlite.SQLiteDatabase.throwIfNotOpenLocked
(SQLiteDatabase.java:2199)
at android.database.sqlite.SQLiteDatabase.createSession
(SQLiteDatabase.java:379)
at android.database.sqlite.SQLiteDatabase.initialValue
(SQLiteDatabase.java:92)
at android.database.sqlite.SQLiteDatabase.initialValue
(SQLiteDatabase.java:89)
at java.lang.ThreadLocal$Values.getAfterMiss (ThreadLocal.java:430)
at java.lang.ThreadLocal.get (ThreadLocal.java:65)
at android.database.sqlite.SQLiteDatabase.getThreadSession
(SQLiteDatabase.java:373)
at android.database.sqlite.SQLiteProgram.getSession (SQLiteProgram.java:101)
at android.database.sqlite.SQLiteStatement.executeUpdateDelete
(SQLiteStatement.java:64)
at android.arch.persistence.db.framework.FrameworkSQLiteStatement.executeUpdateDelete (FrameworkSQLiteStatement.java:75)
at android.arch.persistence.room.EntityDeletionOrUpdateAdapter.handle (EntityDeletionOrUpdateAdapter.java:69)
at mbc.analytics.sdk.room.dao.TimeDao_Impl.updateTimeModel (TimeDao_Impl.java:122)
at mbc.analytics.sdk.room.database.DatabaseRepository.createTimeEntity (DatabaseRepository.java:211)
at mbc.analytics.sdk.room.database.DatabaseRepository.createAppEntity (DatabaseRepository.java:56)
at mbc.analytics.sdk.services.LollipopService.getStats (LollipopService.java:202)
at mbc.analytics.sdk.services.LollipopService.access0 (LollipopService.java:39)
at mbc.analytics.sdk.services.LollipopService.run (LollipopService.java:153)
at java.util.concurrent.ThreadPoolExecutor.runWorker (ThreadPoolExecutor.java:1112)
at java.util.concurrent.ThreadPoolExecutor$Worker.run (ThreadPoolExecutor.java:587)
at java.lang.Thread.run (Thread.java:818)
DatabaseRepository
正在结束对 Room.databaseBuilder()
的调用。由于这是使用单例实现的,因此您将在对 databaseRepository.databaseClose();
的调用中关闭数据库,但不会再次打开。在您的代码中创建新的 DatabaseRepository
没有帮助,因为 AppDatabase.getAppDatabase(ctx);
将 return 同一个关闭的数据库。
因此,可能的解决方案是:
- 删除对
databaseRepository.databaseClose();
的调用,因为该服务 运行 与您的其他活动位于同一个Application
内,并且数据库是(并且应该)共享的。 这是我认为的首选解决方案。 - 另一种方法是
DatabaseRepository#databaseClose()
也通过调用AppDatabase.destroyInstance();
销毁数据库对象。对我来说,这可能会带来其他问题,例如并发问题、保留对旧数据库对象的引用(例如在 activity 中)等
第二个代码,不推荐解决方案:
public void databaseClose() {
if (db.isOpen()) {
db.close();
AppDatabase.destroyInstance();
}
}