Reputation: 23
I have a fragment, viewmodel and database. I call this method in the viewModel from the fragment which deletes data from database by a list of id's.
fun deleteDefects(idList: List<Long>) {
Log.d("RoundViewModel", idList.toString())
viewModelScope.launch(Dispatchers.IO) {
Log.d("RoundViewModel", idList.toString())
ddb.dao().delAddedDefect(idList)
}
}
It works.. sometimes, about 2 or 3 times out of 10, deletes data. And sometimes idList in launch is empty.
2020-06-26 18:40:44.461 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [259, 260]
2020-06-26 18:40:44.464 18524-18555/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:40:47.453 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [264, 267]
2020-06-26 18:40:47.457 18524-18555/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:40:50.838 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [276, 267]
2020-06-26 18:40:50.841 18524-18555/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:40:53.896 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [276, 267, 264]
2020-06-26 18:40:53.899 18524-18555/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:40:56.947 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [259, 260, 264]
2020-06-26 18:40:56.950 18524-18555/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:41:00.023 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [264, 265, 267]
2020-06-26 18:41:00.027 18524-18554/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:41:02.731 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [264, 265]
2020-06-26 18:41:02.733 18524-18554/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:41:08.200 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [277, 267]
2020-06-26 18:41:08.201 18524-18554/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:41:11.694 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [264, 259]
2020-06-26 18:41:11.695 18524-18554/ru.debaser.projects.inspectionsheet D/RoundViewModel: [264, 259]
2020-06-26 18:41:19.528 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [265, 267]
2020-06-26 18:41:19.530 18524-18591/ru.debaser.projects.inspectionsheet D/RoundViewModel: []
2020-06-26 18:41:23.780 18524-18524/ru.debaser.projects.inspectionsheet D/RoundViewModel: [276, 267]
2020-06-26 18:41:23.782 18524-18556/ru.debaser.projects.inspectionsheet D/RoundViewModel: [276, 267]
Upvotes: 2
Views: 2251
Reputation: 1849
The code you have should just work but it looks like you're doing something naughty when calling deleteDefects
.
List<...>
is a read-only interface and it does not guarantee immutability.
I imagine you are modifying the idList
after you pass it into the function.
Something like this...
val idList = mutableListOf<Long>()
idList.add(50)
idList.add(20)
deleteDefects(idList)
idList.clear()
This is a race condition! Since concurrency has been introduced in deleteDefects
, you shouldn't touch idList
after you pass it in.. ever. Unless you use locks or similar.
A quick fix would be to make a defensive copy, like so.
fun deleteDefects(idListTmp: List<Long>) {
val idList = idListTmp.toList() // Safe!
Log.d("RoundViewModel", idList.toString())
viewModelScope.launch(Dispatchers.IO) {
Log.d("RoundViewModel", idList.toString())
ddb.dao().delAddedDefect(idList)
}
}
A proper fix, would be to not modify idList
after you call deleteDefacts(idList)
.
Another proper fix could be to just do deleteDefacts(idList.toList())
.
Upvotes: 4