Skip to content

Commit b883c3b

Browse files
committed
Merge branch '218-illegalstateexception-cannot-access-database-on-the-main-thread-since-it-may-potentially-lock' into 'master'
Resolve "IllegalStateException: Cannot access database on the main thread since it may potentially lock the UI for a long period ..." Closes #218 See merge request pace/mobile/android/pace-cloud-sdk!233
2 parents 745cdfd + 0366109 commit b883c3b

File tree

3 files changed

+49
-40
lines changed

3 files changed

+49
-40
lines changed

CHANGELOG.md

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,11 @@ x.y.z Release notes (yyyy-MM-dd)
33

44
<!-- ### Breaking Changes - Include, if needed -->
55
<!-- ### Enhancements - Include, if needed -->
6-
<!-- ### Fixes - Include, if needed -->
76
<!-- ### Internal - Include, if needed -->
87

8+
### Fixes
9+
* Fix database access on main thread
10+
911
13.1.0 Release notes (2022-03-10)
1012
=============================================================
1113

library/src/main/java/cloud/pace/sdk/poikit/POIKit.kt

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,10 @@ import cloud.pace.sdk.poikit.utils.POIKitConfig
3232
import cloud.pace.sdk.utils.*
3333
import com.google.android.gms.maps.model.VisibleRegion
3434
import io.reactivex.rxjava3.core.Observable
35+
import kotlinx.coroutines.CoroutineScope
36+
import kotlinx.coroutines.Dispatchers
37+
import kotlinx.coroutines.launch
38+
import kotlinx.coroutines.withContext
3539
import org.koin.core.component.inject
3640
import java.util.*
3741

