5

I'm using android.arch.work:work-runtime-ktx:1.0.1-rc1 and receiving many SQLiteException which I cannot reproduce.

The exception:

android.database.sqlite.SQLiteException: 
  at android.database.sqlite.SQLiteConnection.nativeOpen (Native Method)
  at android.database.sqlite.SQLiteConnection.open (SQLiteConnection.java:209)
  at android.database.sqlite.SQLiteConnection.open (SQLiteConnection.java:193)
  at android.database.sqlite.SQLiteConnectionPool.openConnectionLocked (SQLiteConnectionPool.java:463)
  at android.database.sqlite.SQLiteConnectionPool.open (SQLiteConnectionPool.java:185)
  at android.database.sqlite.SQLiteConnectionPool.open (SQLiteConnectionPool.java:177)
  at android.database.sqlite.SQLiteDatabase.openInner (SQLiteDatabase.java:808)
  at android.database.sqlite.SQLiteDatabase.open (SQLiteDatabase.java:793)
  at android.database.sqlite.SQLiteDatabase.openDatabase (SQLiteDatabase.java:696)
  at android.app.ContextImpl.openOrCreateDatabase (ContextImpl.java:652)
  at android.content.ContextWrapper.openOrCreateDatabase (ContextWrapper.java:289)
  at android.database.sqlite.SQLiteOpenHelper.getDatabaseLocked (SQLiteOpenHelper.java:223)
  at android.database.sqlite.SQLiteOpenHelper.getWritableDatabase (SQLiteOpenHelper.java:163)
  at androidx.sqlite.db.framework.FrameworkSQLiteOpenHelper$OpenHelper.getWritableSupportDatabase (FrameworkSQLiteOpenHelper.java:92)
  at androidx.sqlite.db.framework.FrameworkSQLiteOpenHelper.getWritableDatabase (FrameworkSQLiteOpenHelper.java:53)
  at androidx.room.RoomDatabase.endTransaction (RoomDatabase.java:340)
  at androidx.work.impl.utils.ForceStopRunnable.run (ForceStopRunnable.java:107)
  at java.util.concurrent.ThreadPoolExecutor.runWorker (ThreadPoolExecutor.java:1133)
  at java.util.concurrent.ThreadPoolExecutor$Worker.run (ThreadPoolExecutor.java:607)
  at java.lang.Thread.run (Thread.java:761)

Scheduling workers like that:

inline fun <reified T : Worker> schedule(interval: Long,
                                             units: TimeUnit,
                                             tag: String,
                                             networkConstraint: NetworkType? = null) {
            WorkManager.getInstance().apply {
                if (getWorkInfosByTag(tag).get()
                                .all { it.state == WorkInfo.State.CANCELLED || it.state == WorkInfo.State.FAILED }) {
                    // Cancel job by tag if the job already scheduled
                    cancelAllWorkByTag(tag)

                    // Create job and set tag
                    val job = PeriodicWorkRequestBuilder<T>(interval, units).addTag(tag)

                    // Set constraint if networkConstraint != null
                    networkConstraint?.let {
                        val constraints = Constraints.Builder()
                                .setRequiredNetworkType(networkConstraint)
                                .build()

                        job.setConstraints(constraints)
                    }

                    // Enqueue periodic job if no previous job with same tag is scheduled.
                    enqueueUniquePeriodicWork(
                            tag,
                            ExistingPeriodicWorkPolicy.KEEP,
                            job.build())
                }
            }
    }

If it is important, the scheduling of one of the workers is performed once in Application#onCreate() and another worker is scheduled later on after user interactions.

The workers themselves look like this:

internal class SiloWorker(context: Context, params: WorkerParameters)
    : Worker(context, params) {
    override fun doWork(): Result {
        if (isAppInBackground)
            return Result.success()

        doIntenseDatabaseAndNetworkIOOperations()

        return Result.success()
    }
}

and are scheduled to run every 15 minutes.

Another strange thing is that I receive these exceptions only on "Android Vitals" tab of Google Play Console, but I found none of them in Firebase crashlytics.

I don't know whether these SQLiteExceptions occur in foreground or in background and there are many devices with different Android versions that are affected by this exception.

What are possible reasons of this behaviour and how can I fix it?

cora32
  • 388
  • 3
  • 15
  • 1
    The issue seems related to opening the database. How long does the `doIntenseDatabaseAndNetworkIOOperations()` should take on average and on maximum? Given that you cancel your own work (and you've constraints that can change during the execution of the work) it's probably a good idea to add some handling of work's cancellation as described in the [documentation](https://developer.android.com/topic/libraries/architecture/workmanager/how-to/cancel-stop-work). – pfmaggi Apr 20 '19 at 10:49
  • I have an issue closed to you. I'm using WorkManager "2.2.0". But that only happen in Samsung Galaxy S10. Have you have any idea? The release we make, do not make any changes on library version in build.gradle. The only significant change, is we did a DB migration on our own DB (Using Room 2.1.0). Not sure whether this is related to each other. – Cheok Yan Cheng Jan 01 '20 at 15:25
  • Maybe this answer will help : https://stackoverflow.com/a/52605503/6084216 – Эльбек Джураев Feb 06 '20 at 12:20

1 Answers1

1

We made a lot of improvements around this area in 2.1.0-alpha03. Try giving that version a go.

Rahul
  • 19,744
  • 1
  • 25
  • 29
  • I have an issue closed to OP. I'm using WorkManager "2.2.0". But that only happen in Samsung Galaxy S10. Have you have any idea? The release we make, do not make any changes on library version in build.gradle. The only significant change, is we did a DB migration on our own DB (Using Room 2.1.0). Not sure whether this is related to each other. – Cheok Yan Cheng Jan 01 '20 at 15:27
  • @rahul I'm using WorkManager 2.3.4 and experience the same crash, when I try to setup periodic work in Application onCreate. I also use on demand initialization if this info helps. – Lingviston May 20 '20 at 08:27
  • 1
    Upgrading to 2.3.4 fixed this issue for our app. We are using an WorkManager.enqueueUniquePeriodicWork call. For more info see: https://issuetracker.google.com/issues/145231177 – mtkopone Jul 06 '20 at 10:08