今度からSQLiteOpenHelperのDatabaseHelperのインスタンス取得はSingletonパターンにするよ・・・
SQLiteDatabaseLockedExceptionなるエラーが出たんですけど、
android.database.sqlite.SQLiteDatabaseLockedException
java.lang.RuntimeException: An error occured while executing doInBackground()
at android.support.v4.content.ModernAsyncTask$3.done(ModernAsyncTask.java:137)
at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273)
at java.util.concurrent.FutureTask.setException(FutureTask.java:124)
at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307)
at java.util.concurrent.FutureTask.run(FutureTask.java:137)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1076)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:569)
at java.lang.Thread.run(Thread.java:856)
Caused by: android.database.sqlite.SQLiteDatabaseLockedException: database is locked
at android.database.sqlite.SQLiteDatabase.dbopen(Native Method)
at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:1135)
at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:1086)
at android.database.sqlite.SQLiteOpenHelper.getReadableDatabase(SQLiteOpenHelper.java:241)
at xxxxx my content provider pgm xxxxxxxxxxx.query(xxxxxxxxx.java:181)
at android.content.ContentProvider$Transport.query(ContentProvider.java:178)
at android.content.ContentResolver.query(ContentResolver.java:317)
at android.support.v4.content.CursorLoader.loadInBackground(CursorLoader.java:49)
at android.support.v4.content.CursorLoader.loadInBackground(CursorLoader.java:35)
at android.support.v4.content.AsyncTaskLoader.onLoadInBackground(AsyncTaskLoader.java:240)
at android.support.v4.content.AsyncTaskLoader$LoadTask.doInBackground(AsyncTaskLoader.java:51)
at android.support.v4.content.AsyncTaskLoader$LoadTask.doInBackground(AsyncTaskLoader.java:40)
at android.support.v4.content.ModernAsyncTask$2.call(ModernAsyncTask.java:123)
at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)
... 4 more
調べていたら、複数のSQLiteOpenHelperインスタンスが同じデータベースにマルチスレッドで
アクセスしているからでした。
参考サイトさま
Android:1つのDBに複数のContentProvider
Androidのデータベース周りでよくわからないエラーが出る
Android - ContentProviderとSQLite
Using Singleton design pattern for SQLiteDatabase
頻繁にDBにアクセスしないプログラムなら大丈夫だろうけど、念のため
今後はシングルトンパターンにしますよ。
(追記)スレッドセーフにするために、getInstance()メソッドはsynchronizedを指定しておくのも忘れてはいけませんね。(@yusukeさまどうもありがとうございました。)
SQLiteOpenHelperのサブクラス
public class DatabaseHelper extends SQLiteOpenHelper { private static DatabaseHelper sSingleton = null; public static synchronized DatabaseHelper getInstance(Context context) { if (sSingleton == null) { sSingleton = new DatabaseHelper(context); } return sSingleton; } private DatabaseHelper(Context context) { super(context, DatabaseManager.DATABASE_NAME, null, DatabaseManager.DATABASE_VERSION); }
データベースを使用する側
private DatabaseHelper mDBHelper; @Override public boolean onCreate() { mDBHelper = DatabaseHelper.getInstance(getContext()); return true; }