Unified CoroutineDispatcher

This commit is contained in:
Ash 2022-05-16 10:57:40 +08:00
parent a1021c3c3f
commit 962e0ee8dc
4 changed files with 51 additions and 30 deletions

View File

@ -5,12 +5,14 @@ import androidx.compose.foundation.lazy.LazyListState
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.flow.*
import kotlinx.coroutines.launch
import me.ash.reader.R
import me.ash.reader.data.entity.Account
import me.ash.reader.data.entity.GroupWithFeed
import me.ash.reader.data.module.DispatcherDefault
import me.ash.reader.data.module.DispatcherIO
import me.ash.reader.data.repository.AccountRepository
import me.ash.reader.data.repository.OpmlRepository
import me.ash.reader.data.repository.RssRepository
@ -24,6 +26,10 @@ class FeedsViewModel @Inject constructor(
private val rssRepository: RssRepository,
private val opmlRepository: OpmlRepository,
private val stringsRepository: StringsRepository,
@DispatcherDefault
private val dispatcherDefault: CoroutineDispatcher,
@DispatcherIO
private val dispatcherIO: CoroutineDispatcher,
) : ViewModel() {
private val _viewState = MutableStateFlow(FeedsViewState())
val viewState: StateFlow<FeedsViewState> = _viewState.asStateFlow()
@ -38,7 +44,7 @@ class FeedsViewModel @Inject constructor(
}
private fun fetchAccount() {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
_viewState.update {
it.copy(
account = accountRepository.getCurrentAccount()
@ -48,7 +54,7 @@ class FeedsViewModel @Inject constructor(
}
private fun exportAsOpml(callback: (String) -> Unit = {}) {
viewModelScope.launch(Dispatchers.Default) {
viewModelScope.launch(dispatcherDefault) {
try {
callback(opmlRepository.saveToString())
} catch (e: Exception) {
@ -58,7 +64,7 @@ class FeedsViewModel @Inject constructor(
}
private fun fetchData(filterState: FilterState) {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
pullFeeds(
isStarred = filterState.filter.isStarred(),
isUnread = filterState.filter.isUnread(),
@ -118,7 +124,7 @@ class FeedsViewModel @Inject constructor(
}
}.catch {
Log.e("RLog", "catch in articleRepository.pullFeeds(): ${it.message}")
}.flowOn(Dispatchers.Default).collect()
}.flowOn(dispatcherDefault).collect()
}
private fun scrollToItem(index: Int) {

View File

@ -7,8 +7,8 @@ import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import com.google.accompanist.pager.ExperimentalPagerApi
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asStateFlow
@ -17,6 +17,8 @@ import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import me.ash.reader.data.entity.Feed
import me.ash.reader.data.entity.Group
import me.ash.reader.data.module.DispatcherIO
import me.ash.reader.data.module.DispatcherMain
import me.ash.reader.data.repository.RssRepository
import javax.inject.Inject
@ -27,12 +29,16 @@ import javax.inject.Inject
@HiltViewModel
class FeedOptionViewModel @Inject constructor(
private val rssRepository: RssRepository,
@DispatcherMain
private val dispatcherMain: CoroutineDispatcher,
@DispatcherIO
private val dispatcherIO: CoroutineDispatcher,
) : ViewModel() {
private val _viewState = MutableStateFlow(FeedOptionViewState())
val viewState: StateFlow<FeedOptionViewState> = _viewState.asStateFlow()
init {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().pullGroups().collect { groups ->
_viewState.update {
it.copy(
@ -121,7 +127,7 @@ class FeedOptionViewModel @Inject constructor(
}
private fun selectedGroup(groupId: String) {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
_viewState.value.feed?.let {
rssRepository.get().updateFeed(
it.copy(
@ -134,7 +140,7 @@ class FeedOptionViewModel @Inject constructor(
}
private fun changeParseFullContentPreset() {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
_viewState.value.feed?.let {
rssRepository.get().updateFeed(
it.copy(
@ -147,7 +153,7 @@ class FeedOptionViewModel @Inject constructor(
}
private fun changeAllowNotificationPreset() {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
_viewState.value.feed?.let {
rssRepository.get().updateFeed(
it.copy(
@ -161,9 +167,9 @@ class FeedOptionViewModel @Inject constructor(
private fun delete(callback: () -> Unit = {}) {
_viewState.value.feed?.let {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().deleteFeed(it)
withContext(Dispatchers.Main) {
withContext(dispatcherMain) {
callback()
}
}
@ -204,9 +210,9 @@ class FeedOptionViewModel @Inject constructor(
private fun clear(callback: () -> Unit = {}) {
_viewState.value.feed?.let {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().deleteArticles(feed = it)
withContext(Dispatchers.Main) {
withContext(dispatcherMain) {
callback()
}
}

View File

@ -7,8 +7,8 @@ import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import com.google.accompanist.pager.ExperimentalPagerApi
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asStateFlow
@ -16,6 +16,8 @@ import kotlinx.coroutines.flow.update
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import me.ash.reader.data.entity.Group
import me.ash.reader.data.module.DispatcherIO
import me.ash.reader.data.module.DispatcherMain
import me.ash.reader.data.repository.RssRepository
import javax.inject.Inject
@ -26,12 +28,16 @@ import javax.inject.Inject
@HiltViewModel
class GroupOptionViewModel @Inject constructor(
private val rssRepository: RssRepository,
@DispatcherMain
private val dispatcherMain: CoroutineDispatcher,
@DispatcherIO
private val dispatcherIO: CoroutineDispatcher,
) : ViewModel() {
private val _viewState = MutableStateFlow(GroupOptionViewState())
val viewState: StateFlow<GroupOptionViewState> = _viewState.asStateFlow()
init {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().pullGroups().collect { groups ->
_viewState.update {
it.copy(
@ -106,9 +112,9 @@ class GroupOptionViewModel @Inject constructor(
private fun allAllowNotification(isNotification: Boolean, callback: () -> Unit = {}) {
_viewState.value.group?.let {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().groupAllowNotification(it, isNotification)
withContext(Dispatchers.Main) {
withContext(dispatcherMain) {
callback()
}
}
@ -125,9 +131,9 @@ class GroupOptionViewModel @Inject constructor(
private fun allParseFullContent(isFullContent: Boolean, callback: () -> Unit = {}) {
_viewState.value.group?.let {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().groupParseFullContent(it, isFullContent)
withContext(Dispatchers.Main) {
withContext(dispatcherMain) {
callback()
}
}
@ -144,9 +150,9 @@ class GroupOptionViewModel @Inject constructor(
private fun delete(callback: () -> Unit = {}) {
_viewState.value.group?.let {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().deleteGroup(it)
withContext(Dispatchers.Main) {
withContext(dispatcherMain) {
callback()
}
}
@ -179,9 +185,9 @@ class GroupOptionViewModel @Inject constructor(
private fun clear(callback: () -> Unit = {}) {
_viewState.value.group?.let {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().deleteArticles(group = it)
withContext(Dispatchers.Main) {
withContext(dispatcherMain) {
callback()
}
}
@ -191,9 +197,9 @@ class GroupOptionViewModel @Inject constructor(
private fun allMoveToGroup(callback: () -> Unit) {
_viewState.value.group?.let { group ->
_viewState.value.targetGroup?.let { targetGroup ->
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
rssRepository.get().groupMoveToTargetGroup(group, targetGroup)
withContext(Dispatchers.Main) {
withContext(dispatcherMain) {
callback()
}
}

View File

@ -5,7 +5,7 @@ import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import com.google.accompanist.pager.ExperimentalPagerApi
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.Job
import kotlinx.coroutines.async
import kotlinx.coroutines.flow.*
@ -14,6 +14,7 @@ import me.ash.reader.R
import me.ash.reader.data.entity.Article
import me.ash.reader.data.entity.Feed
import me.ash.reader.data.entity.Group
import me.ash.reader.data.module.DispatcherIO
import me.ash.reader.data.repository.OpmlRepository
import me.ash.reader.data.repository.RssHelper
import me.ash.reader.data.repository.RssRepository
@ -29,6 +30,8 @@ class SubscribeViewModel @Inject constructor(
private val rssRepository: RssRepository,
private val rssHelper: RssHelper,
private val stringsRepository: StringsRepository,
@DispatcherIO
private val dispatcherIO: CoroutineDispatcher,
) : ViewModel() {
private val _viewState = MutableStateFlow(SubscribeViewState())
val viewState: StateFlow<SubscribeViewState> = _viewState.asStateFlow()
@ -77,7 +80,7 @@ class SubscribeViewModel @Inject constructor(
}
private fun importFromInputStream(inputStream: InputStream) {
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
try {
opmlRepository.saveToDatabase(inputStream)
rssRepository.get().doSync()
@ -90,7 +93,7 @@ class SubscribeViewModel @Inject constructor(
private fun subscribe() {
val feed = _viewState.value.feed ?: return
val articles = _viewState.value.articles
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
val groupId = async {
_viewState.value.selectedGroupId
}
@ -145,7 +148,7 @@ class SubscribeViewModel @Inject constructor(
private fun search() {
searchJob?.cancel()
viewModelScope.launch(Dispatchers.IO) {
viewModelScope.launch(dispatcherIO) {
try {
_viewState.update {
it.copy(