https://kotlinlang.org logo
#coroutines
Title
# coroutines
f

Florian

10/29/2020, 3:33 PM
I have a DialogFragment that executes some db delete operation (via its own ViewModel). Since a dialog dismisses immediately when you click a button, it makes sense to use applicationScope instead of viewModelScope, correct?
Copy code
class DeleteAllCompletedViewModel @ViewModelInject constructor(
    private val taskDao: TaskDao,
    @ApplicationScope private val applicationScope: CoroutineScope
) :
    ViewModel() {

    fun deleteCompletedTasks() = applicationScope.launch {
        taskDao.deleteCompletedTasks()
    }
}
i

Ian Lake

10/29/2020, 4:05 PM
Or use
launch(NonCancellable)
f

Florian

10/29/2020, 4:27 PM
Thanks, but the article by Manuel Vivo advises against this quite strongly: https://medium.com/androiddevelopers/coroutines-patterns-for-work-that-shouldnt-be-cancelled-e26c40f142ad#aa9c
i

Ian Lake

10/29/2020, 6:37 PM
Most of those downsides don't apply to this particular case, but I agree with the general principle there
l

louiscad

10/29/2020, 6:37 PM
I'd use WorkManager for that, or a custom idempotent and tested mechanism
f

Florian

10/29/2020, 6:55 PM
It doesn't apply because I'm calling the dao directly and we don't expect to get any weird behavior from Room? I guess if I had a repository in between it would already be problematic.
Regarding WorkManager, I am not sure if I should use it for an operation that will probably take only a few milliseconds
l

louiscad

10/29/2020, 7:17 PM
One could argue that since WorkManager implies writing to a db, it doesn't make sense to use it for a trivial db operation (single query with tiny tiny implications like a delete operation). In that case, launching a fire and forget coroutine in the
GlobalScope
or a custom
AppScope
might be the most pragmatic solution.
f

Florian

10/29/2020, 7:22 PM
Globalscope would be easiest, but it's also discouraged in the article above. So I've created my own applicationScope but it feels kinda pointless 😆
l

louiscad

10/29/2020, 7:28 PM
GlobalScope is still there for a reason, and can suit your particular use case, though it's almost never a good solution for the vast majority of coroutines use cases (shareIn excepted)
i

Ian Lake

10/29/2020, 7:37 PM
The only actual concern that applies here is the testing story - can you assert that the deletion occurs. GlobalScope or
NonCancellable
means you rely on the signal from the database to know when that operation finishes, while injecting some scope lets you wait for its work to complete. If you aren't doing that specific kind of testing though, then the shortest, most concise code gets my vote 🤷
l

louiscad

10/29/2020, 7:38 PM
One can call
join()
on
GlobalScope.launch { … }
no problem
5 Views