@@ -88,21 +92,21 @@ object POIKit : CloudSDKKoinComponent, DefaultLifecycleObserver {
8892

8993
@JvmOverloads
9094
fun requestGasStations(locations: Map<String, LocationPoint>, zoomLevel: Int = POIKitConfig.ZOOMLEVEL, completion: (Completion<List<GasStation>>) -> Unit) {
91-
onBackgroundThread {
92-
val tileRequest = locations.values.toTileQueryRequest(zoomLevel)
95+
val tileRequest = locations.values.toTileQueryRequest(zoomLevel)
9396

94-
tileDownloader.load(tileRequest) {
95-
it.onSuccess { stations ->
97+
tileDownloader.load(tileRequest) {
98+
it.onSuccess { stations ->
99+
CoroutineScope(Dispatchers.IO).launch {
96100
database.gasStationDao().insertGasStations(stations)
97-
onMainThread {
101+
withContext(Dispatchers.Main) {
98102
completion(Success(stations))
99103
}
100104
}
105+
}
101106

102-
it.onFailure { error ->
103-
onMainThread {
104-
completion(Failure(error))
105-
}
107+
it.onFailure { error ->
108+
onMainThread {
109+
completion(Failure(error))
106110
}
107111
}
108112
}

library/src/main/java/cloud/pace/sdk/poikit/poi/PoiKitObserverToken.kt

Lines changed: 33 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,7 @@ import cloud.pace.sdk.poikit.utils.addPadding
1414
import cloud.pace.sdk.poikit.utils.toTileQueryRequest
1515
import cloud.pace.sdk.utils.*
1616
import com.google.android.gms.maps.model.VisibleRegion
17-
import kotlinx.coroutines.GlobalScope
18-
import kotlinx.coroutines.MainScope
19-
import kotlinx.coroutines.launch
17+
import kotlinx.coroutines.*
2018
import okhttp3.Call
2119
import org.koin.core.component.inject
2220
import java.util.*
@@ -72,19 +70,21 @@ class VisibleRegionNotificationToken(
7270

7371
downloadTask = tileDownloader.load(tileRequest) {
7472
it.onSuccess { stations ->
75-
gasStationDao.insertGasStations(stations)
76-
77-
MainScope().launch { loading.value = false }
73+
CoroutineScope(Dispatchers.IO).launch {
74+
gasStationDao.insertGasStations(stations)
7875

79-
// Delete gas stations not reported by new tiles anymore
80-
val persistedGasStations = gasStationDao.getInBoundingBox(
81-
minLat = visibleRegion.latLngBounds.southwest.latitude,
82-
minLon = visibleRegion.latLngBounds.southwest.longitude,
83-
maxLat = visibleRegion.latLngBounds.northeast.latitude,
84-
maxLon = visibleRegion.latLngBounds.northeast.longitude
85-
)
86-
val outdatedStations = persistedGasStations.filter { it.id !in stations.map { it.id } }
87-
gasStationDao.delete(outdatedStations)
76+
withContext(Dispatchers.Main) { loading.value = false }
77+
78+
// Delete gas stations not reported by new tiles anymore
79+
val persistedGasStations = gasStationDao.getInBoundingBox(
80+
minLat = visibleRegion.latLngBounds.southwest.latitude,
81+
minLon = visibleRegion.latLngBounds.southwest.longitude,
82+
maxLat = visibleRegion.latLngBounds.northeast.latitude,
83+
maxLon = visibleRegion.latLngBounds.northeast.longitude
84+
)
85+
val outdatedStations = persistedGasStations.filter { it.id !in stations.map { it.id } }
86+
gasStationDao.delete(outdatedStations)
87+
}
8888
}
8989

9090
it.onFailure { error ->
@@ -119,13 +119,15 @@ class IDsNotificationToken(
119119
override fun refresh(zoomLevel: Int) {
120120
loading.value = true
121121

122-
GlobalScope.launch {
122+
CoroutineScope(Dispatchers.IO).launch {
123123
val tileRequest = gasStationDao.getByIds(ids).mapNotNull { it.center }.toTileQueryRequest(zoomLevel)
124124

125125
downloadTask = tileDownloader.load(tileRequest) {
126126
it.onSuccess { stations ->
127-
gasStationDao.insertGasStations(stations)
128-
MainScope().launch { loading.value = false }
127+
CoroutineScope(Dispatchers.IO).launch {
128+
gasStationDao.insertGasStations(stations)
129+
withContext(Dispatchers.Main) { loading.value = false }
130+
}
129131
}
130132

131133
it.onFailure { error ->
@@ -200,8 +202,10 @@ class IDNotificationToken(
200202
private fun download(location: LocationPoint, zoomLevel: Int) {
201203
downloadTask = tileDownloader.load(location.toTileQueryRequest(zoomLevel)) {
202204
it.onSuccess { stations ->
203-
gasStationDao.insertGasStations(stations)
204-
MainScope().launch { loading.value = false }
205+
CoroutineScope(Dispatchers.IO).launch {
206+
gasStationDao.insertGasStations(stations)
207+
withContext(Dispatchers.Main) { loading.value = false }
208+
}
205209
}
206210

207211
it.onFailure { error ->
@@ -229,19 +233,18 @@ class LocationsNotificationToken(
229233
override fun refresh(zoomLevel: Int) {
230234
loading.value = true
231235

232-
GlobalScope.launch {
233-
val tileRequest = locations.values.toTileQueryRequest(zoomLevel)
234-
235-
downloadTask = tileDownloader.load(tileRequest) {
236-
it.onSuccess { stations ->
236+
val tileRequest = locations.values.toTileQueryRequest(zoomLevel)
237+
downloadTask = tileDownloader.load(tileRequest) {
238+
it.onSuccess { stations ->
239+
CoroutineScope(Dispatchers.IO).launch {
237240
gasStationDao.insertGasStations(stations)
238-
MainScope().launch { loading.value = false }
241+
withContext(Dispatchers.Main) { loading.value = false }
239242
}
243+
}
240244

241-
it.onFailure { error ->
242-
completion(Failure(error))
243-
MainScope().launch { loading.value = false }
244-
}
245+
it.onFailure { error ->
246+
completion(Failure(error))
247+
MainScope().launch { loading.value = false }
245248
}
246249
}
247250

0 commit comments

Comments
 (0)