forked from github/wulkanowy-mirror
Resource refactor (#1589)
This commit is contained in:
parent
042b66ca5c
commit
20dde6e896
@ -1,23 +1,173 @@
|
|||||||
package io.github.wulkanowy.data
|
package io.github.wulkanowy.data
|
||||||
|
|
||||||
data class Resource<T>(val status: Status, val data: T?, val error: Throwable?) {
|
import kotlinx.coroutines.flow.*
|
||||||
companion object {
|
import kotlinx.coroutines.sync.Mutex
|
||||||
fun <T> success(data: T?): Resource<T> {
|
import kotlinx.coroutines.sync.withLock
|
||||||
return Resource(Status.SUCCESS, data, null)
|
import timber.log.Timber
|
||||||
}
|
|
||||||
|
|
||||||
fun <T> error(error: Throwable?, data: T? = null): Resource<T> {
|
sealed class Resource<T> {
|
||||||
return Resource(Status.ERROR, data, error)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun <T> loading(data: T? = null): Resource<T> {
|
open class Loading<T> : Resource<T>()
|
||||||
return Resource(Status.LOADING, data, null)
|
|
||||||
}
|
data class Intermediate<T>(val data: T) : Loading<T>()
|
||||||
|
|
||||||
|
data class Success<T>(val data: T) : Resource<T>()
|
||||||
|
|
||||||
|
data class Error<T>(val error: Throwable) : Resource<T>()
|
||||||
|
}
|
||||||
|
|
||||||
|
val <T> Resource<T>.dataOrNull: T?
|
||||||
|
get() = when (this) {
|
||||||
|
is Resource.Success -> this.data
|
||||||
|
is Resource.Intermediate -> this.data
|
||||||
|
is Resource.Loading -> null
|
||||||
|
is Resource.Error -> null
|
||||||
|
}
|
||||||
|
|
||||||
|
val <T> Resource<T>.errorOrNull: Throwable?
|
||||||
|
get() = when (this) {
|
||||||
|
is Resource.Error -> this.error
|
||||||
|
else -> null
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T> resourceFlow(block: suspend () -> T) = flow {
|
||||||
|
emit(Resource.Loading())
|
||||||
|
emit(Resource.Success(block()))
|
||||||
|
}.catch { emit(Resource.Error(it)) }
|
||||||
|
|
||||||
|
fun <T> flatResourceFlow(block: suspend () -> Flow<Resource<T>>) = flow {
|
||||||
|
emit(Resource.Loading())
|
||||||
|
emitAll(block().filter { it is Resource.Intermediate || it !is Resource.Loading })
|
||||||
|
}.catch { emit(Resource.Error(it)) }
|
||||||
|
|
||||||
|
fun <T, U> Resource<T>.mapData(block: (T) -> U) = when (this) {
|
||||||
|
is Resource.Success -> Resource.Success(block(this.data))
|
||||||
|
is Resource.Intermediate -> Resource.Intermediate(block(this.data))
|
||||||
|
is Resource.Loading -> Resource.Loading()
|
||||||
|
is Resource.Error -> Resource.Error(this.error)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T> Flow<Resource<T>>.logResourceStatus(name: String, showData: Boolean = false) = onEach {
|
||||||
|
val description = when (it) {
|
||||||
|
is Resource.Loading -> "started"
|
||||||
|
is Resource.Intermediate -> "intermediate data received" + if (showData) " (data: `${it.data}`)" else ""
|
||||||
|
is Resource.Success -> "success" + if (showData) " (data: `${it.data}`)" else ""
|
||||||
|
is Resource.Error -> "exception occurred: ${it.error}"
|
||||||
|
}
|
||||||
|
Timber.i("$name: $description")
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T, U> Flow<Resource<T>>.mapResourceData(block: (T) -> U) = map {
|
||||||
|
it.mapData(block)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T> Flow<Resource<T>>.onResourceData(block: suspend (T) -> Unit) = onEach {
|
||||||
|
when (it) {
|
||||||
|
is Resource.Success -> block(it.data)
|
||||||
|
is Resource.Intermediate -> block(it.data)
|
||||||
|
is Resource.Error,
|
||||||
|
is Resource.Loading -> Unit
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
enum class Status {
|
fun <T> Flow<Resource<T>>.onResourceLoading(block: suspend () -> Unit) = onEach {
|
||||||
LOADING,
|
if (it is Resource.Loading) {
|
||||||
SUCCESS,
|
block()
|
||||||
ERROR
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T> Flow<Resource<T>>.onResourceIntermediate(block: suspend (T) -> Unit) = onEach {
|
||||||
|
if (it is Resource.Intermediate) {
|
||||||
|
block(it.data)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T> Flow<Resource<T>>.onResourceSuccess(block: suspend (T) -> Unit) = onEach {
|
||||||
|
if (it is Resource.Success) {
|
||||||
|
block(it.data)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T> Flow<Resource<T>>.onResourceError(block: (Throwable) -> Unit) = onEach {
|
||||||
|
if (it is Resource.Error) {
|
||||||
|
block(it.error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun <T> Flow<Resource<T>>.onResourceNotLoading(block: () -> Unit) = onEach {
|
||||||
|
if (it !is Resource.Loading) {
|
||||||
|
block()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
suspend fun <T> Flow<Resource<T>>.toFirstResult() = filter { it !is Resource.Loading }.first()
|
||||||
|
|
||||||
|
suspend fun <T> Flow<Resource<T>>.waitForResult() = takeWhile { it is Resource.Loading }.collect()
|
||||||
|
|
||||||
|
inline fun <ResultType, RequestType> networkBoundResource(
|
||||||
|
mutex: Mutex = Mutex(),
|
||||||
|
showSavedOnLoading: Boolean = true,
|
||||||
|
crossinline isResultEmpty: (ResultType) -> Boolean,
|
||||||
|
crossinline query: () -> Flow<ResultType>,
|
||||||
|
crossinline fetch: suspend (ResultType) -> RequestType,
|
||||||
|
crossinline saveFetchResult: suspend (old: ResultType, new: RequestType) -> Unit,
|
||||||
|
crossinline onFetchFailed: (Throwable) -> Unit = { },
|
||||||
|
crossinline shouldFetch: (ResultType) -> Boolean = { true },
|
||||||
|
crossinline filterResult: (ResultType) -> ResultType = { it }
|
||||||
|
) = flow {
|
||||||
|
emit(Resource.Loading())
|
||||||
|
|
||||||
|
val data = query().first()
|
||||||
|
emitAll(if (shouldFetch(data)) {
|
||||||
|
val filteredResult = filterResult(data)
|
||||||
|
|
||||||
|
if (showSavedOnLoading && !isResultEmpty(filteredResult)) {
|
||||||
|
emit(Resource.Intermediate(filteredResult))
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
val newData = fetch(data)
|
||||||
|
mutex.withLock { saveFetchResult(query().first(), newData) }
|
||||||
|
query().map { Resource.Success(filterResult(it)) }
|
||||||
|
} catch (throwable: Throwable) {
|
||||||
|
onFetchFailed(throwable)
|
||||||
|
query().map { Resource.Error(throwable) }
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
query().map { Resource.Success(filterResult(it)) }
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmName("networkBoundResourceWithMap")
|
||||||
|
inline fun <ResultType, RequestType, T> networkBoundResource(
|
||||||
|
mutex: Mutex = Mutex(),
|
||||||
|
showSavedOnLoading: Boolean = true,
|
||||||
|
crossinline isResultEmpty: (T) -> Boolean,
|
||||||
|
crossinline query: () -> Flow<ResultType>,
|
||||||
|
crossinline fetch: suspend (ResultType) -> RequestType,
|
||||||
|
crossinline saveFetchResult: suspend (old: ResultType, new: RequestType) -> Unit,
|
||||||
|
crossinline onFetchFailed: (Throwable) -> Unit = { },
|
||||||
|
crossinline shouldFetch: (ResultType) -> Boolean = { true },
|
||||||
|
crossinline mapResult: (ResultType) -> T
|
||||||
|
) = flow {
|
||||||
|
emit(Resource.Loading())
|
||||||
|
|
||||||
|
val data = query().first()
|
||||||
|
emitAll(if (shouldFetch(data)) {
|
||||||
|
val mappedResult = mapResult(data)
|
||||||
|
|
||||||
|
if (showSavedOnLoading && !isResultEmpty(mappedResult)) {
|
||||||
|
emit(Resource.Intermediate(mappedResult))
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
val newData = fetch(data)
|
||||||
|
mutex.withLock { saveFetchResult(query().first(), newData) }
|
||||||
|
query().map { Resource.Success(mapResult(it)) }
|
||||||
|
} catch (throwable: Throwable) {
|
||||||
|
onFetchFailed(throwable)
|
||||||
|
query().map { Resource.Error(throwable) }
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
query().map { Resource.Success(mapResult(it)) }
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
@ -33,6 +33,10 @@ abstract class StudentDao {
|
|||||||
@Query("SELECT * FROM Students")
|
@Query("SELECT * FROM Students")
|
||||||
abstract suspend fun loadStudentsWithSemesters(): List<StudentWithSemesters>
|
abstract suspend fun loadStudentsWithSemesters(): List<StudentWithSemesters>
|
||||||
|
|
||||||
|
@Transaction
|
||||||
|
@Query("SELECT * FROM Students WHERE id = :id")
|
||||||
|
abstract suspend fun loadStudentWithSemestersById(id: Long): StudentWithSemesters?
|
||||||
|
|
||||||
@Query("UPDATE Students SET is_current = 1 WHERE id = :id")
|
@Query("UPDATE Students SET is_current = 1 WHERE id = :id")
|
||||||
abstract suspend fun updateCurrent(id: Long)
|
abstract suspend fun updateCurrent(id: Long)
|
||||||
|
|
||||||
|
@ -3,8 +3,8 @@ package io.github.wulkanowy.data.repositories
|
|||||||
import io.github.wulkanowy.data.api.AdminMessageService
|
import io.github.wulkanowy.data.api.AdminMessageService
|
||||||
import io.github.wulkanowy.data.db.dao.AdminMessageDao
|
import io.github.wulkanowy.data.db.dao.AdminMessageDao
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.utils.AppInfo
|
import io.github.wulkanowy.utils.AppInfo
|
||||||
import io.github.wulkanowy.utils.networkBoundResource
|
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
import javax.inject.Singleton
|
import javax.inject.Singleton
|
||||||
@ -19,6 +19,7 @@ class AdminMessageRepository @Inject constructor(
|
|||||||
|
|
||||||
suspend fun getAdminMessages(student: Student) = networkBoundResource(
|
suspend fun getAdminMessages(student: Student) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it == null },
|
||||||
query = { adminMessageDao.loadAll() },
|
query = { adminMessageDao.loadAll() },
|
||||||
fetch = { adminMessageService.getAdminMessages() },
|
fetch = { adminMessageService.getAdminMessages() },
|
||||||
shouldFetch = { true },
|
shouldFetch = { true },
|
||||||
|
@ -5,6 +5,7 @@ import io.github.wulkanowy.data.db.entities.Attendance
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.sdk.pojo.Absent
|
import io.github.wulkanowy.sdk.pojo.Absent
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.*
|
||||||
@ -36,6 +37,7 @@ class AttendanceRepository @Inject constructor(
|
|||||||
notify: Boolean = false,
|
notify: Boolean = false,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(cacheKey, semester, start, end)
|
key = getRefreshKey(cacheKey, semester, start, end)
|
||||||
|
@ -4,8 +4,12 @@ import io.github.wulkanowy.data.db.dao.AttendanceSummaryDao
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
|
import io.github.wulkanowy.utils.init
|
||||||
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
import javax.inject.Singleton
|
import javax.inject.Singleton
|
||||||
@ -28,6 +32,7 @@ class AttendanceSummaryRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
||||||
it.isEmpty() || forceRefresh || isExpired
|
it.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -4,6 +4,7 @@ import io.github.wulkanowy.data.db.dao.CompletedLessonsDao
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.*
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
@ -30,6 +31,7 @@ class CompletedLessonsRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(cacheKey, semester, start, end)
|
key = getRefreshKey(cacheKey, semester, start, end)
|
||||||
|
@ -5,8 +5,12 @@ import io.github.wulkanowy.data.db.entities.Conference
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
|
import io.github.wulkanowy.utils.init
|
||||||
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import java.time.Instant
|
import java.time.Instant
|
||||||
@ -32,6 +36,7 @@ class ConferenceRepository @Inject constructor(
|
|||||||
startDate: Instant = Instant.EPOCH,
|
startDate: Instant = Instant.EPOCH,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
||||||
it.isEmpty() || forceRefresh || isExpired
|
it.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -5,6 +5,7 @@ import io.github.wulkanowy.data.db.entities.Exam
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.*
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
@ -33,6 +34,7 @@ class ExamRepository @Inject constructor(
|
|||||||
notify: Boolean = false,
|
notify: Boolean = false,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(cacheKey, semester, start, end)
|
key = getRefreshKey(cacheKey, semester, start, end)
|
||||||
|
@ -7,6 +7,7 @@ import io.github.wulkanowy.data.db.entities.GradeSummary
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.*
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
@ -36,6 +37,10 @@ class GradeRepository @Inject constructor(
|
|||||||
notify: Boolean = false,
|
notify: Boolean = false,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = {
|
||||||
|
//When details is empty and summary is not, app will not use summary cache - edge case
|
||||||
|
it.first.isEmpty()
|
||||||
|
},
|
||||||
shouldFetch = { (details, summaries) ->
|
shouldFetch = { (details, summaries) ->
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
||||||
details.isEmpty() || summaries.isEmpty() || forceRefresh || isExpired
|
details.isEmpty() || summaries.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -11,8 +11,12 @@ import io.github.wulkanowy.data.mappers.mapPartialToStatisticItems
|
|||||||
import io.github.wulkanowy.data.mappers.mapPointsToStatisticsItems
|
import io.github.wulkanowy.data.mappers.mapPointsToStatisticsItems
|
||||||
import io.github.wulkanowy.data.mappers.mapSemesterToStatisticItems
|
import io.github.wulkanowy.data.mappers.mapSemesterToStatisticItems
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
|
import io.github.wulkanowy.utils.init
|
||||||
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import java.util.*
|
import java.util.*
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -42,6 +46,7 @@ class GradeStatisticsRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = partialMutex,
|
mutex = partialMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(partialCacheKey, semester)
|
key = getRefreshKey(partialCacheKey, semester)
|
||||||
@ -86,6 +91,7 @@ class GradeStatisticsRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = semesterMutex,
|
mutex = semesterMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(semesterCacheKey, semester)
|
key = getRefreshKey(semesterCacheKey, semester)
|
||||||
@ -143,6 +149,7 @@ class GradeStatisticsRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = pointsMutex,
|
mutex = pointsMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(pointsCacheKey, semester))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(pointsCacheKey, semester))
|
||||||
it.isEmpty() || forceRefresh || isExpired
|
it.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -5,6 +5,7 @@ import io.github.wulkanowy.data.db.entities.Homework
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.*
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
@ -32,6 +33,7 @@ class HomeworkRepository @Inject constructor(
|
|||||||
notify: Boolean = false,
|
notify: Boolean = false,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(cacheKey, semester, start, end)
|
key = getRefreshKey(cacheKey, semester, start, end)
|
||||||
|
@ -4,9 +4,9 @@ import io.github.wulkanowy.data.db.dao.LuckyNumberDao
|
|||||||
import io.github.wulkanowy.data.db.entities.LuckyNumber
|
import io.github.wulkanowy.data.db.entities.LuckyNumber
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntity
|
import io.github.wulkanowy.data.mappers.mapToEntity
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.init
|
import io.github.wulkanowy.utils.init
|
||||||
import io.github.wulkanowy.utils.networkBoundResource
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import kotlinx.coroutines.flow.map
|
import kotlinx.coroutines.flow.map
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
@ -29,6 +29,7 @@ class LuckyNumberRepository @Inject constructor(
|
|||||||
notify: Boolean = false,
|
notify: Boolean = false,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it == null },
|
||||||
shouldFetch = { it == null || forceRefresh },
|
shouldFetch = { it == null || forceRefresh },
|
||||||
query = { luckyNumberDb.load(student.studentId, now()) },
|
query = { luckyNumberDb.load(student.studentId, now()) },
|
||||||
fetch = {
|
fetch = {
|
||||||
|
@ -7,15 +7,12 @@ import io.github.wulkanowy.data.Resource
|
|||||||
import io.github.wulkanowy.data.db.SharedPrefProvider
|
import io.github.wulkanowy.data.db.SharedPrefProvider
|
||||||
import io.github.wulkanowy.data.db.dao.MessageAttachmentDao
|
import io.github.wulkanowy.data.db.dao.MessageAttachmentDao
|
||||||
import io.github.wulkanowy.data.db.dao.MessagesDao
|
import io.github.wulkanowy.data.db.dao.MessagesDao
|
||||||
import io.github.wulkanowy.data.db.entities.Message
|
import io.github.wulkanowy.data.db.entities.*
|
||||||
import io.github.wulkanowy.data.db.entities.MessageWithAttachment
|
|
||||||
import io.github.wulkanowy.data.db.entities.Recipient
|
|
||||||
import io.github.wulkanowy.data.db.entities.Semester
|
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
|
||||||
import io.github.wulkanowy.data.enums.MessageFolder
|
import io.github.wulkanowy.data.enums.MessageFolder
|
||||||
import io.github.wulkanowy.data.enums.MessageFolder.RECEIVED
|
import io.github.wulkanowy.data.enums.MessageFolder.RECEIVED
|
||||||
import io.github.wulkanowy.data.mappers.mapFromEntities
|
import io.github.wulkanowy.data.mappers.mapFromEntities
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.data.pojos.MessageDraft
|
import io.github.wulkanowy.data.pojos.MessageDraft
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.sdk.pojo.Folder
|
import io.github.wulkanowy.sdk.pojo.Folder
|
||||||
@ -23,7 +20,6 @@ import io.github.wulkanowy.sdk.pojo.SentMessage
|
|||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.getRefreshKey
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
import io.github.wulkanowy.utils.init
|
import io.github.wulkanowy.utils.init
|
||||||
import io.github.wulkanowy.utils.networkBoundResource
|
|
||||||
import io.github.wulkanowy.utils.uniqueSubtract
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
@ -59,6 +55,7 @@ class MessageRepository @Inject constructor(
|
|||||||
notify: Boolean = false,
|
notify: Boolean = false,
|
||||||
): Flow<Resource<List<Message>>> = networkBoundResource(
|
): Flow<Resource<List<Message>>> = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(cacheKey, student, folder)
|
key = getRefreshKey(cacheKey, student, folder)
|
||||||
@ -106,8 +103,9 @@ class MessageRepository @Inject constructor(
|
|||||||
message: Message,
|
message: Message,
|
||||||
markAsRead: Boolean = false,
|
markAsRead: Boolean = false,
|
||||||
): Flow<Resource<MessageWithAttachment?>> = networkBoundResource(
|
): Flow<Resource<MessageWithAttachment?>> = networkBoundResource(
|
||||||
|
isResultEmpty = { it == null },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
checkNotNull(it, { "This message no longer exist!" })
|
checkNotNull(it) { "This message no longer exist!" }
|
||||||
Timber.d("Message content in db empty: ${it.message.content.isEmpty()}")
|
Timber.d("Message content in db empty: ${it.message.content.isEmpty()}")
|
||||||
it.message.unread || it.message.content.isEmpty()
|
it.message.unread || it.message.content.isEmpty()
|
||||||
},
|
},
|
||||||
@ -123,7 +121,7 @@ class MessageRepository @Inject constructor(
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
saveFetchResult = { old, (downloadedMessage, attachments) ->
|
saveFetchResult = { old, (downloadedMessage, attachments) ->
|
||||||
checkNotNull(old, { "Fetched message no longer exist!" })
|
checkNotNull(old) { "Fetched message no longer exist!" }
|
||||||
messagesDb.updateAll(listOf(old.message.apply {
|
messagesDb.updateAll(listOf(old.message.apply {
|
||||||
id = old.message.id
|
id = old.message.id
|
||||||
unread = !markAsRead
|
unread = !markAsRead
|
||||||
|
@ -6,9 +6,13 @@ import io.github.wulkanowy.data.db.entities.Semester
|
|||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
import io.github.wulkanowy.data.mappers.mapToMobileDeviceToken
|
import io.github.wulkanowy.data.mappers.mapToMobileDeviceToken
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.data.pojos.MobileDeviceToken
|
import io.github.wulkanowy.data.pojos.MobileDeviceToken
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
|
import io.github.wulkanowy.utils.init
|
||||||
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
import javax.inject.Singleton
|
import javax.inject.Singleton
|
||||||
@ -30,6 +34,7 @@ class MobileDeviceRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, student))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, student))
|
||||||
it.isEmpty() || forceRefresh || isExpired
|
it.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -5,6 +5,7 @@ import io.github.wulkanowy.data.db.entities.Note
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.*
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
@ -30,6 +31,7 @@ class NoteRepository @Inject constructor(
|
|||||||
notify: Boolean = false,
|
notify: Boolean = false,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
getRefreshKey(cacheKey, semester)
|
getRefreshKey(cacheKey, semester)
|
||||||
|
@ -4,11 +4,11 @@ import io.github.wulkanowy.data.db.dao.SchoolAnnouncementDao
|
|||||||
import io.github.wulkanowy.data.db.entities.SchoolAnnouncement
|
import io.github.wulkanowy.data.db.entities.SchoolAnnouncement
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.getRefreshKey
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
import io.github.wulkanowy.utils.init
|
import io.github.wulkanowy.utils.init
|
||||||
import io.github.wulkanowy.utils.networkBoundResource
|
|
||||||
import io.github.wulkanowy.utils.uniqueSubtract
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
@ -31,6 +31,7 @@ class SchoolAnnouncementRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean, notify: Boolean = false
|
forceRefresh: Boolean, notify: Boolean = false
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, student))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, student))
|
||||||
it.isEmpty() || forceRefresh || isExpired
|
it.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -4,11 +4,11 @@ import io.github.wulkanowy.data.db.dao.SchoolDao
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntity
|
import io.github.wulkanowy.data.mappers.mapToEntity
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.getRefreshKey
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
import io.github.wulkanowy.utils.init
|
import io.github.wulkanowy.utils.init
|
||||||
import io.github.wulkanowy.utils.networkBoundResource
|
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
import javax.inject.Singleton
|
import javax.inject.Singleton
|
||||||
@ -30,6 +30,7 @@ class SchoolRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it == null },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(
|
val isExpired = refreshHelper.shouldBeRefreshed(
|
||||||
key = getRefreshKey(cacheKey, student)
|
key = getRefreshKey(cacheKey, student)
|
||||||
|
@ -4,9 +4,9 @@ import io.github.wulkanowy.data.db.dao.StudentInfoDao
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntity
|
import io.github.wulkanowy.data.mappers.mapToEntity
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.init
|
import io.github.wulkanowy.utils.init
|
||||||
import io.github.wulkanowy.utils.networkBoundResource
|
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
import javax.inject.Singleton
|
import javax.inject.Singleton
|
||||||
@ -25,6 +25,7 @@ class StudentInfoRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it == null },
|
||||||
shouldFetch = { it == null || forceRefresh },
|
shouldFetch = { it == null || forceRefresh },
|
||||||
query = { studentInfoDao.loadStudentInfo(student.studentId) },
|
query = { studentInfoDao.loadStudentInfo(student.studentId) },
|
||||||
fetch = {
|
fetch = {
|
||||||
|
@ -73,6 +73,15 @@ class StudentRepository @Inject constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
suspend fun getSavedStudentById(id: Long, decryptPass: Boolean = true) =
|
||||||
|
studentDb.loadStudentWithSemestersById(id)?.apply {
|
||||||
|
if (decryptPass && Sdk.Mode.valueOf(student.loginMode) != Sdk.Mode.API) {
|
||||||
|
student.password = withContext(dispatchers.io) {
|
||||||
|
decrypt(student.password)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
suspend fun getStudentById(id: Long, decryptPass: Boolean = true): Student {
|
suspend fun getStudentById(id: Long, decryptPass: Boolean = true): Student {
|
||||||
val student = studentDb.loadById(id) ?: throw NoCurrentStudentException()
|
val student = studentDb.loadById(id) ?: throw NoCurrentStudentException()
|
||||||
|
|
||||||
|
@ -4,8 +4,12 @@ import io.github.wulkanowy.data.db.dao.SubjectDao
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
|
import io.github.wulkanowy.utils.init
|
||||||
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
import javax.inject.Singleton
|
import javax.inject.Singleton
|
||||||
@ -27,6 +31,7 @@ class SubjectRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean = false,
|
forceRefresh: Boolean = false,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
||||||
it.isEmpty() || forceRefresh || isExpired
|
it.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -4,8 +4,12 @@ import io.github.wulkanowy.data.db.dao.TeacherDao
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
|
import io.github.wulkanowy.utils.getRefreshKey
|
||||||
|
import io.github.wulkanowy.utils.init
|
||||||
|
import io.github.wulkanowy.utils.uniqueSubtract
|
||||||
import kotlinx.coroutines.sync.Mutex
|
import kotlinx.coroutines.sync.Mutex
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
import javax.inject.Singleton
|
import javax.inject.Singleton
|
||||||
@ -27,6 +31,7 @@ class TeacherRepository @Inject constructor(
|
|||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = { it.isEmpty() },
|
||||||
shouldFetch = {
|
shouldFetch = {
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
val isExpired = refreshHelper.shouldBeRefreshed(getRefreshKey(cacheKey, semester))
|
||||||
it.isEmpty() || forceRefresh || isExpired
|
it.isEmpty() || forceRefresh || isExpired
|
||||||
|
@ -5,6 +5,7 @@ import io.github.wulkanowy.data.db.dao.TimetableDao
|
|||||||
import io.github.wulkanowy.data.db.dao.TimetableHeaderDao
|
import io.github.wulkanowy.data.db.dao.TimetableHeaderDao
|
||||||
import io.github.wulkanowy.data.db.entities.*
|
import io.github.wulkanowy.data.db.entities.*
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.networkBoundResource
|
||||||
import io.github.wulkanowy.data.pojos.TimetableFull
|
import io.github.wulkanowy.data.pojos.TimetableFull
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.services.alarm.TimetableNotificationSchedulerHelper
|
import io.github.wulkanowy.services.alarm.TimetableNotificationSchedulerHelper
|
||||||
@ -30,6 +31,10 @@ class TimetableRepository @Inject constructor(
|
|||||||
|
|
||||||
private val cacheKey = "timetable"
|
private val cacheKey = "timetable"
|
||||||
|
|
||||||
|
enum class TimetableType {
|
||||||
|
NORMAL, ADDITIONAL
|
||||||
|
}
|
||||||
|
|
||||||
fun getTimetable(
|
fun getTimetable(
|
||||||
student: Student,
|
student: Student,
|
||||||
semester: Semester,
|
semester: Semester,
|
||||||
@ -37,9 +42,16 @@ class TimetableRepository @Inject constructor(
|
|||||||
end: LocalDate,
|
end: LocalDate,
|
||||||
forceRefresh: Boolean,
|
forceRefresh: Boolean,
|
||||||
refreshAdditional: Boolean = false,
|
refreshAdditional: Boolean = false,
|
||||||
notify: Boolean = false
|
notify: Boolean = false,
|
||||||
|
timetableType: TimetableType = TimetableType.NORMAL
|
||||||
) = networkBoundResource(
|
) = networkBoundResource(
|
||||||
mutex = saveFetchResultMutex,
|
mutex = saveFetchResultMutex,
|
||||||
|
isResultEmpty = {
|
||||||
|
when (timetableType) {
|
||||||
|
TimetableType.NORMAL -> it.lessons.isEmpty()
|
||||||
|
TimetableType.ADDITIONAL -> it.additional.isEmpty()
|
||||||
|
}
|
||||||
|
},
|
||||||
shouldFetch = { (timetable, additional, headers) ->
|
shouldFetch = { (timetable, additional, headers) ->
|
||||||
val refreshKey = getRefreshKey(cacheKey, semester, start, end)
|
val refreshKey = getRefreshKey(cacheKey, semester, start, end)
|
||||||
val isExpired = refreshHelper.shouldBeRefreshed(refreshKey)
|
val isExpired = refreshHelper.shouldBeRefreshed(refreshKey)
|
||||||
|
@ -10,19 +10,18 @@ import androidx.core.app.NotificationCompat
|
|||||||
import androidx.core.app.NotificationManagerCompat
|
import androidx.core.app.NotificationManagerCompat
|
||||||
import dagger.hilt.android.AndroidEntryPoint
|
import dagger.hilt.android.AndroidEntryPoint
|
||||||
import io.github.wulkanowy.R
|
import io.github.wulkanowy.R
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.onResourceError
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.services.sync.channels.UpcomingLessonsChannel.Companion.CHANNEL_ID
|
import io.github.wulkanowy.services.sync.channels.UpcomingLessonsChannel.Companion.CHANNEL_ID
|
||||||
import io.github.wulkanowy.ui.modules.Destination
|
import io.github.wulkanowy.ui.modules.Destination
|
||||||
import io.github.wulkanowy.ui.modules.splash.SplashActivity
|
import io.github.wulkanowy.ui.modules.splash.SplashActivity
|
||||||
import io.github.wulkanowy.utils.PendingIntentCompat
|
import io.github.wulkanowy.utils.PendingIntentCompat
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.getCompatColor
|
import io.github.wulkanowy.utils.getCompatColor
|
||||||
import kotlinx.coroutines.DelicateCoroutinesApi
|
import kotlinx.coroutines.DelicateCoroutinesApi
|
||||||
import kotlinx.coroutines.GlobalScope
|
import kotlinx.coroutines.GlobalScope
|
||||||
import kotlinx.coroutines.flow.launchIn
|
import kotlinx.coroutines.flow.launchIn
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -59,7 +58,7 @@ class TimetableNotificationReceiver : BroadcastReceiver() {
|
|||||||
override fun onReceive(context: Context, intent: Intent) {
|
override fun onReceive(context: Context, intent: Intent) {
|
||||||
Timber.d("Receiving intent... ${intent.toUri(0)}")
|
Timber.d("Receiving intent... ${intent.toUri(0)}")
|
||||||
|
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val showStudentName = !studentRepository.isOneUniqueStudent()
|
val showStudentName = !studentRepository.isOneUniqueStudent()
|
||||||
val student = studentRepository.getCurrentStudent(false)
|
val student = studentRepository.getCurrentStudent(false)
|
||||||
val studentId = intent.getIntExtra(STUDENT_ID, 0)
|
val studentId = intent.getIntExtra(STUDENT_ID, 0)
|
||||||
@ -69,9 +68,9 @@ class TimetableNotificationReceiver : BroadcastReceiver() {
|
|||||||
} else {
|
} else {
|
||||||
Timber.d("Notification studentId($studentId) differs from current(${student.studentId})")
|
Timber.d("Notification studentId($studentId) differs from current(${student.studentId})")
|
||||||
}
|
}
|
||||||
}.onEach {
|
}
|
||||||
if (it.status == Status.ERROR) Timber.e(it.error!!)
|
.onResourceError { Timber.e(it) }
|
||||||
}.launchIn(GlobalScope)
|
.launchIn(GlobalScope)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun prepareNotification(context: Context, intent: Intent, showStudentName: Boolean) {
|
private fun prepareNotification(context: Context, intent: Intent, showStudentName: Boolean) {
|
||||||
|
@ -3,7 +3,7 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.AttendanceSummaryRepository
|
import io.github.wulkanowy.data.repositories.AttendanceSummaryRepository
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class AttendanceSummaryWork @Inject constructor(
|
class AttendanceSummaryWork @Inject constructor(
|
||||||
|
@ -3,9 +3,9 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.AttendanceRepository
|
import io.github.wulkanowy.data.repositories.AttendanceRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewAttendanceNotification
|
import io.github.wulkanowy.services.sync.notifications.NewAttendanceNotification
|
||||||
import io.github.wulkanowy.utils.previousOrSameSchoolDay
|
import io.github.wulkanowy.utils.previousOrSameSchoolDay
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import java.time.LocalDate.now
|
import java.time.LocalDate.now
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
@ -3,9 +3,9 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.CompletedLessonsRepository
|
import io.github.wulkanowy.data.repositories.CompletedLessonsRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.utils.monday
|
import io.github.wulkanowy.utils.monday
|
||||||
import io.github.wulkanowy.utils.sunday
|
import io.github.wulkanowy.utils.sunday
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import java.time.LocalDate.now
|
import java.time.LocalDate.now
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
@ -3,8 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.ConferenceRepository
|
import io.github.wulkanowy.data.repositories.ConferenceRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewConferenceNotification
|
import io.github.wulkanowy.services.sync.notifications.NewConferenceNotification
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
@ -3,8 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.ExamRepository
|
import io.github.wulkanowy.data.repositories.ExamRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewExamNotification
|
import io.github.wulkanowy.services.sync.notifications.NewExamNotification
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import java.time.LocalDate.now
|
import java.time.LocalDate.now
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
@ -3,7 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.GradeStatisticsRepository
|
import io.github.wulkanowy.data.repositories.GradeStatisticsRepository
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
import io.github.wulkanowy.data.waitForResult
|
||||||
|
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class GradeStatisticsWork @Inject constructor(
|
class GradeStatisticsWork @Inject constructor(
|
||||||
|
@ -3,8 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.GradeRepository
|
import io.github.wulkanowy.data.repositories.GradeRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewGradeNotification
|
import io.github.wulkanowy.services.sync.notifications.NewGradeNotification
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
@ -3,9 +3,9 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewHomeworkNotification
|
import io.github.wulkanowy.services.sync.notifications.NewHomeworkNotification
|
||||||
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import java.time.LocalDate.now
|
import java.time.LocalDate.now
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
@ -3,8 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewLuckyNumberNotification
|
import io.github.wulkanowy.services.sync.notifications.NewLuckyNumberNotification
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class LuckyNumberWork @Inject constructor(
|
class LuckyNumberWork @Inject constructor(
|
||||||
|
@ -4,8 +4,8 @@ import io.github.wulkanowy.data.db.entities.Semester
|
|||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.enums.MessageFolder.RECEIVED
|
import io.github.wulkanowy.data.enums.MessageFolder.RECEIVED
|
||||||
import io.github.wulkanowy.data.repositories.MessageRepository
|
import io.github.wulkanowy.data.repositories.MessageRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewMessageNotification
|
import io.github.wulkanowy.services.sync.notifications.NewMessageNotification
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
@ -3,8 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.NoteRepository
|
import io.github.wulkanowy.data.repositories.NoteRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewNoteNotification
|
import io.github.wulkanowy.services.sync.notifications.NewNoteNotification
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
@ -3,8 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.SchoolAnnouncementRepository
|
import io.github.wulkanowy.data.repositories.SchoolAnnouncementRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.NewSchoolAnnouncementNotification
|
import io.github.wulkanowy.services.sync.notifications.NewSchoolAnnouncementNotification
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
@ -3,7 +3,8 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.TeacherRepository
|
import io.github.wulkanowy.data.repositories.TeacherRepository
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
import io.github.wulkanowy.data.waitForResult
|
||||||
|
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class TeacherWork @Inject constructor(private val teacherRepository: TeacherRepository) : Work {
|
class TeacherWork @Inject constructor(private val teacherRepository: TeacherRepository) : Work {
|
||||||
|
@ -3,9 +3,9 @@ package io.github.wulkanowy.services.sync.works
|
|||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.TimetableRepository
|
import io.github.wulkanowy.data.repositories.TimetableRepository
|
||||||
|
import io.github.wulkanowy.data.waitForResult
|
||||||
import io.github.wulkanowy.services.sync.notifications.ChangeTimetableNotification
|
import io.github.wulkanowy.services.sync.notifications.ChangeTimetableNotification
|
||||||
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
||||||
import io.github.wulkanowy.utils.waitForResult
|
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import java.time.LocalDate.now
|
import java.time.LocalDate.now
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
@ -1,17 +1,10 @@
|
|||||||
package io.github.wulkanowy.ui.base
|
package io.github.wulkanowy.ui.base
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
import kotlinx.coroutines.*
|
||||||
import kotlinx.coroutines.CoroutineScope
|
|
||||||
import kotlinx.coroutines.Dispatchers
|
|
||||||
import kotlinx.coroutines.Job
|
|
||||||
import kotlinx.coroutines.SupervisorJob
|
|
||||||
import kotlinx.coroutines.cancelChildren
|
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.launchIn
|
import kotlinx.coroutines.flow.launchIn
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
|
|
||||||
open class BasePresenter<T : BaseView>(
|
open class BasePresenter<T : BaseView>(
|
||||||
@ -37,28 +30,28 @@ open class BasePresenter<T : BaseView>(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun onExpiredLoginSelected() {
|
fun onExpiredLoginSelected() {
|
||||||
flowWithResource {
|
Timber.i("Attempt to switch the student after the session expires")
|
||||||
val student = studentRepository.getCurrentStudent(false)
|
|
||||||
studentRepository.logoutStudent(student)
|
|
||||||
|
|
||||||
val students = studentRepository.getSavedStudents(false)
|
presenterScope.launch {
|
||||||
if (students.isNotEmpty()) {
|
runCatching {
|
||||||
Timber.i("Switching current student")
|
val student = studentRepository.getCurrentStudent(false)
|
||||||
studentRepository.switchStudent(students[0])
|
studentRepository.logoutStudent(student)
|
||||||
|
|
||||||
|
val students = studentRepository.getSavedStudents(false)
|
||||||
|
if (students.isNotEmpty()) {
|
||||||
|
Timber.i("Switching current student")
|
||||||
|
studentRepository.switchStudent(students[0])
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}.onEach {
|
.onFailure {
|
||||||
when (it.status) {
|
Timber.i("Switch student result: An exception occurred")
|
||||||
Status.LOADING -> Timber.i("Attempt to switch the student after the session expires")
|
errorHandler.dispatch(it)
|
||||||
Status.SUCCESS -> {
|
}
|
||||||
|
.onSuccess {
|
||||||
Timber.i("Switch student result: Open login view")
|
Timber.i("Switch student result: Open login view")
|
||||||
view?.openClearLoginView()
|
view?.openClearLoginView()
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Switch student result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.launch("expired")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fun <T> Flow<T>.launch(individualJobTag: String = "load"): Job {
|
fun <T> Flow<T>.launch(individualJobTag: String = "load"): Job {
|
||||||
|
@ -1,13 +1,11 @@
|
|||||||
package io.github.wulkanowy.ui.modules.about.contributor
|
package io.github.wulkanowy.ui.modules.about.contributor
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.pojos.Contributor
|
import io.github.wulkanowy.data.pojos.Contributor
|
||||||
import io.github.wulkanowy.data.repositories.AppCreatorRepository
|
import io.github.wulkanowy.data.repositories.AppCreatorRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class ContributorPresenter @Inject constructor(
|
class ContributorPresenter @Inject constructor(
|
||||||
@ -31,15 +29,11 @@ class ContributorPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource { appCreatorRepository.getAppCreators() }.onEach {
|
resourceFlow { appCreatorRepository.getAppCreators() }
|
||||||
when (it.status) {
|
.onResourceLoading { view?.showProgress(true) }
|
||||||
Status.LOADING -> view?.showProgress(true)
|
.onResourceSuccess { view?.updateData(it) }
|
||||||
Status.SUCCESS -> view?.run {
|
.onResourceNotLoading { view?.showProgress(false) }
|
||||||
showProgress(false)
|
.onResourceError { errorHandler.dispatch(it) }
|
||||||
updateData(it.data!!)
|
.launch()
|
||||||
}
|
|
||||||
Status.ERROR -> errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}.launch()
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,16 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.about.license
|
package io.github.wulkanowy.ui.modules.about.license
|
||||||
|
|
||||||
import com.mikepenz.aboutlibraries.entity.Library
|
import com.mikepenz.aboutlibraries.entity.Library
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.DispatchersProvider
|
import io.github.wulkanowy.utils.DispatchersProvider
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
import kotlinx.coroutines.launch
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
import timber.log.Timber
|
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class LicensePresenter @Inject constructor(
|
class LicensePresenter @Inject constructor(
|
||||||
@ -30,18 +26,16 @@ class LicensePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource {
|
presenterScope.launch {
|
||||||
withContext(dispatchers.io) {
|
runCatching {
|
||||||
view?.appLibraries.orEmpty()
|
withContext(dispatchers.io) {
|
||||||
|
view?.appLibraries.orEmpty()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}.onEach {
|
.onFailure { errorHandler.dispatch(it) }
|
||||||
when (it.status) {
|
.onSuccess { view?.updateData(it) }
|
||||||
Status.LOADING -> Timber.d("License data load started")
|
|
||||||
Status.SUCCESS -> view?.updateData(it.data!!)
|
|
||||||
Status.ERROR -> errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}.afterLoading {
|
|
||||||
view?.showProgress(false)
|
view?.showProgress(false)
|
||||||
}.launch()
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,12 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.account
|
package io.github.wulkanowy.ui.modules.account
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
|
import io.github.wulkanowy.data.onResourceError
|
||||||
|
import io.github.wulkanowy.data.onResourceSuccess
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -32,20 +33,10 @@ class AccountPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource { studentRepository.getSavedStudents(false) }
|
resourceFlow { studentRepository.getSavedStudents(false) }
|
||||||
.onEach {
|
.logResourceStatus("load account data")
|
||||||
when (it.status) {
|
.onResourceSuccess { view?.updateData(createAccountItems(it)) }
|
||||||
Status.LOADING -> Timber.i("Loading account data started")
|
.onResourceError(errorHandler::dispatch)
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading account result: Success")
|
|
||||||
view?.updateData(createAccountItems(it.data!!))
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading account result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
.launch("load")
|
.launch("load")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,7 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.account.accountdetails
|
package io.github.wulkanowy.ui.modules.account.accountdetails
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Resource
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
@ -9,10 +8,6 @@ import io.github.wulkanowy.services.sync.SyncManager
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.ui.modules.studentinfo.StudentInfoView
|
import io.github.wulkanowy.ui.modules.studentinfo.StudentInfoView
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.map
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -51,40 +46,25 @@ class AccountDetailsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource { studentRepository.getSavedStudents() }
|
resourceFlow { studentRepository.getSavedStudentById(studentId ?: -1) }
|
||||||
.map { studentWithSemesters ->
|
.logResourceStatus("loading account details view")
|
||||||
Resource(
|
.onResourceLoading {
|
||||||
data = studentWithSemesters.data?.single { it.student.id == studentId },
|
view?.run {
|
||||||
status = studentWithSemesters.status,
|
showProgress(true)
|
||||||
error = studentWithSemesters.error
|
showContent(false)
|
||||||
)
|
|
||||||
}
|
|
||||||
.onEach {
|
|
||||||
when (it.status) {
|
|
||||||
Status.LOADING -> {
|
|
||||||
view?.run {
|
|
||||||
showProgress(true)
|
|
||||||
showContent(false)
|
|
||||||
}
|
|
||||||
Timber.i("Loading account details view started")
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading account details view result: Success")
|
|
||||||
studentWithSemesters = it.data
|
|
||||||
view?.run {
|
|
||||||
showAccountData(studentWithSemesters!!.student)
|
|
||||||
enableSelectStudentButton(!studentWithSemesters!!.student.isCurrent)
|
|
||||||
showContent(true)
|
|
||||||
showErrorView(false)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading account details view result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.afterLoading { view?.showProgress(false) }
|
.onResourceSuccess {
|
||||||
|
studentWithSemesters = it
|
||||||
|
view?.run {
|
||||||
|
showAccountData(studentWithSemesters!!.student)
|
||||||
|
enableSelectStudentButton(!studentWithSemesters!!.student.isCurrent)
|
||||||
|
showContent(true)
|
||||||
|
showErrorView(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceNotLoading { view?.showProgress(false) }
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
.launch()
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -105,22 +85,12 @@ class AccountDetailsPresenter @Inject constructor(
|
|||||||
|
|
||||||
Timber.i("Select student ${studentWithSemesters!!.student.id}")
|
Timber.i("Select student ${studentWithSemesters!!.student.id}")
|
||||||
|
|
||||||
flowWithResource { studentRepository.switchStudent(studentWithSemesters!!) }
|
resourceFlow { studentRepository.switchStudent(studentWithSemesters!!) }
|
||||||
.onEach {
|
.logResourceStatus("change student")
|
||||||
when (it.status) {
|
.onResourceSuccess { view?.recreateMainView() }
|
||||||
Status.LOADING -> Timber.i("Attempt to change a student")
|
.onResourceNotLoading { view?.popViewToMain() }
|
||||||
Status.SUCCESS -> {
|
.onResourceError(errorHandler::dispatch)
|
||||||
Timber.i("Change a student result: Success")
|
.launch("switch")
|
||||||
view?.recreateMainView()
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Change a student result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.afterLoading {
|
|
||||||
view?.popViewToMain()
|
|
||||||
}.launch("switch")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fun onRemoveSelected() {
|
fun onRemoveSelected() {
|
||||||
@ -131,7 +101,7 @@ class AccountDetailsPresenter @Inject constructor(
|
|||||||
fun onLogoutConfirm() {
|
fun onLogoutConfirm() {
|
||||||
if (studentWithSemesters == null) return
|
if (studentWithSemesters == null) return
|
||||||
|
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val studentToLogout = studentWithSemesters!!.student
|
val studentToLogout = studentWithSemesters!!.student
|
||||||
|
|
||||||
studentRepository.logoutStudent(studentToLogout)
|
studentRepository.logoutStudent(studentToLogout)
|
||||||
@ -141,13 +111,13 @@ class AccountDetailsPresenter @Inject constructor(
|
|||||||
studentRepository.switchStudent(students[0])
|
studentRepository.switchStudent(students[0])
|
||||||
}
|
}
|
||||||
|
|
||||||
return@flowWithResource students
|
students
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("logout user")
|
||||||
Status.LOADING -> Timber.i("Attempt to logout user")
|
.onResourceSuccess {
|
||||||
Status.SUCCESS -> view?.run {
|
view?.run {
|
||||||
when {
|
when {
|
||||||
it.data!!.isEmpty() -> {
|
it.isEmpty() -> {
|
||||||
Timber.i("Logout result: Open login view")
|
Timber.i("Logout result: Open login view")
|
||||||
syncManager.stopSyncWorker()
|
syncManager.stopSyncWorker()
|
||||||
openClearLoginView()
|
openClearLoginView()
|
||||||
@ -162,18 +132,16 @@ class AccountDetailsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Logout result: An exception occurred")
|
.onResourceNotLoading {
|
||||||
errorHandler.dispatch(it.error!!)
|
if (studentWithSemesters?.student?.isCurrent == true) {
|
||||||
|
view?.popViewToMain()
|
||||||
|
} else {
|
||||||
|
view?.popViewToAccounts()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceError(errorHandler::dispatch)
|
||||||
if (studentWithSemesters?.student?.isCurrent == true) {
|
.launch("logout")
|
||||||
view?.popViewToMain()
|
|
||||||
} else {
|
|
||||||
view?.popViewToAccounts()
|
|
||||||
}
|
|
||||||
}.launch("logout")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,15 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.account.accountedit
|
package io.github.wulkanowy.ui.modules.account.accountedit
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.db.entities.StudentNickAndAvatar
|
import io.github.wulkanowy.data.db.entities.StudentNickAndAvatar
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AppInfo
|
import io.github.wulkanowy.utils.AppInfo
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -38,43 +35,26 @@ class AccountEditPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource {
|
resourceFlow { studentRepository.getStudentById(student.id, false).avatarColor }
|
||||||
studentRepository.getStudentById(student.id, false).avatarColor
|
.logResourceStatus("load student")
|
||||||
}.onEach { resource ->
|
.onResourceSuccess { view?.updateSelectedColorData(it.toInt()) }
|
||||||
when (resource.status) {
|
.onResourceError(errorHandler::dispatch)
|
||||||
Status.LOADING -> Timber.i("Attempt to load student")
|
.launch("load_data")
|
||||||
Status.SUCCESS -> {
|
|
||||||
view?.updateSelectedColorData(resource.data?.toInt()!!)
|
|
||||||
Timber.i("Attempt to load student: Success")
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Attempt to load student: An exception occurred")
|
|
||||||
errorHandler.dispatch(resource.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.launch("load_data")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fun changeStudentNickAndAvatar(nick: String, avatarColor: Int) {
|
fun changeStudentNickAndAvatar(nick: String, avatarColor: Int) {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val studentNick =
|
val studentNick = StudentNickAndAvatar(
|
||||||
StudentNickAndAvatar(nick = nick.trim(), avatarColor = avatarColor.toLong())
|
nick = nick.trim(),
|
||||||
.apply { id = student.id }
|
avatarColor = avatarColor.toLong()
|
||||||
|
).apply { id = student.id }
|
||||||
|
|
||||||
studentRepository.updateStudentNickAndAvatar(studentNick)
|
studentRepository.updateStudentNickAndAvatar(studentNick)
|
||||||
}.onEach {
|
|
||||||
when (it.status) {
|
|
||||||
Status.LOADING -> Timber.i("Attempt to change a student nick and avatar")
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Change a student nick and avatar result: Success")
|
|
||||||
view?.recreateMainView()
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Change a student nick and avatar result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
.afterLoading { view?.popView() }
|
.logResourceStatus("change student nick and avatar")
|
||||||
|
.onResourceSuccess { view?.recreateMainView() }
|
||||||
|
.onResourceNotLoading { view?.popView() }
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
.launch("update_student")
|
.launch("update_student")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,14 +1,11 @@
|
|||||||
package io.github.wulkanowy.ui.modules.account.accountquick
|
package io.github.wulkanowy.ui.modules.account.accountquick
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.ui.modules.account.AccountItem
|
import io.github.wulkanowy.ui.modules.account.AccountItem
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -43,21 +40,11 @@ class AccountQuickPresenter @Inject constructor(
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
flowWithResource { studentRepository.switchStudent(studentWithSemesters) }
|
resourceFlow { studentRepository.switchStudent(studentWithSemesters) }
|
||||||
.onEach {
|
.logResourceStatus("change student")
|
||||||
when (it.status) {
|
.onResourceSuccess { view?.recreateMainView() }
|
||||||
Status.LOADING -> Timber.i("Attempt to change a student")
|
.onResourceNotLoading { view?.popView() }
|
||||||
Status.SUCCESS -> {
|
.onResourceError(errorHandler::dispatch)
|
||||||
Timber.i("Change a student result: Success")
|
|
||||||
view?.recreateMainView()
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Change a student result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
.afterLoading { view?.popView() }
|
|
||||||
.launch("switch")
|
.launch("switch")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
package io.github.wulkanowy.ui.modules.attendance
|
package io.github.wulkanowy.ui.modules.attendance
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Attendance
|
import io.github.wulkanowy.data.db.entities.Attendance
|
||||||
import io.github.wulkanowy.data.repositories.AttendanceRepository
|
import io.github.wulkanowy.data.repositories.AttendanceRepository
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
||||||
@ -9,18 +9,7 @@ import io.github.wulkanowy.data.repositories.SemesterRepository
|
|||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.*
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.capitalise
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.getLastSchoolDayIfHoliday
|
|
||||||
import io.github.wulkanowy.utils.isExcusableOrNotExcused
|
|
||||||
import io.github.wulkanowy.utils.isHolidays
|
|
||||||
import io.github.wulkanowy.utils.nextSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.previousOrSameSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.previousSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.flow
|
import kotlinx.coroutines.flow.flow
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
@ -213,93 +202,77 @@ class AttendancePresenter @Inject constructor(
|
|||||||
|
|
||||||
var isParent = false
|
var isParent = false
|
||||||
|
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
isParent = student.isParent
|
isParent = student.isParent
|
||||||
|
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
attendanceRepository.getAttendance(
|
attendanceRepository.getAttendance(
|
||||||
student,
|
student = student,
|
||||||
semester,
|
semester = semester,
|
||||||
currentDate,
|
start = currentDate,
|
||||||
currentDate,
|
end = currentDate,
|
||||||
forceRefresh
|
forceRefresh = forceRefresh
|
||||||
)
|
)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load attendance")
|
||||||
Status.LOADING -> {
|
.onResourceLoading {
|
||||||
view?.showExcuseButton(false)
|
view?.showExcuseButton(false)
|
||||||
if (!it.data.isNullOrEmpty()) {
|
}
|
||||||
val filteredAttendance = if (prefRepository.isShowPresent) {
|
.mapResourceData {
|
||||||
it.data
|
if (prefRepository.isShowPresent) {
|
||||||
} else {
|
it
|
||||||
it.data.filter { item -> !item.presence }
|
} else {
|
||||||
}
|
it.filter { item -> !item.presence }
|
||||||
|
}.sortedBy { item -> item.number }
|
||||||
view?.run {
|
}
|
||||||
enableSwipe(true)
|
.onResourceData {
|
||||||
showRefresh(true)
|
view?.run {
|
||||||
showProgress(false)
|
enableSwipe(true)
|
||||||
showErrorView(false)
|
showProgress(false)
|
||||||
showEmpty(filteredAttendance.isEmpty())
|
showErrorView(false)
|
||||||
showContent(filteredAttendance.isNotEmpty())
|
showEmpty(it.isEmpty())
|
||||||
updateData(filteredAttendance.sortedBy { item -> item.number })
|
showContent(it.isNotEmpty())
|
||||||
}
|
updateData(it)
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading attendance result: Success")
|
|
||||||
val filteredAttendance = if (prefRepository.isShowPresent) {
|
|
||||||
it.data.orEmpty()
|
|
||||||
} else {
|
|
||||||
it.data?.filter { item -> !item.presence }.orEmpty()
|
|
||||||
}
|
|
||||||
|
|
||||||
isVulcanExcusedFunctionEnabled =
|
|
||||||
filteredAttendance.any { item -> item.excusable }
|
|
||||||
|
|
||||||
view?.apply {
|
|
||||||
updateData(filteredAttendance.sortedBy { item -> item.number })
|
|
||||||
showEmpty(filteredAttendance.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
showContent(filteredAttendance.isNotEmpty())
|
|
||||||
val anyExcusables = filteredAttendance.any { it.isExcusableOrNotExcused }
|
|
||||||
showExcuseButton(anyExcusables && (isParent || isVulcanExcusedFunctionEnabled))
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "attendance",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading attendance result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
isVulcanExcusedFunctionEnabled = it.any { item -> item.excusable }
|
||||||
showProgress(false)
|
val anyExcusables = it.any { it.isExcusableOrNotExcused }
|
||||||
enableSwipe(true)
|
view?.showExcuseButton(anyExcusables && (isParent || isVulcanExcusedFunctionEnabled))
|
||||||
|
|
||||||
|
analytics.logEvent(
|
||||||
|
"load_data",
|
||||||
|
"type" to "attendance",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
showRefresh(false)
|
||||||
|
showProgress(false)
|
||||||
|
enableSwipe(true)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun excuseAbsence(reason: String?, toExcuseList: List<Attendance>) {
|
private fun excuseAbsence(reason: String?, toExcuseList: List<Attendance>) {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
attendanceRepository.excuseForAbsence(student, semester, toExcuseList, reason)
|
attendanceRepository.excuseForAbsence(student, semester, toExcuseList, reason)
|
||||||
}.onEach {
|
}.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> view?.run {
|
is Resource.Loading -> view?.run {
|
||||||
Timber.i("Excusing absence started")
|
Timber.i("Excusing absence started")
|
||||||
showProgress(true)
|
showProgress(true)
|
||||||
showContent(false)
|
showContent(false)
|
||||||
showExcuseButton(false)
|
showExcuseButton(false)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
Timber.i("Excusing for absence result: Success")
|
Timber.i("Excusing for absence result: Success")
|
||||||
analytics.logEvent("excuse_absence", "items" to attendanceToExcuseList.size)
|
analytics.logEvent("excuse_absence", "items" to attendanceToExcuseList.size)
|
||||||
attendanceToExcuseList.clear()
|
attendanceToExcuseList.clear()
|
||||||
@ -311,9 +284,9 @@ class AttendancePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
loadData(forceRefresh = true)
|
loadData(forceRefresh = true)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Excusing for absence result: An exception occurred")
|
Timber.i("Excusing for absence result: An exception occurred")
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
loadData()
|
loadData()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -74,7 +74,7 @@ class AttendanceSummaryFragment :
|
|||||||
binding.attendanceSummarySubjectsContainer.elevation = requireContext().dpToPx(1f)
|
binding.attendanceSummarySubjectsContainer.elevation = requireContext().dpToPx(1f)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun updateSubjects(data: ArrayList<String>) {
|
override fun updateSubjects(data: Collection<String>) {
|
||||||
with(subjectsAdapter) {
|
with(subjectsAdapter) {
|
||||||
clear()
|
clear()
|
||||||
addAll(data)
|
addAll(data)
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.attendance.summary
|
package io.github.wulkanowy.ui.modules.attendance.summary
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.AttendanceSummary
|
import io.github.wulkanowy.data.db.entities.AttendanceSummary
|
||||||
import io.github.wulkanowy.data.db.entities.Subject
|
import io.github.wulkanowy.data.db.entities.Subject
|
||||||
import io.github.wulkanowy.data.repositories.AttendanceSummaryRepository
|
import io.github.wulkanowy.data.repositories.AttendanceSummaryRepository
|
||||||
@ -10,9 +10,6 @@ import io.github.wulkanowy.data.repositories.SubjectRepository
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import java.time.Month
|
import java.time.Month
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -75,11 +72,9 @@ class AttendanceSummaryPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(subjectId: Int, forceRefresh: Boolean = false) {
|
private fun loadData(subjectId: Int, forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading attendance summary data started")
|
|
||||||
|
|
||||||
currentSubjectId = subjectId
|
currentSubjectId = subjectId
|
||||||
|
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
|
|
||||||
@ -89,47 +84,37 @@ class AttendanceSummaryPresenter @Inject constructor(
|
|||||||
subjectId = subjectId,
|
subjectId = subjectId,
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
)
|
)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load attendance summary")
|
||||||
Status.LOADING -> {
|
.mapResourceData(this::sortItems)
|
||||||
if (!it.data.isNullOrEmpty()) {
|
.onResourceData {
|
||||||
view?.run {
|
view?.run {
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
showRefresh(true)
|
showProgress(false)
|
||||||
showProgress(false)
|
showErrorView(false)
|
||||||
showContent(true)
|
showContent(it.isNotEmpty())
|
||||||
showErrorView(false)
|
showEmpty(it.isEmpty())
|
||||||
updateDataSet(sortItems(it.data))
|
updateDataSet(it)
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading attendance summary result: Success")
|
|
||||||
view?.apply {
|
|
||||||
showErrorView(false)
|
|
||||||
showEmpty(it.data!!.isEmpty())
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
updateDataSet(sortItems(it.data))
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "attendance_summary",
|
|
||||||
"items" to it.data!!.size,
|
|
||||||
"item_id" to subjectId
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading attendance summary result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "attendance_summary",
|
||||||
|
"items" to it.size,
|
||||||
|
"item_id" to subjectId
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
enableSwipe(true)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun sortItems(items: List<AttendanceSummary>) = items.sortedByDescending { item ->
|
private fun sortItems(items: List<AttendanceSummary>) = items.sortedByDescending { item ->
|
||||||
@ -148,27 +133,20 @@ class AttendanceSummaryPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadSubjects() {
|
private fun loadSubjects() {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
subjectRepository.getSubjects(student, semester)
|
subjectRepository.getSubjects(student, semester)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load attendance summary subjects")
|
||||||
Status.LOADING -> Timber.i("Loading attendance summary subjects started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
subjects = it
|
||||||
subjects = it.data!!
|
view?.run {
|
||||||
|
view?.updateSubjects(it.map { subject -> subject.name }.toList())
|
||||||
Timber.i("Loading attendance summary subjects result: Success")
|
showSubjects(true)
|
||||||
view?.run {
|
|
||||||
view?.updateSubjects(ArrayList(it.data.map { subject -> subject.name }))
|
|
||||||
showSubjects(true)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading attendance summary subjects result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("subjects")
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch("subjects")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -25,7 +25,7 @@ interface AttendanceSummaryView : BaseView {
|
|||||||
|
|
||||||
fun updateDataSet(data: List<AttendanceSummary>)
|
fun updateDataSet(data: List<AttendanceSummary>)
|
||||||
|
|
||||||
fun updateSubjects(data: ArrayList<String>)
|
fun updateSubjects(data: Collection<String>)
|
||||||
|
|
||||||
fun showSubjects(show: Boolean)
|
fun showSubjects(show: Boolean)
|
||||||
|
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.conference
|
package io.github.wulkanowy.ui.modules.conference
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Conference
|
import io.github.wulkanowy.data.db.entities.Conference
|
||||||
import io.github.wulkanowy.data.repositories.ConferenceRepository
|
import io.github.wulkanowy.data.repositories.ConferenceRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
@ -8,9 +8,6 @@ import io.github.wulkanowy.data.repositories.StudentRepository
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -64,50 +61,39 @@ class ConferencePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading conference data started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
conferenceRepository.getConferences(student, semester, forceRefresh)
|
conferenceRepository.getConferences(student, semester, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load conference data")
|
||||||
Status.LOADING -> {
|
.mapResourceData { it.sortedByDescending { conference -> conference.date } }
|
||||||
if (!it.data.isNullOrEmpty()) {
|
.onResourceData {
|
||||||
view?.run {
|
view?.run {
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
showRefresh(true)
|
showProgress(false)
|
||||||
showProgress(false)
|
showErrorView(false)
|
||||||
showContent(true)
|
showContent(it.isNotEmpty())
|
||||||
updateData(it.data.sortedByDescending { conference -> conference.date })
|
showEmpty(it.isEmpty())
|
||||||
}
|
updateData(it)
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading conference result: Success")
|
|
||||||
view?.run {
|
|
||||||
updateData(it.data!!.sortedByDescending { conference -> conference.date })
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "conferences",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading conference result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "conferences",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.dashboard
|
package io.github.wulkanowy.ui.modules.dashboard
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Resource
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.AdminMessage
|
import io.github.wulkanowy.data.db.entities.AdminMessage
|
||||||
import io.github.wulkanowy.data.db.entities.LuckyNumber
|
import io.github.wulkanowy.data.db.entities.LuckyNumber
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
@ -10,7 +9,6 @@ import io.github.wulkanowy.data.repositories.*
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.calculatePercentage
|
import io.github.wulkanowy.utils.calculatePercentage
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
||||||
import kotlinx.coroutines.flow.*
|
import kotlinx.coroutines.flow.*
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
@ -104,7 +102,7 @@ class DashboardPresenter @Inject constructor(
|
|||||||
forceRefresh: Boolean
|
forceRefresh: Boolean
|
||||||
) = dashboardTilesToLoad.filter { newItemToLoad ->
|
) = dashboardTilesToLoad.filter { newItemToLoad ->
|
||||||
dashboardLoadedTiles.none { it == newItemToLoad } || forceRefresh
|
dashboardLoadedTiles.none { it == newItemToLoad } || forceRefresh
|
||||||
|| newItemToLoad == DashboardItem.Tile.ADMIN_MESSAGE
|
|| newItemToLoad == DashboardItem.Tile.ADMIN_MESSAGE
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun removeUnselectedTiles(tilesToLoad: List<DashboardItem.Tile>) {
|
private fun removeUnselectedTiles(tilesToLoad: List<DashboardItem.Tile>) {
|
||||||
@ -225,27 +223,26 @@ class DashboardPresenter @Inject constructor(
|
|||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
val selectedTiles = preferencesRepository.selectedDashboardTiles
|
val selectedTiles = preferencesRepository.selectedDashboardTiles
|
||||||
|
|
||||||
|
val flowSuccess = flowOf(Resource.Success(null))
|
||||||
val luckyNumberFlow = luckyNumberRepository.getLuckyNumber(student, forceRefresh)
|
val luckyNumberFlow = luckyNumberRepository.getLuckyNumber(student, forceRefresh)
|
||||||
.map {
|
.mapResourceData {
|
||||||
if (it.data == null) {
|
it ?: LuckyNumber(0, LocalDate.now(), 0)
|
||||||
it.copy(data = LuckyNumber(0, LocalDate.now(), 0))
|
|
||||||
} else it
|
|
||||||
}
|
}
|
||||||
.takeIf { DashboardItem.Tile.LUCKY_NUMBER in selectedTiles } ?: flowOf(null)
|
.takeIf { DashboardItem.Tile.LUCKY_NUMBER in selectedTiles } ?: flowSuccess
|
||||||
|
|
||||||
val messageFLow = messageRepository.getMessages(
|
val messageFLow = messageRepository.getMessages(
|
||||||
student = student,
|
student = student,
|
||||||
semester = semester,
|
semester = semester,
|
||||||
folder = MessageFolder.RECEIVED,
|
folder = MessageFolder.RECEIVED,
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
).takeIf { DashboardItem.Tile.MESSAGES in selectedTiles } ?: flowOf(null)
|
).takeIf { DashboardItem.Tile.MESSAGES in selectedTiles } ?: flowSuccess
|
||||||
|
|
||||||
val attendanceFlow = attendanceSummaryRepository.getAttendanceSummary(
|
val attendanceFlow = attendanceSummaryRepository.getAttendanceSummary(
|
||||||
student = student,
|
student = student,
|
||||||
semester = semester,
|
semester = semester,
|
||||||
subjectId = -1,
|
subjectId = -1,
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
).takeIf { DashboardItem.Tile.ATTENDANCE in selectedTiles } ?: flowOf(null)
|
).takeIf { DashboardItem.Tile.ATTENDANCE in selectedTiles } ?: flowSuccess
|
||||||
|
|
||||||
emitAll(
|
emitAll(
|
||||||
combine(
|
combine(
|
||||||
@ -253,17 +250,13 @@ class DashboardPresenter @Inject constructor(
|
|||||||
messageFLow,
|
messageFLow,
|
||||||
attendanceFlow
|
attendanceFlow
|
||||||
) { luckyNumberResource, messageResource, attendanceResource ->
|
) { luckyNumberResource, messageResource, attendanceResource ->
|
||||||
val error =
|
val resList = listOf(luckyNumberResource, messageResource, attendanceResource)
|
||||||
luckyNumberResource?.error ?: messageResource?.error
|
resList.firstNotNullOfOrNull { it.errorOrNull }?.let { throw it }
|
||||||
?: attendanceResource?.error
|
val isLoading = resList.any { it is Resource.Loading }
|
||||||
error?.let { throw it }
|
|
||||||
|
|
||||||
val luckyNumber = luckyNumberResource?.data?.luckyNumber
|
val luckyNumber = luckyNumberResource.dataOrNull?.luckyNumber
|
||||||
val messageCount = messageResource?.data?.count { it.unread }
|
val messageCount = messageResource.dataOrNull?.count { it.unread }
|
||||||
val attendancePercentage = attendanceResource?.data?.calculatePercentage()
|
val attendancePercentage = attendanceResource.dataOrNull?.calculatePercentage()
|
||||||
|
|
||||||
val isLoading =
|
|
||||||
luckyNumberResource?.status == Status.LOADING || messageResource?.status == Status.LOADING || attendanceResource?.status == Status.LOADING
|
|
||||||
|
|
||||||
DashboardItem.HorizontalGroup(
|
DashboardItem.HorizontalGroup(
|
||||||
isLoading = isLoading,
|
isLoading = isLoading,
|
||||||
@ -300,68 +293,65 @@ class DashboardPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadGrades(student: Student, forceRefresh: Boolean) {
|
private fun loadGrades(student: Student, forceRefresh: Boolean) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
|
|
||||||
gradeRepository.getGrades(student, semester, forceRefresh)
|
gradeRepository.getGrades(student, semester, forceRefresh)
|
||||||
}.map { originalResource ->
|
}
|
||||||
val filteredSubjectWithGrades = originalResource.data?.first
|
.mapResourceData { (details, _) ->
|
||||||
.orEmpty()
|
val filteredSubjectWithGrades = details
|
||||||
.filter { it.date >= LocalDate.now().minusDays(7) }
|
.filter { it.date >= LocalDate.now().minusDays(7) }
|
||||||
.groupBy { it.subject }
|
.groupBy { it.subject }
|
||||||
.mapValues { entry ->
|
.mapValues { entry ->
|
||||||
entry.value
|
entry.value
|
||||||
.take(5)
|
.take(5)
|
||||||
.sortedByDescending { it.date }
|
.sortedByDescending { it.date }
|
||||||
}
|
}
|
||||||
.toList()
|
.toList()
|
||||||
.sortedByDescending { (_, grades) -> grades[0].date }
|
.sortedByDescending { (_, grades) -> grades[0].date }
|
||||||
.toMap()
|
.toMap()
|
||||||
|
|
||||||
Resource(
|
filteredSubjectWithGrades
|
||||||
status = originalResource.status,
|
}
|
||||||
data = filteredSubjectWithGrades.takeIf { originalResource.data != null },
|
.onEach {
|
||||||
error = originalResource.error
|
when (it) {
|
||||||
)
|
is Resource.Loading -> {
|
||||||
}.onEach {
|
Timber.i("Loading dashboard grades data started")
|
||||||
when (it.status) {
|
if (forceRefresh) return@onEach
|
||||||
Status.LOADING -> {
|
updateData(
|
||||||
Timber.i("Loading dashboard grades data started")
|
DashboardItem.Grades(
|
||||||
if (forceRefresh) return@onEach
|
subjectWithGrades = it.dataOrNull,
|
||||||
|
gradeTheme = preferencesRepository.gradeColorTheme,
|
||||||
|
isLoading = true
|
||||||
|
), forceRefresh
|
||||||
|
)
|
||||||
|
|
||||||
updateData(
|
if (!it.dataOrNull.isNullOrEmpty()) {
|
||||||
DashboardItem.Grades(
|
firstLoadedItemList += DashboardItem.Type.GRADES
|
||||||
subjectWithGrades = it.data,
|
}
|
||||||
gradeTheme = preferencesRepository.gradeColorTheme,
|
}
|
||||||
isLoading = true
|
is Resource.Success -> {
|
||||||
), forceRefresh
|
Timber.i("Loading dashboard grades result: Success")
|
||||||
)
|
updateData(
|
||||||
|
DashboardItem.Grades(
|
||||||
if (!it.data.isNullOrEmpty()) {
|
subjectWithGrades = it.data,
|
||||||
firstLoadedItemList += DashboardItem.Type.GRADES
|
gradeTheme = preferencesRepository.gradeColorTheme
|
||||||
|
),
|
||||||
|
forceRefresh
|
||||||
|
)
|
||||||
|
}
|
||||||
|
is Resource.Error -> {
|
||||||
|
Timber.i("Loading dashboard grades result: An exception occurred")
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
updateData(DashboardItem.Grades(error = it.error), forceRefresh)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading dashboard grades result: Success")
|
|
||||||
updateData(
|
|
||||||
DashboardItem.Grades(
|
|
||||||
subjectWithGrades = it.data,
|
|
||||||
gradeTheme = preferencesRepository.gradeColorTheme
|
|
||||||
),
|
|
||||||
forceRefresh
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading dashboard grades result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
updateData(DashboardItem.Grades(error = it.error), forceRefresh)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}.launchWithUniqueRefreshJob("dashboard_grades", forceRefresh)
|
.launchWithUniqueRefreshJob("dashboard_grades", forceRefresh)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadLessons(student: Student, forceRefresh: Boolean) {
|
private fun loadLessons(student: Student, forceRefresh: Boolean) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
val date = LocalDate.now().nextOrSameSchoolDay
|
val date = LocalDate.now().nextOrSameSchoolDay
|
||||||
|
|
||||||
@ -372,40 +362,41 @@ class DashboardPresenter @Inject constructor(
|
|||||||
end = date.plusDays(1),
|
end = date.plusDays(1),
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
)
|
)
|
||||||
|
}
|
||||||
|
.onEach {
|
||||||
|
when (it) {
|
||||||
|
is Resource.Loading -> {
|
||||||
|
Timber.i("Loading dashboard lessons data started")
|
||||||
|
if (forceRefresh) return@onEach
|
||||||
|
updateData(
|
||||||
|
DashboardItem.Lessons(it.dataOrNull, isLoading = true),
|
||||||
|
forceRefresh
|
||||||
|
)
|
||||||
|
|
||||||
}.onEach {
|
if (!it.dataOrNull?.lessons.isNullOrEmpty()) {
|
||||||
when (it.status) {
|
firstLoadedItemList += DashboardItem.Type.LESSONS
|
||||||
Status.LOADING -> {
|
}
|
||||||
Timber.i("Loading dashboard lessons data started")
|
}
|
||||||
if (forceRefresh) return@onEach
|
is Resource.Success -> {
|
||||||
updateData(
|
Timber.i("Loading dashboard lessons result: Success")
|
||||||
DashboardItem.Lessons(it.data, isLoading = true),
|
updateData(
|
||||||
forceRefresh
|
DashboardItem.Lessons(it.data), forceRefresh
|
||||||
)
|
)
|
||||||
|
}
|
||||||
if (!it.data?.lessons.isNullOrEmpty()) {
|
is Resource.Error -> {
|
||||||
firstLoadedItemList += DashboardItem.Type.LESSONS
|
Timber.i("Loading dashboard lessons result: An exception occurred")
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
updateData(
|
||||||
|
DashboardItem.Lessons(error = it.error), forceRefresh
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading dashboard lessons result: Success")
|
|
||||||
updateData(
|
|
||||||
DashboardItem.Lessons(it.data), forceRefresh
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading dashboard lessons result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
updateData(
|
|
||||||
DashboardItem.Lessons(error = it.error), forceRefresh
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}.launchWithUniqueRefreshJob("dashboard_lessons", forceRefresh)
|
.launchWithUniqueRefreshJob("dashboard_lessons", forceRefresh)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadHomework(student: Student, forceRefresh: Boolean) {
|
private fun loadHomework(student: Student, forceRefresh: Boolean) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
val date = LocalDate.now().nextOrSameSchoolDay
|
val date = LocalDate.now().nextOrSameSchoolDay
|
||||||
|
|
||||||
@ -416,73 +407,79 @@ class DashboardPresenter @Inject constructor(
|
|||||||
end = date,
|
end = date,
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
)
|
)
|
||||||
}.map { homeworkResource ->
|
}
|
||||||
val currentDate = LocalDate.now()
|
.mapResourceData { homework ->
|
||||||
|
val currentDate = LocalDate.now()
|
||||||
|
|
||||||
val filteredHomework = homeworkResource.data
|
val filteredHomework = homework.filter {
|
||||||
?.filter { (it.date.isAfter(currentDate) || it.date == currentDate) && !it.isDone }
|
(it.date.isAfter(currentDate) || it.date == currentDate) && !it.isDone
|
||||||
?.sortedBy { it.date }
|
}.sortedBy { it.date }
|
||||||
|
|
||||||
homeworkResource.copy(data = filteredHomework)
|
filteredHomework
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.onEach {
|
||||||
Status.LOADING -> {
|
when (it) {
|
||||||
Timber.i("Loading dashboard homework data started")
|
is Resource.Loading -> {
|
||||||
if (forceRefresh) return@onEach
|
Timber.i("Loading dashboard homework data started")
|
||||||
updateData(
|
if (forceRefresh) return@onEach
|
||||||
DashboardItem.Homework(it.data ?: emptyList(), isLoading = true),
|
val data = it.dataOrNull.orEmpty()
|
||||||
forceRefresh
|
updateData(
|
||||||
)
|
DashboardItem.Homework(data, isLoading = true),
|
||||||
|
forceRefresh
|
||||||
|
)
|
||||||
|
|
||||||
if (!it.data.isNullOrEmpty()) {
|
if (data.isNotEmpty()) {
|
||||||
firstLoadedItemList += DashboardItem.Type.HOMEWORK
|
firstLoadedItemList += DashboardItem.Type.HOMEWORK
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is Resource.Success -> {
|
||||||
|
Timber.i("Loading dashboard homework result: Success")
|
||||||
|
updateData(DashboardItem.Homework(it.data), forceRefresh)
|
||||||
|
}
|
||||||
|
is Resource.Error -> {
|
||||||
|
Timber.i("Loading dashboard homework result: An exception occurred")
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
updateData(DashboardItem.Homework(error = it.error), forceRefresh)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading dashboard homework result: Success")
|
|
||||||
updateData(DashboardItem.Homework(it.data ?: emptyList()), forceRefresh)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading dashboard homework result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
updateData(DashboardItem.Homework(error = it.error), forceRefresh)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}.launchWithUniqueRefreshJob("dashboard_homework", forceRefresh)
|
.launchWithUniqueRefreshJob("dashboard_homework", forceRefresh)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadSchoolAnnouncements(student: Student, forceRefresh: Boolean) {
|
private fun loadSchoolAnnouncements(student: Student, forceRefresh: Boolean) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
schoolAnnouncementRepository.getSchoolAnnouncements(student, forceRefresh)
|
schoolAnnouncementRepository.getSchoolAnnouncements(student, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.onEach {
|
||||||
Status.LOADING -> {
|
when (it) {
|
||||||
Timber.i("Loading dashboard announcements data started")
|
is Resource.Loading -> {
|
||||||
if (forceRefresh) return@onEach
|
Timber.i("Loading dashboard announcements data started")
|
||||||
updateData(
|
if (forceRefresh) return@onEach
|
||||||
DashboardItem.Announcements(it.data ?: emptyList(), isLoading = true),
|
updateData(
|
||||||
forceRefresh
|
DashboardItem.Announcements(it.dataOrNull.orEmpty(), isLoading = true),
|
||||||
)
|
forceRefresh
|
||||||
|
)
|
||||||
|
|
||||||
if (!it.data.isNullOrEmpty()) {
|
if (!it.dataOrNull.isNullOrEmpty()) {
|
||||||
firstLoadedItemList += DashboardItem.Type.ANNOUNCEMENTS
|
firstLoadedItemList += DashboardItem.Type.ANNOUNCEMENTS
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is Resource.Success -> {
|
||||||
|
Timber.i("Loading dashboard announcements result: Success")
|
||||||
|
updateData(DashboardItem.Announcements(it.data), forceRefresh)
|
||||||
|
}
|
||||||
|
is Resource.Error -> {
|
||||||
|
Timber.i("Loading dashboard announcements result: An exception occurred")
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
updateData(DashboardItem.Announcements(error = it.error), forceRefresh)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading dashboard announcements result: Success")
|
|
||||||
updateData(DashboardItem.Announcements(it.data ?: emptyList()), forceRefresh)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading dashboard announcements result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
updateData(DashboardItem.Announcements(error = it.error), forceRefresh)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}.launchWithUniqueRefreshJob("dashboard_announcements", forceRefresh)
|
.launchWithUniqueRefreshJob("dashboard_announcements", forceRefresh)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadExams(student: Student, forceRefresh: Boolean) {
|
private fun loadExams(student: Student, forceRefresh: Boolean) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
|
|
||||||
examRepository.getExams(
|
examRepository.getExams(
|
||||||
@ -493,40 +490,37 @@ class DashboardPresenter @Inject constructor(
|
|||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
.map { examResource ->
|
.mapResourceData { exams -> exams.sortedBy { exam -> exam.date } }
|
||||||
val sortedExams = examResource.data?.sortedBy { it.date }
|
|
||||||
|
|
||||||
examResource.copy(data = sortedExams)
|
|
||||||
}
|
|
||||||
.onEach {
|
.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> {
|
is Resource.Loading -> {
|
||||||
Timber.i("Loading dashboard exams data started")
|
Timber.i("Loading dashboard exams data started")
|
||||||
if (forceRefresh) return@onEach
|
if (forceRefresh) return@onEach
|
||||||
updateData(
|
updateData(
|
||||||
DashboardItem.Exams(it.data.orEmpty(), isLoading = true),
|
DashboardItem.Exams(it.dataOrNull.orEmpty(), isLoading = true),
|
||||||
forceRefresh
|
forceRefresh
|
||||||
)
|
)
|
||||||
|
|
||||||
if (!it.data.isNullOrEmpty()) {
|
if (!it.dataOrNull.isNullOrEmpty()) {
|
||||||
firstLoadedItemList += DashboardItem.Type.EXAMS
|
firstLoadedItemList += DashboardItem.Type.EXAMS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
Timber.i("Loading dashboard exams result: Success")
|
Timber.i("Loading dashboard exams result: Success")
|
||||||
updateData(DashboardItem.Exams(it.data ?: emptyList()), forceRefresh)
|
updateData(DashboardItem.Exams(it.data), forceRefresh)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Loading dashboard exams result: An exception occurred")
|
Timber.i("Loading dashboard exams result: An exception occurred")
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
updateData(DashboardItem.Exams(error = it.error), forceRefresh)
|
updateData(DashboardItem.Exams(error = it.error), forceRefresh)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launchWithUniqueRefreshJob("dashboard_exams", forceRefresh)
|
}
|
||||||
|
.launchWithUniqueRefreshJob("dashboard_exams", forceRefresh)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadConferences(student: Student, forceRefresh: Boolean) {
|
private fun loadConferences(student: Student, forceRefresh: Boolean) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
|
|
||||||
conferenceRepository.getConferences(
|
conferenceRepository.getConferences(
|
||||||
@ -535,59 +529,62 @@ class DashboardPresenter @Inject constructor(
|
|||||||
forceRefresh = forceRefresh,
|
forceRefresh = forceRefresh,
|
||||||
startDate = Instant.now(),
|
startDate = Instant.now(),
|
||||||
)
|
)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.onEach {
|
||||||
Status.LOADING -> {
|
when (it) {
|
||||||
Timber.i("Loading dashboard conferences data started")
|
is Resource.Loading -> {
|
||||||
if (forceRefresh) return@onEach
|
Timber.i("Loading dashboard conferences data started")
|
||||||
updateData(
|
if (forceRefresh) return@onEach
|
||||||
DashboardItem.Conferences(it.data ?: emptyList(), isLoading = true),
|
updateData(
|
||||||
forceRefresh
|
DashboardItem.Conferences(it.dataOrNull.orEmpty(), isLoading = true),
|
||||||
)
|
forceRefresh
|
||||||
|
)
|
||||||
|
|
||||||
if (!it.data.isNullOrEmpty()) {
|
if (!it.dataOrNull.isNullOrEmpty()) {
|
||||||
firstLoadedItemList += DashboardItem.Type.CONFERENCES
|
firstLoadedItemList += DashboardItem.Type.CONFERENCES
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is Resource.Success -> {
|
||||||
|
Timber.i("Loading dashboard conferences result: Success")
|
||||||
|
updateData(DashboardItem.Conferences(it.data), forceRefresh)
|
||||||
|
}
|
||||||
|
is Resource.Error -> {
|
||||||
|
Timber.i("Loading dashboard conferences result: An exception occurred")
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
updateData(DashboardItem.Conferences(error = it.error), forceRefresh)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading dashboard conferences result: Success")
|
|
||||||
updateData(DashboardItem.Conferences(it.data ?: emptyList()), forceRefresh)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading dashboard conferences result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
updateData(DashboardItem.Conferences(error = it.error), forceRefresh)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}.launchWithUniqueRefreshJob("dashboard_conferences", forceRefresh)
|
.launchWithUniqueRefreshJob("dashboard_conferences", forceRefresh)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadAdminMessage(student: Student, forceRefresh: Boolean) {
|
private fun loadAdminMessage(student: Student, forceRefresh: Boolean) {
|
||||||
flowWithResourceIn { adminMessageRepository.getAdminMessages(student) }
|
flatResourceFlow { adminMessageRepository.getAdminMessages(student) }
|
||||||
.map {
|
.filter {
|
||||||
val isDismissed = it.data?.id in preferencesRepository.dismissedAdminMessageIds
|
val data = it.dataOrNull ?: return@filter true
|
||||||
it.copy(data = it.data.takeUnless { isDismissed })
|
val isDismissed = data.id in preferencesRepository.dismissedAdminMessageIds
|
||||||
|
!isDismissed
|
||||||
}
|
}
|
||||||
.onEach {
|
.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> {
|
is Resource.Loading -> {
|
||||||
Timber.i("Loading dashboard admin message data started")
|
Timber.i("Loading dashboard admin message data started")
|
||||||
if (forceRefresh) return@onEach
|
if (forceRefresh) return@onEach
|
||||||
updateData(DashboardItem.AdminMessages(), forceRefresh)
|
updateData(DashboardItem.AdminMessages(), forceRefresh)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
Timber.i("Loading dashboard admin message result: Success")
|
Timber.i("Loading dashboard admin message result: Success")
|
||||||
updateData(
|
updateData(
|
||||||
dashboardItem = DashboardItem.AdminMessages(adminMessage = it.data),
|
dashboardItem = DashboardItem.AdminMessages(adminMessage = it.data),
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Loading dashboard admin message result: An exception occurred")
|
Timber.i("Loading dashboard admin message result: An exception occurred")
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
updateData(
|
updateData(
|
||||||
dashboardItem = DashboardItem.AdminMessages(
|
dashboardItem = DashboardItem.AdminMessages(
|
||||||
adminMessage = it.data,
|
adminMessage = null,
|
||||||
error = it.error
|
error = it.error
|
||||||
),
|
),
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
@ -740,7 +737,7 @@ class DashboardPresenter @Inject constructor(
|
|||||||
|
|
||||||
if (forceRefresh) {
|
if (forceRefresh) {
|
||||||
onEach {
|
onEach {
|
||||||
if (it.status == Status.SUCCESS) {
|
if (it is Resource.Success) {
|
||||||
cancelJobs(jobName)
|
cancelJobs(jobName)
|
||||||
}
|
}
|
||||||
}.launch(jobName)
|
}.launch(jobName)
|
||||||
|
@ -1,11 +1,11 @@
|
|||||||
package io.github.wulkanowy.ui.modules.debug.logviewer
|
package io.github.wulkanowy.ui.modules.debug.logviewer
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
import io.github.wulkanowy.data.repositories.LoggerRepository
|
import io.github.wulkanowy.data.repositories.LoggerRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -23,19 +23,21 @@ class LogViewerPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun onShareLogsSelected(): Boolean {
|
fun onShareLogsSelected(): Boolean {
|
||||||
flowWithResource { loggerRepository.getLogFiles() }.onEach {
|
resourceFlow { loggerRepository.getLogFiles() }
|
||||||
when (it.status) {
|
.onEach {
|
||||||
Status.LOADING -> Timber.d("Loading logs files started")
|
when (it) {
|
||||||
Status.SUCCESS -> {
|
is Resource.Loading -> Timber.d("Loading logs files started")
|
||||||
Timber.i("Loading logs files result: ${it.data!!.joinToString { file -> file.name }}")
|
is Resource.Success -> {
|
||||||
view?.shareLogs(it.data)
|
Timber.i("Loading logs files result: ${it.data.joinToString { file -> file.name }}")
|
||||||
}
|
view?.shareLogs(it.data)
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading logs files result: An exception occurred")
|
is Resource.Error -> {
|
||||||
errorHandler.dispatch(it.error!!)
|
Timber.i("Loading logs files result: An exception occurred")
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("share")
|
.launch("share")
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -44,18 +46,20 @@ class LogViewerPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadLogFile() {
|
private fun loadLogFile() {
|
||||||
flowWithResource { loggerRepository.getLastLogLines() }.onEach {
|
resourceFlow { loggerRepository.getLastLogLines() }
|
||||||
when (it.status) {
|
.onEach {
|
||||||
Status.LOADING -> Timber.d("Loading last log file started")
|
when (it) {
|
||||||
Status.SUCCESS -> {
|
is Resource.Loading -> Timber.d("Loading last log file started")
|
||||||
Timber.i("Loading last log file result: load ${it.data!!.size} lines")
|
is Resource.Success -> {
|
||||||
view?.setLines(it.data)
|
Timber.i("Loading last log file result: load ${it.data.size} lines")
|
||||||
}
|
view?.setLines(it.data)
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading last log file result: An exception occurred")
|
is Resource.Error -> {
|
||||||
errorHandler.dispatch(it.error!!)
|
Timber.i("Loading last log file result: An exception occurred")
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("file")
|
.launch("file")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,21 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.exam
|
package io.github.wulkanowy.ui.modules.exam
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Exam
|
import io.github.wulkanowy.data.db.entities.Exam
|
||||||
import io.github.wulkanowy.data.repositories.ExamRepository
|
import io.github.wulkanowy.data.repositories.ExamRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.*
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.getLastSchoolDayIfHoliday
|
|
||||||
import io.github.wulkanowy.utils.isHolidays
|
|
||||||
import io.github.wulkanowy.utils.monday
|
|
||||||
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.sunday
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.flow
|
import kotlinx.coroutines.flow.flow
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
@ -86,61 +78,57 @@ class ExamPresenter @Inject constructor(
|
|||||||
flow {
|
flow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
emit(semesterRepository.getCurrentSemester(student))
|
emit(semesterRepository.getCurrentSemester(student))
|
||||||
}.catch {
|
}
|
||||||
Timber.i("Loading semester result: An exception occurred")
|
.catch { Timber.i("Loading semester result: An exception occurred") }
|
||||||
}.onEach {
|
.onEach {
|
||||||
baseDate = baseDate.getLastSchoolDayIfHoliday(it.schoolYear)
|
baseDate = baseDate.getLastSchoolDayIfHoliday(it.schoolYear)
|
||||||
currentDate = baseDate
|
currentDate = baseDate
|
||||||
reloadNavigation()
|
reloadNavigation()
|
||||||
}.launch("holidays")
|
}
|
||||||
|
.launch("holidays")
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading exam data started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
examRepository.getExams(student, semester, currentDate.monday, currentDate.sunday, forceRefresh)
|
examRepository.getExams(
|
||||||
}.onEach {
|
student = student,
|
||||||
when (it.status) {
|
semester = semester,
|
||||||
Status.LOADING -> {
|
start = currentDate.monday,
|
||||||
if (!it.data.isNullOrEmpty()) {
|
end = currentDate.sunday,
|
||||||
view?.run {
|
forceRefresh = forceRefresh
|
||||||
enableSwipe(true)
|
)
|
||||||
showRefresh(true)
|
}
|
||||||
showProgress(false)
|
.logResourceStatus("load exam data")
|
||||||
showContent(true)
|
.mapResourceData { createExamItems(it) }
|
||||||
updateData(createExamItems(it.data))
|
.onResourceData {
|
||||||
}
|
view?.run {
|
||||||
}
|
enableSwipe(true)
|
||||||
}
|
showProgress(false)
|
||||||
Status.SUCCESS -> {
|
showErrorView(false)
|
||||||
Timber.i("Loading exam result: Success")
|
showContent(it.isNotEmpty())
|
||||||
view?.apply {
|
showEmpty(it.isEmpty())
|
||||||
updateData(createExamItems(it.data!!))
|
updateData(it)
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "exam",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading exam result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "exam",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
@ -181,8 +169,10 @@ class ExamPresenter @Inject constructor(
|
|||||||
view?.apply {
|
view?.apply {
|
||||||
showPreButton(!currentDate.minusDays(7).isHolidays)
|
showPreButton(!currentDate.minusDays(7).isHolidays)
|
||||||
showNextButton(!currentDate.plusDays(7).isHolidays)
|
showNextButton(!currentDate.plusDays(7).isHolidays)
|
||||||
updateNavigationWeek("${currentDate.monday.toFormattedString("dd.MM")} - " +
|
updateNavigationWeek(
|
||||||
currentDate.sunday.toFormattedString("dd.MM"))
|
"${currentDate.monday.toFormattedString("dd.MM")} - " +
|
||||||
|
currentDate.sunday.toFormattedString("dd.MM")
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.grade
|
package io.github.wulkanowy.ui.modules.grade
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Resource
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.Grade
|
import io.github.wulkanowy.data.db.entities.Grade
|
||||||
import io.github.wulkanowy.data.db.entities.GradeSummary
|
import io.github.wulkanowy.data.db.entities.GradeSummary
|
||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
@ -13,12 +12,10 @@ import io.github.wulkanowy.sdk.Sdk
|
|||||||
import io.github.wulkanowy.ui.modules.grade.GradeAverageMode.*
|
import io.github.wulkanowy.ui.modules.grade.GradeAverageMode.*
|
||||||
import io.github.wulkanowy.utils.calcAverage
|
import io.github.wulkanowy.utils.calcAverage
|
||||||
import io.github.wulkanowy.utils.changeModifier
|
import io.github.wulkanowy.utils.changeModifier
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.FlowPreview
|
import kotlinx.coroutines.FlowPreview
|
||||||
import kotlinx.coroutines.flow.Flow
|
import kotlinx.coroutines.flow.Flow
|
||||||
import kotlinx.coroutines.flow.combine
|
import kotlinx.coroutines.flow.combine
|
||||||
import kotlinx.coroutines.flow.distinctUntilChanged
|
import kotlinx.coroutines.flow.distinctUntilChanged
|
||||||
import kotlinx.coroutines.flow.map
|
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@OptIn(FlowPreview::class)
|
@OptIn(FlowPreview::class)
|
||||||
@ -35,7 +32,7 @@ class GradeAverageProvider @Inject constructor(
|
|||||||
private val isOptionalArithmeticAverage get() = preferencesRepository.isOptionalArithmeticAverage
|
private val isOptionalArithmeticAverage get() = preferencesRepository.isOptionalArithmeticAverage
|
||||||
|
|
||||||
fun getGradesDetailsWithAverage(student: Student, semesterId: Int, forceRefresh: Boolean) =
|
fun getGradesDetailsWithAverage(student: Student, semesterId: Int, forceRefresh: Boolean) =
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val semesters = semesterRepository.getSemesters(student)
|
val semesters = semesterRepository.getSemesters(student)
|
||||||
|
|
||||||
when (preferencesRepository.gradeAverageMode) {
|
when (preferencesRepository.gradeAverageMode) {
|
||||||
@ -81,17 +78,17 @@ class GradeAverageProvider @Inject constructor(
|
|||||||
val firstSemesterGradeSubjects = getGradeSubjects(student, firstSemester, forceRefresh)
|
val firstSemesterGradeSubjects = getGradeSubjects(student, firstSemester, forceRefresh)
|
||||||
|
|
||||||
return selectedSemesterGradeSubjects.combine(firstSemesterGradeSubjects) { secondSemesterGradeSubject, firstSemesterGradeSubject ->
|
return selectedSemesterGradeSubjects.combine(firstSemesterGradeSubjects) { secondSemesterGradeSubject, firstSemesterGradeSubject ->
|
||||||
if (firstSemesterGradeSubject.status == Status.ERROR) {
|
if (firstSemesterGradeSubject.errorOrNull != null) {
|
||||||
return@combine firstSemesterGradeSubject
|
return@combine firstSemesterGradeSubject
|
||||||
}
|
}
|
||||||
|
|
||||||
val isAnyVulcanAverageInFirstSemester =
|
val isAnyVulcanAverageInFirstSemester =
|
||||||
firstSemesterGradeSubject.data.orEmpty().any { it.isVulcanAverage }
|
firstSemesterGradeSubject.dataOrNull.orEmpty().any { it.isVulcanAverage }
|
||||||
val isAnyVulcanAverageInSecondSemester =
|
val isAnyVulcanAverageInSecondSemester =
|
||||||
secondSemesterGradeSubject.data.orEmpty().any { it.isVulcanAverage }
|
secondSemesterGradeSubject.dataOrNull.orEmpty().any { it.isVulcanAverage }
|
||||||
|
|
||||||
val updatedData = secondSemesterGradeSubject.data?.map { secondSemesterSubject ->
|
val updatedData = secondSemesterGradeSubject.dataOrNull?.map { secondSemesterSubject ->
|
||||||
val firstSemesterSubject = firstSemesterGradeSubject.data.orEmpty()
|
val firstSemesterSubject = firstSemesterGradeSubject.dataOrNull.orEmpty()
|
||||||
.singleOrNull { it.subject == secondSemesterSubject.subject }
|
.singleOrNull { it.subject == secondSemesterSubject.subject }
|
||||||
|
|
||||||
val updatedAverage = if (averageMode == ALL_YEAR) {
|
val updatedAverage = if (averageMode == ALL_YEAR) {
|
||||||
@ -113,7 +110,7 @@ class GradeAverageProvider @Inject constructor(
|
|||||||
}
|
}
|
||||||
secondSemesterSubject.copy(average = updatedAverage)
|
secondSemesterSubject.copy(average = updatedAverage)
|
||||||
}
|
}
|
||||||
secondSemesterGradeSubject.copy(data = updatedData)
|
secondSemesterGradeSubject.mapData { updatedData!! }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -166,17 +163,17 @@ class GradeAverageProvider @Inject constructor(
|
|||||||
val isGradeAverageForceCalc = preferencesRepository.gradeAverageForceCalc
|
val isGradeAverageForceCalc = preferencesRepository.gradeAverageForceCalc
|
||||||
|
|
||||||
return gradeRepository.getGrades(student, semester, forceRefresh = forceRefresh)
|
return gradeRepository.getGrades(student, semester, forceRefresh = forceRefresh)
|
||||||
.map { res ->
|
.mapResourceData { res ->
|
||||||
val (details, summaries) = res.data ?: null to null
|
val (details, summaries) = res
|
||||||
val isAnyAverage = summaries.orEmpty().any { it.average != .0 }
|
val isAnyAverage = summaries.any { it.average != .0 }
|
||||||
val allGrades = details.orEmpty().groupBy { it.subject }
|
val allGrades = details.groupBy { it.subject }
|
||||||
|
|
||||||
val items = summaries?.emulateEmptySummaries(
|
val items = summaries.emulateEmptySummaries(
|
||||||
student = student,
|
student = student,
|
||||||
semester = semester,
|
semester = semester,
|
||||||
grades = allGrades.toList(),
|
grades = allGrades.toList(),
|
||||||
calcAverage = isAnyAverage
|
calcAverage = isAnyAverage
|
||||||
)?.map { summary ->
|
).map { summary ->
|
||||||
val grades = allGrades[summary.subject].orEmpty()
|
val grades = allGrades[summary.subject].orEmpty()
|
||||||
GradeSubject(
|
GradeSubject(
|
||||||
subject = summary.subject,
|
subject = summary.subject,
|
||||||
@ -190,7 +187,7 @@ class GradeAverageProvider @Inject constructor(
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
Resource(res.status, items, res.error)
|
items
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,16 +1,16 @@
|
|||||||
package io.github.wulkanowy.ui.modules.grade
|
package io.github.wulkanowy.ui.modules.grade
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.Semester
|
import io.github.wulkanowy.data.db.entities.Semester
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
|
import io.github.wulkanowy.data.onResourceData
|
||||||
|
import io.github.wulkanowy.data.onResourceError
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.getCurrentOrLast
|
import io.github.wulkanowy.utils.getCurrentOrLast
|
||||||
import kotlinx.coroutines.delay
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -99,32 +99,26 @@ class GradePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
semesterRepository.getSemesters(student, refreshOnNoCurrent = true)
|
semesterRepository.getSemesters(student, refreshOnNoCurrent = true)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load grade data")
|
||||||
Status.LOADING -> Timber.i("Loading grade data started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
val current = it.getCurrentOrLast()
|
||||||
val current = it.data!!.getCurrentOrLast()
|
selectedIndex = if (selectedIndex == 0) current.semesterName else selectedIndex
|
||||||
selectedIndex = if (selectedIndex == 0) current.semesterName else selectedIndex
|
schoolYear = current.schoolYear
|
||||||
schoolYear = current.schoolYear
|
semesters = it.filter { semester -> semester.diaryId == current.diaryId }
|
||||||
semesters = it.data.filter { semester -> semester.diaryId == current.diaryId }
|
view?.setCurrentSemesterName(current.semesterName, schoolYear)
|
||||||
view?.setCurrentSemesterName(current.semesterName, schoolYear)
|
view?.run {
|
||||||
|
Timber.i("Loading grade data: Attempt load index $currentPageIndex")
|
||||||
view?.run {
|
loadChild(currentPageIndex)
|
||||||
Timber.i("Loading grade result: Attempt load index $currentPageIndex")
|
showErrorView(false)
|
||||||
loadChild(currentPageIndex)
|
showSemesterSwitch(true)
|
||||||
showErrorView(false)
|
|
||||||
showSemesterSwitch(true)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading grade result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -12,6 +12,7 @@ import io.github.wulkanowy.data.enums.GradeColorTheme
|
|||||||
import io.github.wulkanowy.databinding.DialogGradeBinding
|
import io.github.wulkanowy.databinding.DialogGradeBinding
|
||||||
import io.github.wulkanowy.utils.*
|
import io.github.wulkanowy.utils.*
|
||||||
|
|
||||||
|
|
||||||
class GradeDetailsDialog : DialogFragment() {
|
class GradeDetailsDialog : DialogFragment() {
|
||||||
|
|
||||||
private var binding: DialogGradeBinding by lifecycleAwareVariable()
|
private var binding: DialogGradeBinding by lifecycleAwareVariable()
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.grade.details
|
package io.github.wulkanowy.ui.modules.grade.details
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Grade
|
import io.github.wulkanowy.data.db.entities.Grade
|
||||||
import io.github.wulkanowy.data.enums.GradeExpandMode
|
import io.github.wulkanowy.data.enums.GradeExpandMode
|
||||||
import io.github.wulkanowy.data.enums.GradeSortingMode.ALPHABETIC
|
import io.github.wulkanowy.data.enums.GradeSortingMode.ALPHABETIC
|
||||||
@ -14,12 +14,8 @@ import io.github.wulkanowy.ui.base.ErrorHandler
|
|||||||
import io.github.wulkanowy.ui.modules.grade.GradeAverageProvider
|
import io.github.wulkanowy.ui.modules.grade.GradeAverageProvider
|
||||||
import io.github.wulkanowy.ui.modules.grade.GradeSubject
|
import io.github.wulkanowy.ui.modules.grade.GradeSubject
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -71,7 +67,7 @@ class GradeDetailsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun onMarkAsReadSelected(): Boolean {
|
fun onMarkAsReadSelected(): Boolean {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semesters = semesterRepository.getSemesters(student)
|
val semesters = semesterRepository.getSemesters(student)
|
||||||
val semester = semesters.first { item -> item.semesterId == currentSemesterId }
|
val semester = semesters.first { item -> item.semesterId == currentSemesterId }
|
||||||
@ -79,19 +75,11 @@ class GradeDetailsPresenter @Inject constructor(
|
|||||||
|
|
||||||
Timber.i("Mark as read ${unreadGrades.size} grades")
|
Timber.i("Mark as read ${unreadGrades.size} grades")
|
||||||
gradeRepository.updateGrades(unreadGrades.map { it.apply { isRead = true } })
|
gradeRepository.updateGrades(unreadGrades.map { it.apply { isRead = true } })
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("mark grades as read")
|
||||||
Status.LOADING -> Timber.i("Select mark grades as read")
|
.onResourceSuccess { loadData(currentSemesterId, false) }
|
||||||
Status.SUCCESS -> {
|
.onResourceError(errorHandler::dispatch)
|
||||||
Timber.i("Mark as read result: Success")
|
.launch("mark")
|
||||||
loadData(currentSemesterId, false)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Mark as read result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.launch("mark")
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -138,71 +126,49 @@ class GradeDetailsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(semesterId: Int, forceRefresh: Boolean) {
|
private fun loadData(semesterId: Int, forceRefresh: Boolean) {
|
||||||
Timber.i("Loading grade details data started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
averageProvider.getGradesDetailsWithAverage(student, semesterId, forceRefresh)
|
averageProvider.getGradesDetailsWithAverage(student, semesterId, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
Timber.d("Loading grade details status: ${it.status}, data: ${it.data != null}")
|
.logResourceStatus("load grade details")
|
||||||
when (it.status) {
|
.onResourceData {
|
||||||
Status.LOADING -> {
|
view?.run {
|
||||||
val items = createGradeItems(it.data.orEmpty())
|
enableSwipe(true)
|
||||||
if (items.isNotEmpty()) {
|
showProgress(false)
|
||||||
Timber.i("Loading grade details result: load cached data")
|
showErrorView(false)
|
||||||
view?.run {
|
showContent(it.isNotEmpty())
|
||||||
updateNewGradesAmount(it.data.orEmpty())
|
showEmpty(it.isEmpty())
|
||||||
enableSwipe(true)
|
updateNewGradesAmount(it)
|
||||||
showRefresh(true)
|
|
||||||
showProgress(false)
|
|
||||||
showEmpty(false)
|
|
||||||
showContent(true)
|
|
||||||
updateData(
|
|
||||||
data = items,
|
|
||||||
expandMode = preferencesRepository.gradeExpandMode,
|
|
||||||
gradeColorTheme = preferencesRepository.gradeColorTheme
|
|
||||||
)
|
|
||||||
notifyParentDataLoaded(semesterId)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading grade details result: Success")
|
|
||||||
updateNewGradesAmount(it.data!!)
|
|
||||||
updateMarkAsDoneButton()
|
updateMarkAsDoneButton()
|
||||||
val items = createGradeItems(it.data)
|
updateData(
|
||||||
view?.run {
|
data = createGradeItems(it),
|
||||||
showEmpty(items.isEmpty())
|
expandMode = preferencesRepository.gradeExpandMode,
|
||||||
showErrorView(false)
|
preferencesRepository.gradeColorTheme
|
||||||
showContent(items.isNotEmpty())
|
|
||||||
updateData(
|
|
||||||
data = items,
|
|
||||||
expandMode = preferencesRepository.gradeExpandMode,
|
|
||||||
gradeColorTheme = preferencesRepository.gradeColorTheme
|
|
||||||
)
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "grade_details",
|
|
||||||
"items" to it.data.size
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading grade details result: An exception occurred")
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
errorHandler.dispatch(it.error!!)
|
.onResourceSuccess {
|
||||||
|
analytics.logEvent(
|
||||||
|
"load_data",
|
||||||
|
"type" to "grade_details",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
|
}
|
||||||
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showRefresh(false)
|
||||||
|
showProgress(false)
|
||||||
|
notifyParentDataLoaded(semesterId)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.catch {
|
||||||
view?.run {
|
errorHandler.dispatch(it)
|
||||||
showRefresh(false)
|
view?.notifyParentDataLoaded(semesterId)
|
||||||
showProgress(false)
|
|
||||||
enableSwipe(true)
|
|
||||||
notifyParentDataLoaded(semesterId)
|
|
||||||
}
|
}
|
||||||
}.catch {
|
.onResourceError(errorHandler::dispatch)
|
||||||
errorHandler.dispatch(it)
|
.launch()
|
||||||
view?.notifyParentDataLoaded(semesterId)
|
|
||||||
}.launch()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun updateNewGradesAmount(grades: List<GradeSubject>) {
|
private fun updateNewGradesAmount(grades: List<GradeSubject>) {
|
||||||
@ -267,15 +233,9 @@ class GradeDetailsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun updateGrade(grade: Grade) {
|
private fun updateGrade(grade: Grade) {
|
||||||
flowWithResource { gradeRepository.updateGrade(grade) }.onEach {
|
resourceFlow { gradeRepository.updateGrade(grade) }
|
||||||
when (it.status) {
|
.logResourceStatus("update grade result ${grade.id}")
|
||||||
Status.LOADING -> Timber.i("Attempt to update grade ${grade.id}")
|
.onResourceError(errorHandler::dispatch)
|
||||||
Status.SUCCESS -> Timber.i("Update grade result: Success")
|
.launch("update")
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Update grade result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.launch("update")
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,19 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.grade.statistics
|
package io.github.wulkanowy.ui.modules.grade.statistics
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Subject
|
import io.github.wulkanowy.data.db.entities.Subject
|
||||||
import io.github.wulkanowy.data.pojos.GradeStatisticsItem
|
import io.github.wulkanowy.data.pojos.GradeStatisticsItem
|
||||||
import io.github.wulkanowy.data.repositories.GradeStatisticsRepository
|
import io.github.wulkanowy.data.repositories.*
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
|
||||||
import io.github.wulkanowy.data.repositories.SubjectRepository
|
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -125,33 +118,26 @@ class GradeStatisticsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadSubjects() {
|
private fun loadSubjects() {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
subjectRepository.getSubjects(student, semester)
|
subjectRepository.getSubjects(student, semester)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load grade stats subjects")
|
||||||
Status.LOADING -> Timber.i("Loading grade stats subjects started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
subjects = it
|
||||||
subjects = requireNotNull(it.data)
|
view?.run {
|
||||||
Timber.i("Loading grade stats subjects result: Success")
|
showSubjects(!preferencesRepository.showAllSubjectsOnStatisticsList)
|
||||||
|
updateSubjects(
|
||||||
view?.run {
|
data = it.map { subject -> subject.name },
|
||||||
showSubjects(!preferencesRepository.showAllSubjectsOnStatisticsList)
|
selectedIndex = it.indexOfFirst { subject ->
|
||||||
updateSubjects(
|
subject.name == currentSubjectName
|
||||||
data = it.data.map { subject -> subject.name },
|
},
|
||||||
selectedIndex = it.data.indexOfFirst { subject ->
|
)
|
||||||
subject.name == currentSubjectName
|
|
||||||
},
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading grade stats subjects result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("subjects")
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch("subjects")
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadDataByType(
|
private fun loadDataByType(
|
||||||
@ -168,7 +154,7 @@ class GradeStatisticsPresenter @Inject constructor(
|
|||||||
else -> subjectName
|
else -> subjectName
|
||||||
}
|
}
|
||||||
|
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semesters = semesterRepository.getSemesters(student)
|
val semesters = semesterRepository.getSemesters(student)
|
||||||
val semester = semesters.first { item -> item.semesterId == semesterId }
|
val semester = semesters.first { item -> item.semesterId == semesterId }
|
||||||
@ -201,58 +187,43 @@ class GradeStatisticsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load grade stats data")
|
||||||
Status.LOADING -> {
|
.mapResourceData {
|
||||||
val isNoContent = it.data == null || checkIsNoContent(it.data, type)
|
val isNoContent = checkIsNoContent(it, type)
|
||||||
if (!isNoContent) {
|
if (isNoContent) emptyList() else it
|
||||||
view?.run {
|
}
|
||||||
showEmpty(isNoContent)
|
.onResourceData {
|
||||||
showErrorView(false)
|
view?.run {
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
showRefresh(true)
|
showProgress(false)
|
||||||
showProgress(false)
|
showErrorView(false)
|
||||||
updateData(
|
showEmpty(it.isEmpty())
|
||||||
newItems = if (isNoContent) emptyList() else it.data!!,
|
updateData(
|
||||||
newTheme = preferencesRepository.gradeColorTheme,
|
newItems = it,
|
||||||
showAllSubjectsOnStatisticsList = preferencesRepository.showAllSubjectsOnStatisticsList,
|
newTheme = preferencesRepository.gradeColorTheme,
|
||||||
)
|
showAllSubjectsOnStatisticsList = preferencesRepository.showAllSubjectsOnStatisticsList
|
||||||
showSubjects(!preferencesRepository.showAllSubjectsOnStatisticsList)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading grade stats result: Success")
|
|
||||||
view?.run {
|
|
||||||
val isNoContent = checkIsNoContent(it.data!!, type)
|
|
||||||
showEmpty(isNoContent)
|
|
||||||
showErrorView(false)
|
|
||||||
updateData(
|
|
||||||
newItems = if (isNoContent) emptyList() else it.data,
|
|
||||||
newTheme = preferencesRepository.gradeColorTheme,
|
|
||||||
showAllSubjectsOnStatisticsList = preferencesRepository.showAllSubjectsOnStatisticsList,
|
|
||||||
)
|
|
||||||
showSubjects(!preferencesRepository.showAllSubjectsOnStatisticsList)
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "grade_statistics",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading grade stats result: An exception occurred")
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
errorHandler.dispatch(it.error!!)
|
.onResourceSuccess {
|
||||||
|
analytics.logEvent(
|
||||||
|
"load_data",
|
||||||
|
"type" to "grade_statistics",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
|
}
|
||||||
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showRefresh(false)
|
||||||
|
showProgress(false)
|
||||||
|
notifyParentDataLoaded(semesterId)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceError(errorHandler::dispatch)
|
||||||
view?.run {
|
.launch("load")
|
||||||
showRefresh(false)
|
|
||||||
showProgress(false)
|
|
||||||
enableSwipe(true)
|
|
||||||
notifyParentDataLoaded(semesterId)
|
|
||||||
}
|
|
||||||
}.launch("load")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun checkIsNoContent(
|
private fun checkIsNoContent(
|
||||||
@ -267,7 +238,8 @@ class GradeStatisticsPresenter @Inject constructor(
|
|||||||
items.firstOrNull()?.partial?.classAmounts.orEmpty().sum() == 0
|
items.firstOrNull()?.partial?.classAmounts.orEmpty().sum() == 0
|
||||||
}
|
}
|
||||||
GradeStatisticsItem.DataType.POINTS -> {
|
GradeStatisticsItem.DataType.POINTS -> {
|
||||||
items.firstOrNull()?.points?.let { points -> points.student == .0 && points.others == .0 } ?: false
|
items.firstOrNull()?.points?.let { points -> points.student == .0 && points.others == .0 }
|
||||||
|
?: false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.grade.summary
|
package io.github.wulkanowy.ui.modules.grade.summary
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.GradeSummary
|
import io.github.wulkanowy.data.db.entities.GradeSummary
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
@ -8,9 +8,6 @@ import io.github.wulkanowy.ui.base.ErrorHandler
|
|||||||
import io.github.wulkanowy.ui.modules.grade.GradeAverageProvider
|
import io.github.wulkanowy.ui.modules.grade.GradeAverageProvider
|
||||||
import io.github.wulkanowy.ui.modules.grade.GradeSubject
|
import io.github.wulkanowy.ui.modules.grade.GradeSubject
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -37,56 +34,40 @@ class GradeSummaryPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(semesterId: Int, forceRefresh: Boolean) {
|
private fun loadData(semesterId: Int, forceRefresh: Boolean) {
|
||||||
Timber.i("Loading grade summary started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
averageProvider.getGradesDetailsWithAverage(student, semesterId, forceRefresh)
|
averageProvider.getGradesDetailsWithAverage(student, semesterId, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
Timber.d("Loading grade summary status: ${it.status}, data: ${it.data != null}")
|
.logResourceStatus("load grade summary", showData = true)
|
||||||
when (it.status) {
|
.mapResourceData { createGradeSummaryItems(it) }
|
||||||
Status.LOADING -> {
|
.onResourceData {
|
||||||
val items = createGradeSummaryItems(it.data.orEmpty())
|
view?.run {
|
||||||
if (items.isNotEmpty()) {
|
enableSwipe(true)
|
||||||
Timber.i("Loading grade summary result: load cached data")
|
showProgress(false)
|
||||||
view?.run {
|
showErrorView(false)
|
||||||
enableSwipe(true)
|
showContent(it.isNotEmpty())
|
||||||
showRefresh(true)
|
showEmpty(it.isEmpty())
|
||||||
showProgress(false)
|
updateData(it)
|
||||||
showEmpty(false)
|
|
||||||
showContent(true)
|
|
||||||
updateData(items)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading grade summary result: Success")
|
|
||||||
val items = createGradeSummaryItems(it.data!!)
|
|
||||||
view?.run {
|
|
||||||
showEmpty(items.isEmpty())
|
|
||||||
showContent(items.isNotEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
updateData(items)
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "grade_summary",
|
|
||||||
"items" to it.data.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading grade summary result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "grade_summary",
|
||||||
notifyParentDataLoaded(semesterId)
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showRefresh(false)
|
||||||
|
showProgress(false)
|
||||||
|
notifyParentDataLoaded(semesterId)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
@ -153,9 +134,9 @@ class GradeSummaryPresenter @Inject constructor(
|
|||||||
private fun checkEmpty(gradeSummary: GradeSubject): Boolean {
|
private fun checkEmpty(gradeSummary: GradeSubject): Boolean {
|
||||||
return gradeSummary.run {
|
return gradeSummary.run {
|
||||||
summary.finalGrade.isBlank()
|
summary.finalGrade.isBlank()
|
||||||
&& summary.predictedGrade.isBlank()
|
&& summary.predictedGrade.isBlank()
|
||||||
&& average == .0
|
&& average == .0
|
||||||
&& points.isBlank()
|
&& points.isBlank()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,21 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.homework
|
package io.github.wulkanowy.ui.modules.homework
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Homework
|
import io.github.wulkanowy.data.db.entities.Homework
|
||||||
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.*
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.getLastSchoolDayIfHoliday
|
|
||||||
import io.github.wulkanowy.utils.isHolidays
|
|
||||||
import io.github.wulkanowy.utils.monday
|
|
||||||
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.sunday
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.flow
|
import kotlinx.coroutines.flow.flow
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
@ -89,61 +81,59 @@ class HomeworkPresenter @Inject constructor(
|
|||||||
flow {
|
flow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
emit(semesterRepository.getCurrentSemester(student))
|
emit(semesterRepository.getCurrentSemester(student))
|
||||||
}.catch {
|
}
|
||||||
Timber.i("Loading semester result: An exception occurred")
|
.catch { Timber.i("Loading semester result: An exception occurred") }
|
||||||
}.onEach {
|
.onEach {
|
||||||
baseDate = baseDate.getLastSchoolDayIfHoliday(it.schoolYear)
|
baseDate = baseDate.getLastSchoolDayIfHoliday(it.schoolYear)
|
||||||
currentDate = baseDate
|
currentDate = baseDate
|
||||||
reloadNavigation()
|
reloadNavigation()
|
||||||
}.launch("holidays")
|
}
|
||||||
|
.launch("holidays")
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading homework data started")
|
Timber.i("Loading homework data started")
|
||||||
|
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
homeworkRepository.getHomework(student, semester, currentDate, currentDate, forceRefresh)
|
homeworkRepository.getHomework(
|
||||||
}.onEach {
|
student = student,
|
||||||
when (it.status) {
|
semester = semester,
|
||||||
Status.LOADING -> {
|
start = currentDate,
|
||||||
if (!it.data.isNullOrEmpty()) {
|
end = currentDate,
|
||||||
view?.run {
|
forceRefresh = forceRefresh
|
||||||
enableSwipe(true)
|
)
|
||||||
showRefresh(true)
|
}
|
||||||
showProgress(false)
|
.logResourceStatus("loading homework")
|
||||||
showContent(true)
|
.mapResourceData { createHomeworkItem(it) }
|
||||||
updateData(createHomeworkItem(it.data))
|
.onResourceData {
|
||||||
}
|
view?.run {
|
||||||
}
|
enableSwipe(true)
|
||||||
}
|
showProgress(false)
|
||||||
Status.SUCCESS -> {
|
showErrorView(false)
|
||||||
Timber.i("Loading homework result: Success")
|
showContent(it.isNotEmpty())
|
||||||
view?.apply {
|
showEmpty(it.isEmpty())
|
||||||
updateData(createHomeworkItem(it.data!!))
|
updateData(it)
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "homework",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading homework result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "homework",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
@ -159,9 +149,10 @@ class HomeworkPresenter @Inject constructor(
|
|||||||
|
|
||||||
private fun createHomeworkItem(items: List<Homework>): List<HomeworkItem<*>> {
|
private fun createHomeworkItem(items: List<Homework>): List<HomeworkItem<*>> {
|
||||||
return items.groupBy { it.date }.toSortedMap().map { (date, exams) ->
|
return items.groupBy { it.date }.toSortedMap().map { (date, exams) ->
|
||||||
listOf(HomeworkItem(date, HomeworkItem.ViewType.HEADER)) + exams.reversed().map { exam ->
|
listOf(HomeworkItem(date, HomeworkItem.ViewType.HEADER)) + exams.reversed()
|
||||||
HomeworkItem(exam, HomeworkItem.ViewType.ITEM)
|
.map { exam ->
|
||||||
}
|
HomeworkItem(exam, HomeworkItem.ViewType.ITEM)
|
||||||
|
}
|
||||||
}.flatten()
|
}.flatten()
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -184,8 +175,10 @@ class HomeworkPresenter @Inject constructor(
|
|||||||
view?.apply {
|
view?.apply {
|
||||||
showPreButton(!currentDate.minusDays(7).isHolidays)
|
showPreButton(!currentDate.minusDays(7).isHolidays)
|
||||||
showNextButton(!currentDate.plusDays(7).isHolidays)
|
showNextButton(!currentDate.plusDays(7).isHolidays)
|
||||||
updateNavigationWeek("${currentDate.monday.toFormattedString("dd.MM")} - " +
|
updateNavigationWeek(
|
||||||
currentDate.sunday.toFormattedString("dd.MM"))
|
"${currentDate.monday.toFormattedString("dd.MM")} - " +
|
||||||
|
currentDate.sunday.toFormattedString("dd.MM")
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,15 +1,16 @@
|
|||||||
package io.github.wulkanowy.ui.modules.homework.add
|
package io.github.wulkanowy.ui.modules.homework.add
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.Homework
|
import io.github.wulkanowy.data.db.entities.Homework
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
|
import io.github.wulkanowy.data.onResourceError
|
||||||
|
import io.github.wulkanowy.data.onResourceSuccess
|
||||||
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.toLocalDate
|
import io.github.wulkanowy.utils.toLocalDate
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import java.time.LocalDate
|
import java.time.LocalDate
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -55,7 +56,7 @@ class HomeworkAddPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun saveHomework(subject: String, teacher: String, date: LocalDate, content: String) {
|
private fun saveHomework(subject: String, teacher: String, date: LocalDate, content: String) {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
val entryDate = LocalDate.now()
|
val entryDate = LocalDate.now()
|
||||||
@ -72,21 +73,15 @@ class HomeworkAddPresenter @Inject constructor(
|
|||||||
attachments = emptyList(),
|
attachments = emptyList(),
|
||||||
).apply { isAddedByUser = true }
|
).apply { isAddedByUser = true }
|
||||||
)
|
)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("homework insert")
|
||||||
Status.LOADING -> Timber.i("Homework insert start")
|
.onResourceSuccess {
|
||||||
Status.SUCCESS -> {
|
view?.run {
|
||||||
Timber.i("Homework insert: Success")
|
showSuccessMessage()
|
||||||
view?.run {
|
closeDialog()
|
||||||
showSuccessMessage()
|
|
||||||
closeDialog()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Homework insert result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("add_homework")
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch("add_homework")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,15 +1,16 @@
|
|||||||
package io.github.wulkanowy.ui.modules.homework.details
|
package io.github.wulkanowy.ui.modules.homework.details
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.Homework
|
import io.github.wulkanowy.data.db.entities.Homework
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
|
import io.github.wulkanowy.data.onResourceError
|
||||||
|
import io.github.wulkanowy.data.onResourceSuccess
|
||||||
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
import io.github.wulkanowy.data.repositories.HomeworkRepository
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -34,38 +35,26 @@ class HomeworkDetailsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun deleteHomework(homework: Homework) {
|
fun deleteHomework(homework: Homework) {
|
||||||
flowWithResource { homeworkRepository.deleteHomework(homework) }.onEach {
|
resourceFlow { homeworkRepository.deleteHomework(homework) }
|
||||||
when (it.status) {
|
.logResourceStatus("homework delete")
|
||||||
Status.LOADING -> Timber.i("Homework delete start")
|
.onResourceSuccess {
|
||||||
Status.SUCCESS -> {
|
view?.run {
|
||||||
Timber.i("Homework delete: Success")
|
showMessage(homeworkDeleteSuccess)
|
||||||
view?.run {
|
closeDialog()
|
||||||
showMessage(homeworkDeleteSuccess)
|
|
||||||
closeDialog()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Homework delete result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("delete")
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch("delete")
|
||||||
}
|
}
|
||||||
|
|
||||||
fun toggleDone(homework: Homework) {
|
fun toggleDone(homework: Homework) {
|
||||||
flowWithResource { homeworkRepository.toggleDone(homework) }.onEach {
|
resourceFlow { homeworkRepository.toggleDone(homework) }
|
||||||
when (it.status) {
|
.logResourceStatus("homework details update")
|
||||||
Status.LOADING -> Timber.i("Homework details update start")
|
.onResourceSuccess {
|
||||||
Status.SUCCESS -> {
|
view?.updateMarkAsDoneLabel(homework.isDone)
|
||||||
Timber.i("Homework details update: Success")
|
analytics.logEvent("homework_mark_as_done")
|
||||||
view?.updateMarkAsDoneLabel(homework.isDone)
|
|
||||||
analytics.logEvent("homework_mark_as_done")
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Homework details update result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}.launch("toggle")
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch("toggle")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,15 +1,16 @@
|
|||||||
package io.github.wulkanowy.ui.modules.login.advanced
|
package io.github.wulkanowy.ui.modules.login.advanced
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
|
import io.github.wulkanowy.data.onResourceNotLoading
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.modules.login.LoginData
|
import io.github.wulkanowy.ui.modules.login.LoginData
|
||||||
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.ifNullOrBlank
|
import io.github.wulkanowy.utils.ifNullOrBlank
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
@ -129,20 +130,20 @@ class LoginAdvancedPresenter @Inject constructor(
|
|||||||
fun onSignInClick() {
|
fun onSignInClick() {
|
||||||
if (!validateCredentials()) return
|
if (!validateCredentials()) return
|
||||||
|
|
||||||
flowWithResource { getStudentsAppropriatesToLoginType() }.onEach {
|
resourceFlow { getStudentsAppropriatesToLoginType() }
|
||||||
when (it.status) {
|
.logResourceStatus("login")
|
||||||
Status.LOADING -> view?.run {
|
.onEach {
|
||||||
Timber.i("Login started")
|
when (it) {
|
||||||
hideSoftKeyboard()
|
is Resource.Loading -> view?.run {
|
||||||
showProgress(true)
|
hideSoftKeyboard()
|
||||||
showContent(false)
|
showProgress(true)
|
||||||
}
|
showContent(false)
|
||||||
Status.SUCCESS -> {
|
}
|
||||||
Timber.i("Login result: Success")
|
is Resource.Success -> {
|
||||||
analytics.logEvent(
|
analytics.logEvent(
|
||||||
"registration_form",
|
"registration_form",
|
||||||
"success" to true,
|
"success" to true,
|
||||||
"students" to it.data!!.size,
|
"students" to it.data.size,
|
||||||
"error" to "No error"
|
"error" to "No error"
|
||||||
)
|
)
|
||||||
val loginData = LoginData(
|
val loginData = LoginData(
|
||||||
@ -154,23 +155,22 @@ class LoginAdvancedPresenter @Inject constructor(
|
|||||||
0 -> view?.navigateToSymbol(loginData)
|
0 -> view?.navigateToSymbol(loginData)
|
||||||
else -> view?.navigateToStudentSelect(it.data)
|
else -> view?.navigateToStudentSelect(it.data)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
is Resource.Error -> {
|
||||||
|
analytics.logEvent(
|
||||||
|
"registration_form",
|
||||||
|
"success" to false, "students" to -1,
|
||||||
|
"error" to it.error.message.ifNullOrBlank { "No message" }
|
||||||
|
)
|
||||||
|
loginErrorHandler.dispatch(it.error)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}.onResourceNotLoading {
|
||||||
Timber.i("Login result: An exception occurred")
|
view?.apply {
|
||||||
analytics.logEvent(
|
showProgress(false)
|
||||||
"registration_form",
|
showContent(true)
|
||||||
"success" to false, "students" to -1,
|
|
||||||
"error" to it.error!!.message.ifNullOrBlank { "No message" }
|
|
||||||
)
|
|
||||||
loginErrorHandler.dispatch(it.error)
|
|
||||||
}
|
}
|
||||||
}
|
}.launch("login")
|
||||||
}.afterLoading {
|
|
||||||
view?.apply {
|
|
||||||
showProgress(false)
|
|
||||||
showContent(true)
|
|
||||||
}
|
|
||||||
}.launch("login")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private suspend fun getStudentsAppropriatesToLoginType(): List<StudentWithSemesters> {
|
private suspend fun getStudentsAppropriatesToLoginType(): List<StudentWithSemesters> {
|
||||||
|
@ -1,16 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.login.form
|
package io.github.wulkanowy.ui.modules.login.form
|
||||||
|
|
||||||
import androidx.core.net.toUri
|
import androidx.core.net.toUri
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.modules.login.LoginData
|
import io.github.wulkanowy.ui.modules.login.LoginData
|
||||||
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.ifNullOrBlank
|
import io.github.wulkanowy.utils.ifNullOrBlank
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import java.net.URL
|
import java.net.URL
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -75,7 +72,7 @@ class LoginFormPresenter @Inject constructor(
|
|||||||
|
|
||||||
val username = view?.formUsernameValue.orEmpty().trim()
|
val username = view?.formUsernameValue.orEmpty().trim()
|
||||||
if ("@" in username && "@vulcan" !in username) {
|
if ("@" in username && "@vulcan" !in username) {
|
||||||
val hosts = view?.getHostsValues().orEmpty().map { it.toUri().host to it }.toMap()
|
val hosts = view?.getHostsValues().orEmpty().associateBy { it.toUri().host }
|
||||||
val usernameHost = username.substringAfter("@")
|
val usernameHost = username.substringAfter("@")
|
||||||
|
|
||||||
hosts[usernameHost]?.let {
|
hosts[usernameHost]?.let {
|
||||||
@ -95,54 +92,54 @@ class LoginFormPresenter @Inject constructor(
|
|||||||
|
|
||||||
if (!validateCredentials(email, password, host)) return
|
if (!validateCredentials(email, password, host)) return
|
||||||
|
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
studentRepository.getStudentsScrapper(
|
studentRepository.getStudentsScrapper(
|
||||||
email = email,
|
email = email,
|
||||||
password = password,
|
password = password,
|
||||||
scrapperBaseUrl = host,
|
scrapperBaseUrl = host,
|
||||||
symbol = symbol
|
symbol = symbol
|
||||||
)
|
)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("login")
|
||||||
Status.LOADING -> view?.run {
|
.onResourceLoading {
|
||||||
Timber.i("Login started")
|
view?.run {
|
||||||
hideSoftKeyboard()
|
hideSoftKeyboard()
|
||||||
showProgress(true)
|
showProgress(true)
|
||||||
showContent(false)
|
showContent(false)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
}
|
||||||
Timber.i("Login result: Success")
|
.onResourceSuccess {
|
||||||
analytics.logEvent(
|
when (it.size) {
|
||||||
"registration_form",
|
0 -> view?.navigateToSymbol(LoginData(email, password, host))
|
||||||
"success" to true,
|
else -> view?.navigateToStudentSelect(it)
|
||||||
"students" to it.data!!.size,
|
|
||||||
"scrapperBaseUrl" to host,
|
|
||||||
"error" to "No error"
|
|
||||||
)
|
|
||||||
when (it.data.size) {
|
|
||||||
0 -> view?.navigateToSymbol(LoginData(email, password, host))
|
|
||||||
else -> view?.navigateToStudentSelect(it.data)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
analytics.logEvent(
|
||||||
Timber.i("Login result: An exception occurred")
|
"registration_form",
|
||||||
analytics.logEvent(
|
"success" to true,
|
||||||
"registration_form",
|
"students" to it.size,
|
||||||
"success" to false,
|
"scrapperBaseUrl" to host,
|
||||||
"students" to -1,
|
"error" to "No error"
|
||||||
"scrapperBaseUrl" to host,
|
)
|
||||||
"error" to it.error!!.message.ifNullOrBlank { "No message" })
|
}
|
||||||
loginErrorHandler.dispatch(it.error)
|
.onResourceNotLoading {
|
||||||
lastError = it.error
|
view?.apply {
|
||||||
view?.showContact(true)
|
showProgress(false)
|
||||||
|
showContent(true)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceError {
|
||||||
view?.apply {
|
loginErrorHandler.dispatch(it)
|
||||||
showProgress(false)
|
lastError = it
|
||||||
showContent(true)
|
view?.showContact(true)
|
||||||
|
analytics.logEvent(
|
||||||
|
"registration_form",
|
||||||
|
"success" to false,
|
||||||
|
"students" to -1,
|
||||||
|
"scrapperBaseUrl" to host,
|
||||||
|
"error" to it.message.ifNullOrBlank { "No message" }
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch("login")
|
.launch("login")
|
||||||
}
|
}
|
||||||
|
|
||||||
fun onFaqClick() {
|
fun onFaqClick() {
|
||||||
|
@ -1,12 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.login.recover
|
package io.github.wulkanowy.ui.modules.login.recover
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
|
import io.github.wulkanowy.data.onResourceNotLoading
|
||||||
import io.github.wulkanowy.data.repositories.RecoverRepository
|
import io.github.wulkanowy.data.repositories.RecoverRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.ifNullOrBlank
|
import io.github.wulkanowy.utils.ifNullOrBlank
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
@ -57,24 +57,28 @@ class LoginRecoverPresenter @Inject constructor(
|
|||||||
|
|
||||||
if (!validateInput(username, host)) return
|
if (!validateInput(username, host)) return
|
||||||
|
|
||||||
flowWithResource { recoverRepository.getReCaptchaSiteKey(host, symbol.ifBlank { "Default" }) }.onEach {
|
resourceFlow {
|
||||||
when (it.status) {
|
recoverRepository.getReCaptchaSiteKey(
|
||||||
Status.LOADING -> view?.run {
|
host,
|
||||||
|
symbol.ifBlank { "Default" })
|
||||||
|
}.onEach {
|
||||||
|
when (it) {
|
||||||
|
is Resource.Loading -> view?.run {
|
||||||
hideSoftKeyboard()
|
hideSoftKeyboard()
|
||||||
showRecoverForm(false)
|
showRecoverForm(false)
|
||||||
showProgress(true)
|
showProgress(true)
|
||||||
showErrorView(false)
|
showErrorView(false)
|
||||||
showCaptcha(false)
|
showCaptcha(false)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> view?.run {
|
is Resource.Success -> view?.run {
|
||||||
loadReCaptcha(url = it.data!!.first, siteKey = it.data.second)
|
loadReCaptcha(url = it.data.first, siteKey = it.data.second)
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
showErrorView(false)
|
showErrorView(false)
|
||||||
showCaptcha(true)
|
showCaptcha(true)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Obtain captcha site key result: An exception occurred")
|
Timber.i("Obtain captcha site key result: An exception occurred")
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("captcha")
|
}.launch("captcha")
|
||||||
@ -101,26 +105,43 @@ class LoginRecoverPresenter @Inject constructor(
|
|||||||
val host = view?.recoverHostValue.orEmpty()
|
val host = view?.recoverHostValue.orEmpty()
|
||||||
val symbol = view?.formHostSymbol.ifNullOrBlank { "Default" }
|
val symbol = view?.formHostSymbol.ifNullOrBlank { "Default" }
|
||||||
|
|
||||||
flowWithResource { recoverRepository.sendRecoverRequest(host, symbol, username, reCaptchaResponse) }.onEach {
|
resourceFlow {
|
||||||
when (it.status) {
|
recoverRepository.sendRecoverRequest(
|
||||||
Status.LOADING -> view?.run {
|
host,
|
||||||
|
symbol,
|
||||||
|
username,
|
||||||
|
reCaptchaResponse
|
||||||
|
)
|
||||||
|
}.onEach {
|
||||||
|
when (it) {
|
||||||
|
is Resource.Loading -> view?.run {
|
||||||
showProgress(true)
|
showProgress(true)
|
||||||
showRecoverForm(false)
|
showRecoverForm(false)
|
||||||
showCaptcha(false)
|
showCaptcha(false)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> view?.run {
|
is Resource.Success -> view?.run {
|
||||||
showSuccessView(true)
|
showSuccessView(true)
|
||||||
setSuccessTitle(it.data!!.substringBefore(". "))
|
setSuccessTitle(it.data.substringBefore(". "))
|
||||||
setSuccessMessage(it.data.substringAfter(". "))
|
setSuccessMessage(it.data.substringAfter(". "))
|
||||||
analytics.logEvent("account_recover", "register" to host, "symbol" to symbol, "success" to true)
|
analytics.logEvent(
|
||||||
|
"account_recover",
|
||||||
|
"register" to host,
|
||||||
|
"symbol" to symbol,
|
||||||
|
"success" to true
|
||||||
|
)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Send recover request result: An exception occurred")
|
Timber.i("Send recover request result: An exception occurred")
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
analytics.logEvent("account_recover", "register" to host, "symbol" to symbol, "success" to false)
|
analytics.logEvent(
|
||||||
|
"account_recover",
|
||||||
|
"register" to host,
|
||||||
|
"symbol" to symbol,
|
||||||
|
"success" to false
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
}.onResourceNotLoading {
|
||||||
view?.showProgress(false)
|
view?.showProgress(false)
|
||||||
}.launch("verified")
|
}.launch("verified")
|
||||||
}
|
}
|
||||||
|
@ -1,14 +1,15 @@
|
|||||||
package io.github.wulkanowy.ui.modules.login.studentselect
|
package io.github.wulkanowy.ui.modules.login.studentselect
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.services.sync.SyncManager
|
import io.github.wulkanowy.services.sync.SyncManager
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.ifNullOrBlank
|
import io.github.wulkanowy.utils.ifNullOrBlank
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
@ -66,16 +67,16 @@ class LoginStudentSelectPresenter @Inject constructor(
|
|||||||
private fun loadData(studentsWithSemesters: List<StudentWithSemesters>) {
|
private fun loadData(studentsWithSemesters: List<StudentWithSemesters>) {
|
||||||
resetSelectedState()
|
resetSelectedState()
|
||||||
|
|
||||||
flowWithResource { studentRepository.getSavedStudents(false) }.onEach {
|
resourceFlow { studentRepository.getSavedStudents(false) }.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> Timber.d("Login student select students load started")
|
is Resource.Loading -> Timber.d("Login student select students load started")
|
||||||
Status.SUCCESS -> view?.updateData(studentsWithSemesters.map { studentWithSemesters ->
|
is Resource.Success -> view?.updateData(studentsWithSemesters.map { studentWithSemesters ->
|
||||||
studentWithSemesters to it.data!!.any { item ->
|
studentWithSemesters to it.data.any { item ->
|
||||||
compareStudents(studentWithSemesters.student, item.student)
|
compareStudents(studentWithSemesters.student, item.student)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
lastError = it.error
|
lastError = it.error
|
||||||
view?.updateData(studentsWithSemesters.map { student -> student to false })
|
view?.updateData(studentsWithSemesters.map { student -> student to false })
|
||||||
}
|
}
|
||||||
@ -89,29 +90,27 @@ class LoginStudentSelectPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun registerStudents(studentsWithSemesters: List<StudentWithSemesters>) {
|
private fun registerStudents(studentsWithSemesters: List<StudentWithSemesters>) {
|
||||||
flowWithResource { studentRepository.saveStudents(studentsWithSemesters) }
|
resourceFlow { studentRepository.saveStudents(studentsWithSemesters) }
|
||||||
|
.logResourceStatus("registration")
|
||||||
.onEach {
|
.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> view?.run {
|
is Resource.Loading -> view?.run {
|
||||||
Timber.i("Registration started")
|
|
||||||
showProgress(true)
|
showProgress(true)
|
||||||
showContent(false)
|
showContent(false)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
Timber.i("Registration result: Success")
|
|
||||||
syncManager.startOneTimeSyncWorker(quiet = true)
|
syncManager.startOneTimeSyncWorker(quiet = true)
|
||||||
view?.openMainView()
|
view?.openMainView()
|
||||||
logRegisterEvent(studentsWithSemesters)
|
logRegisterEvent(studentsWithSemesters)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Registration result: An exception occurred ")
|
|
||||||
view?.apply {
|
view?.apply {
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
showContent(true)
|
showContent(true)
|
||||||
showContact(true)
|
showContact(true)
|
||||||
}
|
}
|
||||||
lastError = it.error
|
lastError = it.error
|
||||||
loginErrorHandler.dispatch(it.error!!)
|
loginErrorHandler.dispatch(it.error)
|
||||||
logRegisterEvent(studentsWithSemesters, it.error)
|
logRegisterEvent(studentsWithSemesters, it.error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,13 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.login.symbol
|
package io.github.wulkanowy.ui.modules.login.symbol
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
|
import io.github.wulkanowy.data.onResourceNotLoading
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.modules.login.LoginData
|
import io.github.wulkanowy.ui.modules.login.LoginData
|
||||||
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
import io.github.wulkanowy.ui.modules.login.LoginErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.ifNullOrBlank
|
import io.github.wulkanowy.utils.ifNullOrBlank
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
@ -45,7 +45,7 @@ class LoginSymbolPresenter @Inject constructor(
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
studentRepository.getStudentsScrapper(
|
studentRepository.getStudentsScrapper(
|
||||||
email = loginData.login,
|
email = loginData.login,
|
||||||
password = loginData.password,
|
password = loginData.password,
|
||||||
@ -53,15 +53,15 @@ class LoginSymbolPresenter @Inject constructor(
|
|||||||
symbol = symbol,
|
symbol = symbol,
|
||||||
)
|
)
|
||||||
}.onEach {
|
}.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> view?.run {
|
is Resource.Loading -> view?.run {
|
||||||
Timber.i("Login with symbol started")
|
Timber.i("Login with symbol started")
|
||||||
hideSoftKeyboard()
|
hideSoftKeyboard()
|
||||||
showProgress(true)
|
showProgress(true)
|
||||||
showContent(false)
|
showContent(false)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
when (it.data?.size) {
|
when (it.data.size) {
|
||||||
0 -> {
|
0 -> {
|
||||||
Timber.i("Login with symbol result: Empty student list")
|
Timber.i("Login with symbol result: Empty student list")
|
||||||
view?.run {
|
view?.run {
|
||||||
@ -77,13 +77,13 @@ class LoginSymbolPresenter @Inject constructor(
|
|||||||
analytics.logEvent(
|
analytics.logEvent(
|
||||||
"registration_symbol",
|
"registration_symbol",
|
||||||
"success" to true,
|
"success" to true,
|
||||||
"students" to it.data!!.size,
|
"students" to it.data.size,
|
||||||
"scrapperBaseUrl" to loginData.baseUrl,
|
"scrapperBaseUrl" to loginData.baseUrl,
|
||||||
"symbol" to symbol,
|
"symbol" to symbol,
|
||||||
"error" to "No error"
|
"error" to "No error"
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Login with symbol result: An exception occurred")
|
Timber.i("Login with symbol result: An exception occurred")
|
||||||
analytics.logEvent(
|
analytics.logEvent(
|
||||||
"registration_symbol",
|
"registration_symbol",
|
||||||
@ -91,14 +91,14 @@ class LoginSymbolPresenter @Inject constructor(
|
|||||||
"students" to -1,
|
"students" to -1,
|
||||||
"scrapperBaseUrl" to loginData.baseUrl,
|
"scrapperBaseUrl" to loginData.baseUrl,
|
||||||
"symbol" to symbol,
|
"symbol" to symbol,
|
||||||
"error" to it.error!!.message.ifNullOrBlank { "No message" }
|
"error" to it.error.message.ifNullOrBlank { "No message" }
|
||||||
)
|
)
|
||||||
loginErrorHandler.dispatch(it.error)
|
loginErrorHandler.dispatch(it.error)
|
||||||
lastError = it.error
|
lastError = it.error
|
||||||
view?.showContact(true)
|
view?.showContact(true)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
}.onResourceNotLoading {
|
||||||
view?.apply {
|
view?.apply {
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
showContent(true)
|
showContent(true)
|
||||||
|
@ -1,14 +1,11 @@
|
|||||||
package io.github.wulkanowy.ui.modules.luckynumber
|
package io.github.wulkanowy.ui.modules.luckynumber
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -34,47 +31,45 @@ class LuckyNumberPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
luckyNumberRepository.getLuckyNumber(student, forceRefresh)
|
luckyNumberRepository.getLuckyNumber(student, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load lucky number")
|
||||||
Status.LOADING -> Timber.i("Loading lucky number started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
if (it != null) {
|
||||||
if (it.data != null) {
|
view?.apply {
|
||||||
Timber.i("Loading lucky number result: Success")
|
updateData(it)
|
||||||
view?.apply {
|
showContent(true)
|
||||||
updateData(it.data)
|
showEmpty(false)
|
||||||
showContent(true)
|
showErrorView(false)
|
||||||
showEmpty(false)
|
}
|
||||||
showErrorView(false)
|
} else {
|
||||||
}
|
view?.run {
|
||||||
analytics.logEvent(
|
showContent(false)
|
||||||
"load_item",
|
showEmpty(true)
|
||||||
"type" to "lucky_number",
|
showErrorView(false)
|
||||||
"number" to it.data.luckyNumber
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
Timber.i("Loading lucky number result: No lucky number found")
|
|
||||||
view?.run {
|
|
||||||
showContent(false)
|
|
||||||
showEmpty(true)
|
|
||||||
showErrorView(false)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading lucky number result: An exception occurred")
|
.onResourceSuccess {
|
||||||
errorHandler.dispatch(it.error!!)
|
if (it != null) {
|
||||||
|
analytics.logEvent(
|
||||||
|
"load_item",
|
||||||
|
"type" to "lucky_number",
|
||||||
|
"number" to it.luckyNumber
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceNotLoading {
|
||||||
view?.run {
|
view?.run {
|
||||||
hideRefresh()
|
hideRefresh()
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,24 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.luckynumber.history
|
package io.github.wulkanowy.ui.modules.luckynumber.history
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.*
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
import kotlinx.coroutines.flow.*
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.getLastSchoolDayIfHoliday
|
|
||||||
import io.github.wulkanowy.utils.isHolidays
|
|
||||||
import io.github.wulkanowy.utils.monday
|
|
||||||
import io.github.wulkanowy.utils.previousOrSameSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.sunday
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
|
||||||
import kotlinx.coroutines.flow.catch
|
|
||||||
import kotlinx.coroutines.flow.first
|
|
||||||
import kotlinx.coroutines.flow.flow
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import java.time.LocalDate
|
import java.time.LocalDate
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -52,55 +40,51 @@ class LuckyNumberHistoryPresenter @Inject constructor(
|
|||||||
flow {
|
flow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
emit(semesterRepository.getCurrentSemester(student))
|
emit(semesterRepository.getCurrentSemester(student))
|
||||||
}.catch {
|
}
|
||||||
Timber.i("Loading semester result: An exception occurred")
|
.catch { Timber.i("Loading semester result: An exception occurred") }
|
||||||
}.onEach {
|
.onEach {
|
||||||
currentDate = currentDate.getLastSchoolDayIfHoliday(it.schoolYear)
|
currentDate = currentDate.getLastSchoolDayIfHoliday(it.schoolYear)
|
||||||
reloadNavigation()
|
reloadNavigation()
|
||||||
}.launch("holidays")
|
}
|
||||||
|
.launch("holidays")
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource {
|
flow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
luckyNumberRepository.getLuckyNumberHistory(student, currentDate.monday, currentDate.sunday)
|
emitAll(
|
||||||
}.onEach {
|
luckyNumberRepository.getLuckyNumberHistory(
|
||||||
when (it.status) {
|
student = student,
|
||||||
Status.LOADING -> Timber.i("Loading lucky number history started")
|
start = currentDate.monday,
|
||||||
Status.SUCCESS -> {
|
end = currentDate.sunday
|
||||||
if (!it.data?.first().isNullOrEmpty()) {
|
)
|
||||||
Timber.i("Loading lucky number result: Success")
|
)
|
||||||
view?.apply {
|
}
|
||||||
updateData(it.data!!.first())
|
.onEach {
|
||||||
showContent(true)
|
if (!it.isNullOrEmpty()) {
|
||||||
showEmpty(false)
|
view?.apply {
|
||||||
showErrorView(false)
|
updateData(it)
|
||||||
showProgress(false)
|
showContent(true)
|
||||||
}
|
showEmpty(false)
|
||||||
analytics.logEvent(
|
showErrorView(false)
|
||||||
"load_items",
|
showProgress(false)
|
||||||
"type" to "lucky_number_history",
|
}
|
||||||
"numbers" to it.data
|
} else {
|
||||||
)
|
view?.run {
|
||||||
} else {
|
showContent(false)
|
||||||
Timber.i("Loading lucky number history result: No lucky numbers found")
|
showEmpty(true)
|
||||||
view?.run {
|
showErrorView(false)
|
||||||
showContent(false)
|
showProgress(false)
|
||||||
showEmpty(true)
|
|
||||||
showErrorView(false)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading lucky number history result: An exception occurred")
|
analytics.logEvent(
|
||||||
errorHandler.dispatch(it.error!!)
|
"load_items",
|
||||||
}
|
"type" to "lucky_number_history",
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.catch { errorHandler.dispatch(it) }
|
||||||
view?.run {
|
.launchIn(presenterScope)
|
||||||
showProgress(false)
|
|
||||||
}
|
|
||||||
}.launch()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
@ -143,8 +127,10 @@ class LuckyNumberHistoryPresenter @Inject constructor(
|
|||||||
view?.apply {
|
view?.apply {
|
||||||
showPreButton(!currentDate.minusDays(7).isHolidays)
|
showPreButton(!currentDate.minusDays(7).isHolidays)
|
||||||
showNextButton(!currentDate.plusDays(7).isHolidays)
|
showNextButton(!currentDate.plusDays(7).isHolidays)
|
||||||
updateNavigationWeek("${currentDate.monday.toFormattedString("dd.MM")} - " +
|
updateNavigationWeek(
|
||||||
currentDate.sunday.toFormattedString("dd.MM"))
|
"${currentDate.monday.toFormattedString("dd.MM")} - " +
|
||||||
|
currentDate.sunday.toFormattedString("dd.MM")
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,14 +1,14 @@
|
|||||||
package io.github.wulkanowy.ui.modules.luckynumberwidget
|
package io.github.wulkanowy.ui.modules.luckynumberwidget
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
import io.github.wulkanowy.data.db.SharedPrefProvider
|
import io.github.wulkanowy.data.db.SharedPrefProvider
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.ui.modules.luckynumberwidget.LuckyNumberWidgetProvider.Companion.getStudentWidgetKey
|
import io.github.wulkanowy.ui.modules.luckynumberwidget.LuckyNumberWidgetProvider.Companion.getStudentWidgetKey
|
||||||
import io.github.wulkanowy.ui.modules.luckynumberwidget.LuckyNumberWidgetProvider.Companion.getThemeWidgetKey
|
import io.github.wulkanowy.ui.modules.luckynumberwidget.LuckyNumberWidgetProvider.Companion.getThemeWidgetKey
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -47,16 +47,15 @@ class LuckyNumberWidgetConfigurePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource { studentRepository.getSavedStudents(false) }.onEach {
|
resourceFlow { studentRepository.getSavedStudents(false) }.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> Timber.d("Lucky number widget configure students data load")
|
is Resource.Loading -> Timber.d("Lucky number widget configure students data load")
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
val selectedStudentId = appWidgetId?.let { id ->
|
val selectedStudentId = appWidgetId?.let { id ->
|
||||||
sharedPref.getLong(getStudentWidgetKey(id), 0)
|
sharedPref.getLong(getStudentWidgetKey(id), 0)
|
||||||
} ?: -1
|
} ?: -1
|
||||||
|
|
||||||
when {
|
when {
|
||||||
it.data!!.isEmpty() -> view?.openLoginView()
|
it.data.isEmpty() -> view?.openLoginView()
|
||||||
it.data.size == 1 -> {
|
it.data.size == 1 -> {
|
||||||
selectedStudent = it.data.single().student
|
selectedStudent = it.data.single().student
|
||||||
view?.showThemeDialog()
|
view?.showThemeDialog()
|
||||||
@ -64,7 +63,7 @@ class LuckyNumberWidgetConfigurePresenter @Inject constructor(
|
|||||||
else -> view?.updateData(it.data, selectedStudentId)
|
else -> view?.updateData(it.data, selectedStudentId)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> errorHandler.dispatch(it.error!!)
|
is Resource.Error -> errorHandler.dispatch(it.error)
|
||||||
}
|
}
|
||||||
}.launch()
|
}.launch()
|
||||||
}
|
}
|
||||||
|
@ -13,14 +13,17 @@ import android.view.View.VISIBLE
|
|||||||
import android.widget.RemoteViews
|
import android.widget.RemoteViews
|
||||||
import dagger.hilt.android.AndroidEntryPoint
|
import dagger.hilt.android.AndroidEntryPoint
|
||||||
import io.github.wulkanowy.R
|
import io.github.wulkanowy.R
|
||||||
|
import io.github.wulkanowy.data.Resource
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.SharedPrefProvider
|
import io.github.wulkanowy.data.db.SharedPrefProvider
|
||||||
|
import io.github.wulkanowy.data.db.entities.LuckyNumber
|
||||||
import io.github.wulkanowy.data.exceptions.NoCurrentStudentException
|
import io.github.wulkanowy.data.exceptions.NoCurrentStudentException
|
||||||
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
import io.github.wulkanowy.data.repositories.LuckyNumberRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.ui.modules.Destination
|
import io.github.wulkanowy.ui.modules.Destination
|
||||||
import io.github.wulkanowy.ui.modules.splash.SplashActivity
|
import io.github.wulkanowy.ui.modules.splash.SplashActivity
|
||||||
import io.github.wulkanowy.utils.PendingIntentCompat
|
import io.github.wulkanowy.utils.PendingIntentCompat
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -66,12 +69,16 @@ class LuckyNumberWidgetProvider : AppWidgetProvider() {
|
|||||||
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntentCompat.FLAG_IMMUTABLE
|
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntentCompat.FLAG_IMMUTABLE
|
||||||
)
|
)
|
||||||
|
|
||||||
|
if (luckyNumber is Resource.Error) {
|
||||||
|
Timber.e("Error loading lucky number for widget", luckyNumber.error)
|
||||||
|
}
|
||||||
|
|
||||||
val remoteView =
|
val remoteView =
|
||||||
RemoteViews(context.packageName, getCorrectLayoutId(appWidgetId, context))
|
RemoteViews(context.packageName, getCorrectLayoutId(appWidgetId, context))
|
||||||
.apply {
|
.apply {
|
||||||
setTextViewText(
|
setTextViewText(
|
||||||
R.id.luckyNumberWidgetNumber,
|
R.id.luckyNumberWidgetNumber,
|
||||||
luckyNumber?.luckyNumber?.toString() ?: "#"
|
luckyNumber.dataOrNull?.toString() ?: "#"
|
||||||
)
|
)
|
||||||
setOnClickPendingIntent(R.id.luckyNumberWidgetContainer, appIntent)
|
setOnClickPendingIntent(R.id.luckyNumberWidgetContainer, appIntent)
|
||||||
}
|
}
|
||||||
@ -167,14 +174,17 @@ class LuckyNumberWidgetProvider : AppWidgetProvider() {
|
|||||||
else -> null
|
else -> null
|
||||||
}
|
}
|
||||||
|
|
||||||
currentStudent?.let {
|
if (currentStudent != null) {
|
||||||
luckyNumberRepository.getLuckyNumber(it, false).toFirstResult().data
|
luckyNumberRepository.getLuckyNumber(currentStudent, forceRefresh = false)
|
||||||
|
.toFirstResult()
|
||||||
|
} else {
|
||||||
|
Resource.Success<LuckyNumber?>(null)
|
||||||
}
|
}
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
if (e.cause !is NoCurrentStudentException) {
|
if (e.cause !is NoCurrentStudentException) {
|
||||||
Timber.e(e, "An error has occurred in lucky number provider")
|
Timber.e(e, "An error has occurred in lucky number provider")
|
||||||
}
|
}
|
||||||
null
|
Resource.Error(e)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,9 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.main
|
package io.github.wulkanowy.ui.modules.main
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
|
import io.github.wulkanowy.data.onResourceError
|
||||||
|
import io.github.wulkanowy.data.onResourceSuccess
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.services.sync.SyncManager
|
import io.github.wulkanowy.services.sync.SyncManager
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.BaseView
|
import io.github.wulkanowy.ui.base.BaseView
|
||||||
@ -16,8 +19,6 @@ import io.github.wulkanowy.ui.modules.message.MessageView
|
|||||||
import io.github.wulkanowy.ui.modules.schoolandteachers.SchoolAndTeachersView
|
import io.github.wulkanowy.ui.modules.schoolandteachers.SchoolAndTeachersView
|
||||||
import io.github.wulkanowy.ui.modules.studentinfo.StudentInfoView
|
import io.github.wulkanowy.ui.modules.studentinfo.StudentInfoView
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import java.time.Duration
|
import java.time.Duration
|
||||||
import java.time.Instant
|
import java.time.Instant
|
||||||
@ -75,20 +76,14 @@ class MainPresenter @Inject constructor(
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
flowWithResource { studentRepository.getSavedStudents(false) }
|
resourceFlow { studentRepository.getSavedStudents(false) }
|
||||||
.onEach { resource ->
|
.logResourceStatus("load student avatar")
|
||||||
when (resource.status) {
|
.onResourceSuccess {
|
||||||
Status.LOADING -> Timber.i("Loading student avatar data started")
|
studentsWitSemesters = it
|
||||||
Status.SUCCESS -> {
|
showCurrentStudentAvatar()
|
||||||
studentsWitSemesters = resource.data
|
}
|
||||||
showCurrentStudentAvatar()
|
.onResourceError(errorHandler::dispatch)
|
||||||
}
|
.launch("avatar")
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading student avatar result: An exception occurred")
|
|
||||||
errorHandler.dispatch(resource.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.launch("avatar")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fun onViewChange(destinationView: BaseView) {
|
fun onViewChange(destinationView: BaseView) {
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
package io.github.wulkanowy.ui.modules.message.preview
|
package io.github.wulkanowy.ui.modules.message.preview
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Message
|
import io.github.wulkanowy.data.db.entities.Message
|
||||||
import io.github.wulkanowy.data.db.entities.MessageAttachment
|
import io.github.wulkanowy.data.db.entities.MessageAttachment
|
||||||
import io.github.wulkanowy.data.enums.MessageFolder
|
import io.github.wulkanowy.data.enums.MessageFolder
|
||||||
@ -10,11 +10,8 @@ import io.github.wulkanowy.data.repositories.StudentRepository
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
import io.github.wulkanowy.utils.toFormattedString
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.launch
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -53,44 +50,43 @@ class MessagePreviewPresenter @Inject constructor(
|
|||||||
view?.showErrorDetailsDialog(lastError)
|
view?.showErrorDetailsDialog(lastError)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(message: Message) {
|
private fun loadData(messageToLoad: Message) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getStudentById(message.studentId)
|
val student = studentRepository.getStudentById(messageToLoad.studentId)
|
||||||
messageRepository.getMessage(student, message, true)
|
messageRepository.getMessage(student, messageToLoad, true)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("message ${messageToLoad.messageId} preview")
|
||||||
Status.LOADING -> Timber.i("Loading message ${message.messageId} preview started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
if (it != null) {
|
||||||
Timber.i("Loading message ${message.messageId} preview result: Success ")
|
message = it.message
|
||||||
if (it.data != null) {
|
attachments = it.attachments
|
||||||
this@MessagePreviewPresenter.message = it.data.message
|
view?.apply {
|
||||||
this@MessagePreviewPresenter.attachments = it.data.attachments
|
setMessageWithAttachment(it)
|
||||||
view?.apply {
|
showContent(true)
|
||||||
setMessageWithAttachment(it.data)
|
initOptions()
|
||||||
showContent(true)
|
}
|
||||||
initOptions()
|
} else {
|
||||||
}
|
view?.run {
|
||||||
analytics.logEvent(
|
showMessage(messageNotExists)
|
||||||
"load_item",
|
popView()
|
||||||
"type" to "message_preview",
|
|
||||||
"length" to it.data.message.content.length
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
view?.run {
|
|
||||||
showMessage(messageNotExists)
|
|
||||||
popView()
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading message ${message.messageId} preview result: An exception occurred ")
|
.onResourceSuccess {
|
||||||
retryCallback = { onMessageLoadRetry(message) }
|
if (it != null) {
|
||||||
errorHandler.dispatch(it.error!!)
|
analytics.logEvent(
|
||||||
|
"load_item",
|
||||||
|
"type" to "message_preview",
|
||||||
|
"length" to it.message.content.length
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceNotLoading { view?.showProgress(false) }
|
||||||
view?.showProgress(false)
|
.onResourceError {
|
||||||
}.launch()
|
retryCallback = { onMessageLoadRetry(messageToLoad) }
|
||||||
|
errorHandler.dispatch(it)
|
||||||
|
}
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun onReply(): Boolean {
|
fun onReply(): Boolean {
|
||||||
@ -176,28 +172,26 @@ class MessagePreviewPresenter @Inject constructor(
|
|||||||
showErrorView(false)
|
showErrorView(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
flowWithResource {
|
Timber.i("Delete message ${message?.id}")
|
||||||
val student = studentRepository.getCurrentStudent()
|
|
||||||
messageRepository.deleteMessage(student, message!!)
|
presenterScope.launch {
|
||||||
}.onEach {
|
runCatching {
|
||||||
when (it.status) {
|
val student = studentRepository.getCurrentStudent()
|
||||||
Status.LOADING -> Timber.d("Message ${message?.id} delete started")
|
messageRepository.deleteMessage(student, message!!)
|
||||||
Status.SUCCESS -> {
|
}
|
||||||
Timber.d("Message ${message?.id} delete success")
|
.onFailure {
|
||||||
|
retryCallback = { onMessageDelete() }
|
||||||
|
errorHandler.dispatch(it)
|
||||||
|
}
|
||||||
|
.onSuccess {
|
||||||
view?.run {
|
view?.run {
|
||||||
showMessage(deleteMessageSuccessString)
|
showMessage(deleteMessageSuccessString)
|
||||||
popView()
|
popView()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.d("Message ${message?.id} delete failed")
|
|
||||||
retryCallback = { onMessageDelete() }
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.afterLoading {
|
|
||||||
view?.showProgress(false)
|
view?.showProgress(false)
|
||||||
}.launch("delete")
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,25 +1,20 @@
|
|||||||
package io.github.wulkanowy.ui.modules.message.send
|
package io.github.wulkanowy.ui.modules.message.send
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
import io.github.wulkanowy.data.db.entities.Message
|
import io.github.wulkanowy.data.db.entities.Message
|
||||||
import io.github.wulkanowy.data.db.entities.Recipient
|
import io.github.wulkanowy.data.db.entities.Recipient
|
||||||
|
import io.github.wulkanowy.data.logResourceStatus
|
||||||
|
import io.github.wulkanowy.data.onResourceNotLoading
|
||||||
import io.github.wulkanowy.data.pojos.MessageDraft
|
import io.github.wulkanowy.data.pojos.MessageDraft
|
||||||
import io.github.wulkanowy.data.repositories.MessageRepository
|
import io.github.wulkanowy.data.repositories.*
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.data.repositories.RecipientRepository
|
|
||||||
import io.github.wulkanowy.data.repositories.ReportingUnitRepository
|
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
import io.github.wulkanowy.utils.toFormattedString
|
||||||
import kotlinx.coroutines.FlowPreview
|
import kotlinx.coroutines.FlowPreview
|
||||||
import kotlinx.coroutines.channels.Channel
|
import kotlinx.coroutines.channels.Channel
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.collect
|
|
||||||
import kotlinx.coroutines.flow.consumeAsFlow
|
import kotlinx.coroutines.flow.consumeAsFlow
|
||||||
import kotlinx.coroutines.flow.debounce
|
import kotlinx.coroutines.flow.debounce
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
@ -55,10 +50,12 @@ class SendMessagePresenter @Inject constructor(
|
|||||||
setContent(it)
|
setContent(it)
|
||||||
}
|
}
|
||||||
message?.let {
|
message?.let {
|
||||||
setSubject(when (reply) {
|
setSubject(
|
||||||
true -> "Re: "
|
when (reply) {
|
||||||
else -> "FW: "
|
true -> "Re: "
|
||||||
} + message.subject)
|
else -> "FW: "
|
||||||
|
} + message.subject
|
||||||
|
)
|
||||||
if (preferencesRepository.fillMessageContent || reply != true) {
|
if (preferencesRepository.fillMessageContent || reply != true) {
|
||||||
setContent(
|
setContent(
|
||||||
when (reply) {
|
when (reply) {
|
||||||
@ -67,7 +64,8 @@ class SendMessagePresenter @Inject constructor(
|
|||||||
} + when (message.sender.isNotEmpty()) {
|
} + when (message.sender.isNotEmpty()) {
|
||||||
true -> "Od: ${message.sender}\n"
|
true -> "Od: ${message.sender}\n"
|
||||||
false -> "Do: ${message.recipient}\n"
|
false -> "Do: ${message.recipient}\n"
|
||||||
} + "Data: ${message.date.toFormattedString("yyyy-MM-dd HH:mm:ss")}\n\n${message.content}")
|
} + "Data: ${message.date.toFormattedString("yyyy-MM-dd HH:mm:ss")}\n\n${message.content}"
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -111,7 +109,7 @@ class SendMessagePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(message: Message?, reply: Boolean?) {
|
private fun loadData(message: Message?, reply: Boolean?) {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
val unit = reportingUnitRepository.getReportingUnit(student, semester.unitId)
|
val unit = reportingUnitRepository.getReportingUnit(student, semester.unitId)
|
||||||
@ -125,58 +123,64 @@ class SendMessagePresenter @Inject constructor(
|
|||||||
|
|
||||||
Timber.i("Loading message recipients started")
|
Timber.i("Loading message recipients started")
|
||||||
val messageRecipients = when {
|
val messageRecipients = when {
|
||||||
message != null && reply == true -> recipientRepository.getMessageRecipients(student, message)
|
message != null && reply == true -> recipientRepository.getMessageRecipients(
|
||||||
|
student,
|
||||||
|
message
|
||||||
|
)
|
||||||
else -> emptyList()
|
else -> emptyList()
|
||||||
}.let { createChips(it) }
|
}.let { createChips(it) }
|
||||||
Timber.i("Loaded message recipients to reply result: Success, fetched %d recipients", messageRecipients.size)
|
Timber.i(
|
||||||
|
"Loaded message recipients to reply result: Success, fetched %d recipients",
|
||||||
|
messageRecipients.size
|
||||||
|
)
|
||||||
|
|
||||||
Triple(unit, recipients, messageRecipients)
|
Triple(unit, recipients, messageRecipients)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load recipients")
|
||||||
Status.LOADING -> view?.run {
|
.onEach {
|
||||||
Timber.i("Loading recipients started")
|
when (it) {
|
||||||
showProgress(true)
|
is Resource.Loading -> view?.run {
|
||||||
showContent(false)
|
showProgress(true)
|
||||||
}
|
showContent(false)
|
||||||
Status.SUCCESS -> it.data!!.let { (reportingUnit, recipientChips, selectedRecipientChips) ->
|
}
|
||||||
view?.run {
|
is Resource.Success -> it.data.let { (reportingUnit, recipientChips, selectedRecipientChips) ->
|
||||||
if (reportingUnit != null) {
|
view?.run {
|
||||||
setReportingUnit(reportingUnit)
|
if (reportingUnit != null) {
|
||||||
setRecipients(recipientChips)
|
setReportingUnit(reportingUnit)
|
||||||
if (selectedRecipientChips.isNotEmpty()) setSelectedRecipients(selectedRecipientChips)
|
setRecipients(recipientChips)
|
||||||
showContent(true)
|
if (selectedRecipientChips.isNotEmpty()) setSelectedRecipients(
|
||||||
} else {
|
selectedRecipientChips
|
||||||
Timber.i("Loading recipients result: Can't find the reporting unit")
|
)
|
||||||
view?.showEmpty(true)
|
showContent(true)
|
||||||
|
} else {
|
||||||
|
Timber.i("Loading recipients result: Can't find the reporting unit")
|
||||||
|
view?.showEmpty(true)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
is Resource.Error -> {
|
||||||
|
view?.showContent(true)
|
||||||
|
errorHandler.dispatch(it.error)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}.onResourceNotLoading {
|
||||||
Timber.i("Loading recipients result: An exception occurred")
|
view?.run { showProgress(false) }
|
||||||
view?.showContent(true)
|
}.launch()
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}.afterLoading {
|
|
||||||
view?.run { showProgress(false) }
|
|
||||||
}.launch()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun sendMessage(subject: String, content: String, recipients: List<Recipient>) {
|
private fun sendMessage(subject: String, content: String, recipients: List<Recipient>) {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
messageRepository.sendMessage(student, subject, content, recipients)
|
messageRepository.sendMessage(student, subject, content, recipients)
|
||||||
}.onEach {
|
}.logResourceStatus("sending message").onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> view?.run {
|
is Resource.Loading -> view?.run {
|
||||||
Timber.i("Sending message started")
|
|
||||||
showSoftInput(false)
|
showSoftInput(false)
|
||||||
showContent(false)
|
showContent(false)
|
||||||
showProgress(true)
|
showProgress(true)
|
||||||
showActionBar(false)
|
showActionBar(false)
|
||||||
}
|
}
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
Timber.i("Sending message result: Success")
|
|
||||||
view?.clearDraft()
|
view?.clearDraft()
|
||||||
view?.run {
|
view?.run {
|
||||||
showMessage(messageSuccess)
|
showMessage(messageSuccess)
|
||||||
@ -184,14 +188,13 @@ class SendMessagePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
analytics.logEvent("send_message", "recipients" to recipients.size)
|
analytics.logEvent("send_message", "recipients" to recipients.size)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Sending message result: An exception occurred")
|
|
||||||
view?.run {
|
view?.run {
|
||||||
showContent(true)
|
showContent(true)
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
showActionBar(true)
|
showActionBar(true)
|
||||||
}
|
}
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("send")
|
}.launch("send")
|
||||||
@ -259,7 +262,8 @@ class SendMessagePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun getRecipientsNames(): String {
|
fun getRecipientsNames(): String {
|
||||||
return messageRepository.draftMessage?.recipients.orEmpty().joinToString { it.recipient.name }
|
return messageRepository.draftMessage?.recipients.orEmpty()
|
||||||
|
.joinToString { it.recipient.name }
|
||||||
}
|
}
|
||||||
|
|
||||||
fun clearDraft() {
|
fun clearDraft() {
|
||||||
@ -267,6 +271,7 @@ class SendMessagePresenter @Inject constructor(
|
|||||||
Timber.i("Draft cleared!")
|
Timber.i("Draft cleared!")
|
||||||
}
|
}
|
||||||
|
|
||||||
fun getMessageBackupContent(recipients: String) = if (recipients.isEmpty()) view?.getMessageBackupDialogString()
|
fun getMessageBackupContent(recipients: String) =
|
||||||
|
if (recipients.isEmpty()) view?.getMessageBackupDialogString()
|
||||||
else view?.getMessageBackupDialogStringWithRecipients(recipients)
|
else view?.getMessageBackupDialogStringWithRecipients(recipients)
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.message.tab
|
package io.github.wulkanowy.ui.modules.message.tab
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Message
|
import io.github.wulkanowy.data.db.entities.Message
|
||||||
import io.github.wulkanowy.data.enums.MessageFolder
|
import io.github.wulkanowy.data.enums.MessageFolder
|
||||||
import io.github.wulkanowy.data.repositories.MessageRepository
|
import io.github.wulkanowy.data.repositories.MessageRepository
|
||||||
@ -9,17 +9,10 @@ import io.github.wulkanowy.data.repositories.StudentRepository
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
import io.github.wulkanowy.utils.toFormattedString
|
||||||
import kotlinx.coroutines.FlowPreview
|
import kotlinx.coroutines.FlowPreview
|
||||||
import kotlinx.coroutines.channels.Channel
|
import kotlinx.coroutines.channels.Channel
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.*
|
||||||
import kotlinx.coroutines.flow.collect
|
|
||||||
import kotlinx.coroutines.flow.consumeAsFlow
|
|
||||||
import kotlinx.coroutines.flow.debounce
|
|
||||||
import kotlinx.coroutines.flow.map
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import me.xdrop.fuzzywuzzy.FuzzySearch
|
import me.xdrop.fuzzywuzzy.FuzzySearch
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
@ -107,64 +100,75 @@ class MessageTabPresenter @Inject constructor(
|
|||||||
) {
|
) {
|
||||||
Timber.i("Loading $folder message data started")
|
Timber.i("Loading $folder message data started")
|
||||||
|
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
messageRepository.getMessages(student, semester, folder, forceRefresh)
|
messageRepository.getMessages(student, semester, folder, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load $folder message")
|
||||||
Status.LOADING -> {
|
.onEach {
|
||||||
if (!it.data.isNullOrEmpty()) {
|
when (it) {
|
||||||
view?.run {
|
is Resource.Intermediate -> {
|
||||||
enableSwipe(true)
|
if (it.data.isNotEmpty()) {
|
||||||
showErrorView(false)
|
view?.run {
|
||||||
showRefresh(true)
|
enableSwipe(true)
|
||||||
showProgress(false)
|
showErrorView(false)
|
||||||
showContent(true)
|
showRefresh(true)
|
||||||
messages = it.data
|
showProgress(false)
|
||||||
val filteredData = getFilteredData(
|
showContent(true)
|
||||||
|
messages = it.data
|
||||||
|
val filteredData = getFilteredData(
|
||||||
|
lastSearchQuery,
|
||||||
|
onlyUnread,
|
||||||
|
onlyWithAttachments
|
||||||
|
)
|
||||||
|
val messageItems = filteredData.map { message ->
|
||||||
|
MessageTabDataItem.MessageItem(message)
|
||||||
|
}
|
||||||
|
val messageItemsWithHeader =
|
||||||
|
listOf(MessageTabDataItem.Header) + messageItems
|
||||||
|
|
||||||
|
updateData(
|
||||||
|
messageItemsWithHeader,
|
||||||
|
folder.id == MessageFolder.SENT.id
|
||||||
|
)
|
||||||
|
notifyParentDataLoaded()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is Resource.Success -> {
|
||||||
|
messages = it.data
|
||||||
|
updateData(
|
||||||
|
getFilteredData(
|
||||||
lastSearchQuery,
|
lastSearchQuery,
|
||||||
onlyUnread,
|
onlyUnread,
|
||||||
onlyWithAttachments
|
onlyWithAttachments
|
||||||
)
|
)
|
||||||
val messageItems = filteredData.map { message ->
|
)
|
||||||
MessageTabDataItem.MessageItem(message)
|
analytics.logEvent(
|
||||||
}
|
"load_data",
|
||||||
val messageItemsWithHeader =
|
"type" to "messages",
|
||||||
listOf(MessageTabDataItem.Header) + messageItems
|
"items" to it.data.size,
|
||||||
|
"folder" to folder.name
|
||||||
updateData(messageItemsWithHeader, folder.id == MessageFolder.SENT.id)
|
)
|
||||||
notifyParentDataLoaded()
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
else -> {}
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading $folder message result: Success")
|
|
||||||
messages = it.data!!
|
|
||||||
updateData(getFilteredData(lastSearchQuery, onlyUnread, onlyWithAttachments))
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "messages",
|
|
||||||
"items" to it.data.size,
|
|
||||||
"folder" to folder.name
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading $folder message result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceNotLoading {
|
||||||
view?.run {
|
view?.run {
|
||||||
showRefresh(false)
|
showRefresh(false)
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
notifyParentDataLoaded()
|
notifyParentDataLoaded()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}.catch {
|
.onResourceError(errorHandler::dispatch)
|
||||||
errorHandler.dispatch(it)
|
.catch {
|
||||||
view?.notifyParentDataLoaded()
|
errorHandler.dispatch(it)
|
||||||
}.launch()
|
view?.notifyParentDataLoaded()
|
||||||
|
}
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.mobiledevice
|
package io.github.wulkanowy.ui.modules.mobiledevice
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.MobileDevice
|
import io.github.wulkanowy.data.db.entities.MobileDevice
|
||||||
import io.github.wulkanowy.data.repositories.MobileDeviceRepository
|
import io.github.wulkanowy.data.repositories.MobileDeviceRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
@ -8,10 +8,6 @@ import io.github.wulkanowy.data.repositories.StudentRepository
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -52,49 +48,39 @@ class MobileDevicePresenter @Inject constructor(
|
|||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading mobile devices data started")
|
Timber.i("Loading mobile devices data started")
|
||||||
|
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
mobileDeviceRepository.getDevices(student, semester, forceRefresh)
|
mobileDeviceRepository.getDevices(student, semester, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load mobile devices data")
|
||||||
Status.LOADING -> {
|
.onResourceData {
|
||||||
if (!it.data.isNullOrEmpty()) {
|
view?.run {
|
||||||
view?.run {
|
enableSwipe(true)
|
||||||
enableSwipe(true)
|
showProgress(false)
|
||||||
showRefresh(true)
|
showErrorView(false)
|
||||||
showProgress(false)
|
showContent(it.isNotEmpty())
|
||||||
showContent(true)
|
showEmpty(it.isEmpty())
|
||||||
updateData(it.data)
|
updateData(it)
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading mobile devices result: Success")
|
|
||||||
view?.run {
|
|
||||||
updateData(it.data!!)
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "devices",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading mobile devices result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "devices",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
@ -128,25 +114,19 @@ class MobileDevicePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun onUnregisterConfirmed(device: MobileDevice) {
|
fun onUnregisterConfirmed(device: MobileDevice) {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
mobileDeviceRepository.unregisterDevice(student, semester, device)
|
mobileDeviceRepository.unregisterDevice(student, semester, device)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("unregister device")
|
||||||
Status.LOADING -> Timber.i("Unregister device started")
|
.onResourceSuccess {
|
||||||
Status.SUCCESS -> {
|
view?.run {
|
||||||
Timber.i("Unregister device result: Success")
|
showProgress(false)
|
||||||
view?.run {
|
enableSwipe(true)
|
||||||
showProgress(false)
|
|
||||||
enableSwipe(true)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Unregister device result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.launch("unregister")
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch("unregister")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,15 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.mobiledevice.token
|
package io.github.wulkanowy.ui.modules.mobiledevice.token
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.repositories.MobileDeviceRepository
|
import io.github.wulkanowy.data.repositories.MobileDeviceRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -29,29 +26,29 @@ class MobileDeviceTokenPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource {
|
resourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
mobileDeviceRepository.getToken(student, semester)
|
mobileDeviceRepository.getToken(student, semester)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load mobile device registration")
|
||||||
Status.LOADING -> Timber.i("Mobile device registration data started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
view?.run {
|
||||||
Timber.i("Mobile device registration result: Success")
|
updateData(it)
|
||||||
view?.run {
|
showContent()
|
||||||
updateData(it.data!!)
|
|
||||||
showContent()
|
|
||||||
}
|
|
||||||
analytics.logEvent("device_register", "symbol" to it.data!!.token.substring(0, 3))
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Mobile device registration result: An exception occurred")
|
|
||||||
view?.closeDialog()
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceSuccess {
|
||||||
view?.hideLoading()
|
analytics.logEvent(
|
||||||
}.launch()
|
"device_register",
|
||||||
|
"symbol" to it.token.substring(0, 3)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
.onResourceNotLoading { view?.hideLoading() }
|
||||||
|
.onResourceError {
|
||||||
|
view?.closeDialog()
|
||||||
|
errorHandler.dispatch(it)
|
||||||
|
}
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.note
|
package io.github.wulkanowy.ui.modules.note
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Note
|
import io.github.wulkanowy.data.db.entities.Note
|
||||||
import io.github.wulkanowy.data.repositories.NoteRepository
|
import io.github.wulkanowy.data.repositories.NoteRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
@ -8,9 +8,6 @@ import io.github.wulkanowy.data.repositories.StudentRepository
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -51,51 +48,40 @@ class NotePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading note data started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
noteRepository.getNotes(student, semester, forceRefresh)
|
noteRepository.getNotes(student, semester, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load note data")
|
||||||
Status.LOADING -> {
|
.mapResourceData { it.sortedByDescending { note -> note.date } }
|
||||||
if (!it.data.isNullOrEmpty()) {
|
.onResourceData {
|
||||||
view?.run {
|
view?.run {
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
showRefresh(true)
|
showProgress(false)
|
||||||
showProgress(false)
|
showErrorView(false)
|
||||||
showContent(true)
|
showContent(it.isNotEmpty())
|
||||||
updateData(it.data.sortedByDescending { item -> item.date })
|
showEmpty(it.isEmpty())
|
||||||
}
|
updateData(it)
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading note result: Success")
|
|
||||||
view?.apply {
|
|
||||||
updateData(it.data!!.sortedByDescending { item -> item.date })
|
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "note",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading note result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "note",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
@ -122,14 +108,14 @@ class NotePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun updateNote(note: Note) {
|
private fun updateNote(note: Note) {
|
||||||
flowWithResource { noteRepository.updateNote(note) }
|
resourceFlow { noteRepository.updateNote(note) }
|
||||||
.onEach {
|
.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> Timber.i("Attempt to update note ${note.id}")
|
is Resource.Loading -> Timber.i("Attempt to update note ${note.id}")
|
||||||
Status.SUCCESS -> Timber.i("Update note result: Success")
|
is Resource.Success -> Timber.i("Update note result: Success")
|
||||||
Status.ERROR -> {
|
is Resource.Error -> {
|
||||||
Timber.i("Update note result: An exception occurred")
|
Timber.i("Update note result: An exception occurred")
|
||||||
errorHandler.dispatch(it.error!!)
|
errorHandler.dispatch(it.error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,16 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.schoolandteachers.school
|
package io.github.wulkanowy.ui.modules.schoolandteachers.school
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.repositories.SchoolRepository
|
import io.github.wulkanowy.data.repositories.SchoolRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -65,46 +62,48 @@ class SchoolPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
schoolRepository.getSchoolInfo(student, semester, forceRefresh)
|
schoolRepository.getSchoolInfo(student, semester, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load school info")
|
||||||
Status.LOADING -> Timber.i("Loading school info started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> if (it.data != null) {
|
if (it != null) {
|
||||||
Timber.i("Loading teachers result: Success")
|
|
||||||
view?.run {
|
view?.run {
|
||||||
address = it.data.address.ifBlank { null }
|
address = it.address.ifBlank { null }
|
||||||
contact = it.data.contact.ifBlank { null }
|
contact = it.contact.ifBlank { null }
|
||||||
updateData(it.data)
|
updateData(it)
|
||||||
showContent(true)
|
showContent(true)
|
||||||
showEmpty(false)
|
showEmpty(false)
|
||||||
showErrorView(false)
|
showErrorView(false)
|
||||||
}
|
}
|
||||||
analytics.logEvent("load_item", "type" to "school")
|
|
||||||
} else view?.run {
|
} else view?.run {
|
||||||
Timber.i("Loading school result: No school info found")
|
Timber.i("Loading school result: No school info found")
|
||||||
showContent(!isViewEmpty)
|
showContent(!isViewEmpty)
|
||||||
showEmpty(isViewEmpty)
|
showEmpty(isViewEmpty)
|
||||||
showErrorView(false)
|
showErrorView(false)
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading school result: An exception occurred")
|
.onResourceSuccess {
|
||||||
errorHandler.dispatch(it.error!!)
|
if (it != null) {
|
||||||
|
analytics.logEvent("load_item", "type" to "school")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceNotLoading {
|
||||||
view?.run {
|
view?.run {
|
||||||
hideRefresh()
|
hideRefresh()
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
notifyParentDataLoaded()
|
notifyParentDataLoaded()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}.catch {
|
.onResourceError(errorHandler::dispatch)
|
||||||
errorHandler.dispatch(it)
|
.catch {
|
||||||
view?.notifyParentDataLoaded()
|
errorHandler.dispatch(it)
|
||||||
}.launch()
|
view?.notifyParentDataLoaded()
|
||||||
|
}
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,16 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.schoolandteachers.teacher
|
package io.github.wulkanowy.ui.modules.schoolandteachers.teacher
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.data.repositories.TeacherRepository
|
import io.github.wulkanowy.data.repositories.TeacherRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -53,43 +50,41 @@ class TeacherPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
teacherRepository.getTeachers(student, semester, forceRefresh)
|
teacherRepository.getTeachers(student, semester, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load teachers data")
|
||||||
Status.LOADING -> Timber.i("Loading teachers data started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
view?.run {
|
||||||
Timber.i("Loading teachers result: Success")
|
updateData(it.filter { item -> item.name.isNotBlank() })
|
||||||
view?.run {
|
showContent(it.isNotEmpty())
|
||||||
updateData(it.data!!.filter { item -> item.name.isNotBlank() })
|
showEmpty(it.isEmpty())
|
||||||
showContent(it.data.isNotEmpty())
|
showErrorView(false)
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "teachers",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading teachers result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceSuccess {
|
||||||
view?.run {
|
analytics.logEvent(
|
||||||
hideRefresh()
|
"load_data",
|
||||||
showProgress(false)
|
"type" to "teachers",
|
||||||
enableSwipe(true)
|
"items" to it.size
|
||||||
notifyParentDataLoaded()
|
)
|
||||||
}
|
}
|
||||||
}.catch {
|
.onResourceNotLoading {
|
||||||
errorHandler.dispatch(it)
|
view?.run {
|
||||||
view?.notifyParentDataLoaded()
|
hideRefresh()
|
||||||
}.launch()
|
showProgress(false)
|
||||||
|
enableSwipe(true)
|
||||||
|
notifyParentDataLoaded()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.catch {
|
||||||
|
errorHandler.dispatch(it)
|
||||||
|
view?.notifyParentDataLoaded()
|
||||||
|
}
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,15 +1,12 @@
|
|||||||
package io.github.wulkanowy.ui.modules.schoolannouncement
|
package io.github.wulkanowy.ui.modules.schoolannouncement
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.SchoolAnnouncement
|
import io.github.wulkanowy.data.db.entities.SchoolAnnouncement
|
||||||
import io.github.wulkanowy.data.repositories.SchoolAnnouncementRepository
|
import io.github.wulkanowy.data.repositories.SchoolAnnouncementRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -52,50 +49,37 @@ class SchoolAnnouncementPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading School announcement data started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
schoolAnnouncementRepository.getSchoolAnnouncements(student, forceRefresh)
|
schoolAnnouncementRepository.getSchoolAnnouncements(student, forceRefresh)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load school announcement")
|
||||||
Status.LOADING -> {
|
.onResourceData {
|
||||||
if (!it.data.isNullOrEmpty()) {
|
view?.run {
|
||||||
view?.run {
|
enableSwipe(true)
|
||||||
enableSwipe(true)
|
showProgress(false)
|
||||||
showRefresh(true)
|
showErrorView(false)
|
||||||
showErrorView(false)
|
showContent(it.isNotEmpty())
|
||||||
showProgress(false)
|
showEmpty(it.isEmpty())
|
||||||
showContent(true)
|
updateData(it)
|
||||||
updateData(it.data)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading School announcement result: Success")
|
|
||||||
view?.apply {
|
|
||||||
updateData(it.data!!)
|
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_school_announcement",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading School announcement result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceSuccess {
|
||||||
view?.run {
|
analytics.logEvent(
|
||||||
showRefresh(false)
|
"load_school_announcement",
|
||||||
showProgress(false)
|
"items" to it.size
|
||||||
enableSwipe(true)
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch("load_data")
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.studentinfo
|
package io.github.wulkanowy.ui.modules.studentinfo
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.StudentInfo
|
import io.github.wulkanowy.data.db.entities.StudentInfo
|
||||||
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
import io.github.wulkanowy.data.db.entities.StudentWithSemesters
|
||||||
import io.github.wulkanowy.data.repositories.StudentInfoRepository
|
import io.github.wulkanowy.data.repositories.StudentInfoRepository
|
||||||
@ -8,10 +8,7 @@ import io.github.wulkanowy.data.repositories.StudentRepository
|
|||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.AnalyticsHelper
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.getCurrentOrLast
|
import io.github.wulkanowy.utils.getCurrentOrLast
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@ -72,51 +69,50 @@ class StudentInfoPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val semester = studentWithSemesters.semesters.getCurrentOrLast()
|
val semester = studentWithSemesters.semesters.getCurrentOrLast()
|
||||||
studentInfoRepository.getStudentInfo(
|
studentInfoRepository.getStudentInfo(
|
||||||
student = studentWithSemesters.student,
|
student = studentWithSemesters.student,
|
||||||
semester = semester,
|
semester = semester,
|
||||||
forceRefresh = forceRefresh
|
forceRefresh = forceRefresh
|
||||||
)
|
)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load student info $infoType")
|
||||||
Status.LOADING -> Timber.i("Loading student info $infoType started")
|
.onResourceData {
|
||||||
Status.SUCCESS -> {
|
val isFamily = infoType == StudentInfoView.Type.FAMILY
|
||||||
val isFamily = infoType == StudentInfoView.Type.FAMILY
|
val isFirstGuardianEmpty = it?.firstGuardian == null
|
||||||
val isFirstGuardianEmpty = it.data?.firstGuardian == null
|
val isSecondGuardianEmpty = it?.secondGuardian == null
|
||||||
val isSecondGuardianEmpty = it.data?.secondGuardian == null
|
if (it != null && !(isFamily && isFirstGuardianEmpty && isSecondGuardianEmpty)) {
|
||||||
|
Timber.i("Loading student info $infoType result: Success")
|
||||||
if (it.data != null && !(isFamily && isFirstGuardianEmpty && isSecondGuardianEmpty)) {
|
showCorrectData(it)
|
||||||
Timber.i("Loading student info $infoType result: Success")
|
view?.run {
|
||||||
showCorrectData(it.data)
|
showContent(true)
|
||||||
view?.run {
|
showEmpty(false)
|
||||||
showContent(true)
|
showErrorView(false)
|
||||||
showEmpty(false)
|
}
|
||||||
showErrorView(false)
|
} else {
|
||||||
}
|
Timber.i("Loading student info $infoType result: No student or family info found")
|
||||||
analytics.logEvent("load_item", "type" to "student_info")
|
view?.run {
|
||||||
} else {
|
showContent(!isViewEmpty)
|
||||||
Timber.i("Loading student info $infoType result: No student or family info found")
|
showEmpty(isViewEmpty)
|
||||||
view?.run {
|
showErrorView(false)
|
||||||
showContent(!isViewEmpty)
|
|
||||||
showEmpty(isViewEmpty)
|
|
||||||
showErrorView(false)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> {
|
}
|
||||||
Timber.i("Loading student info $infoType result: An exception occurred")
|
.onResourceSuccess {
|
||||||
errorHandler.dispatch(it.error!!)
|
if (it != null) {
|
||||||
|
analytics.logEvent("load_item", "type" to "student_info")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceNotLoading {
|
||||||
view?.run {
|
view?.run {
|
||||||
hideRefresh()
|
hideRefresh()
|
||||||
showProgress(false)
|
showProgress(false)
|
||||||
enableSwipe(true)
|
enableSwipe(true)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showCorrectData(studentInfo: StudentInfo) {
|
private fun showCorrectData(studentInfo: StudentInfo) {
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package io.github.wulkanowy.ui.modules.timetable
|
package io.github.wulkanowy.ui.modules.timetable
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.Timetable
|
import io.github.wulkanowy.data.db.entities.Timetable
|
||||||
import io.github.wulkanowy.data.enums.TimetableMode
|
import io.github.wulkanowy.data.enums.TimetableMode
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
||||||
@ -123,57 +123,47 @@ class TimetablePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading timetable data started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
timetableRepository.getTimetable(
|
timetableRepository.getTimetable(
|
||||||
student, semester, currentDate, currentDate, forceRefresh
|
student = student,
|
||||||
|
semester = semester,
|
||||||
|
start = currentDate,
|
||||||
|
end = currentDate,
|
||||||
|
forceRefresh = forceRefresh,
|
||||||
|
timetableType = TimetableRepository.TimetableType.NORMAL
|
||||||
)
|
)
|
||||||
}.onEach {
|
}
|
||||||
when (it.status) {
|
.logResourceStatus("load timetable data")
|
||||||
Status.LOADING -> {
|
.onResourceData {
|
||||||
if (!it.data?.lessons.isNullOrEmpty()) {
|
view?.run {
|
||||||
view?.run {
|
enableSwipe(true)
|
||||||
updateData(it.data!!.lessons)
|
showProgress(false)
|
||||||
enableSwipe(true)
|
showErrorView(false)
|
||||||
showRefresh(true)
|
showContent(it.lessons.isNotEmpty())
|
||||||
showErrorView(false)
|
showEmpty(it.lessons.isEmpty())
|
||||||
showProgress(false)
|
updateData(it.lessons)
|
||||||
showContent(true)
|
setDayHeaderMessage(it.headers.singleOrNull { header -> header.date == currentDate }?.content)
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Status.SUCCESS -> {
|
|
||||||
Timber.i("Loading timetable result: Success")
|
|
||||||
view?.apply {
|
|
||||||
updateData(it.data!!.lessons)
|
|
||||||
showEmpty(it.data.lessons.isEmpty())
|
|
||||||
setDayHeaderMessage(it.data.headers.singleOrNull { header ->
|
|
||||||
header.date == currentDate
|
|
||||||
}?.content)
|
|
||||||
showErrorView(false)
|
|
||||||
showContent(it.data.lessons.isNotEmpty())
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "timetable",
|
|
||||||
"items" to it.data!!.lessons.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading timetable result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "timetable",
|
||||||
|
"items" to it.lessons.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun updateData(lessons: List<Timetable>) {
|
private fun updateData(lessons: List<Timetable>) {
|
||||||
|
@ -1,23 +1,14 @@
|
|||||||
package io.github.wulkanowy.ui.modules.timetable.additional
|
package io.github.wulkanowy.ui.modules.timetable.additional
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.TimetableAdditional
|
import io.github.wulkanowy.data.db.entities.TimetableAdditional
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.data.repositories.TimetableRepository
|
import io.github.wulkanowy.data.repositories.TimetableRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.*
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.capitalise
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.getLastSchoolDayIfHoliday
|
|
||||||
import io.github.wulkanowy.utils.isHolidays
|
|
||||||
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.nextSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.previousSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.flow
|
import kotlinx.coroutines.flow.flow
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
@ -137,39 +128,44 @@ class AdditionalLessonsPresenter @Inject constructor(
|
|||||||
private fun loadData(date: LocalDate, forceRefresh: Boolean = false) {
|
private fun loadData(date: LocalDate, forceRefresh: Boolean = false) {
|
||||||
currentDate = date
|
currentDate = date
|
||||||
|
|
||||||
flowWithResourceIn {
|
flatResourceFlow {
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
timetableRepository.getTimetable(student, semester, date, date, forceRefresh, true)
|
timetableRepository.getTimetable(
|
||||||
}.onEach {
|
student = student,
|
||||||
when (it.status) {
|
semester = semester,
|
||||||
Status.LOADING -> Timber.i("Loading additional lessons data started")
|
start = date,
|
||||||
Status.SUCCESS -> {
|
end = date,
|
||||||
Timber.i("Loading additional lessons lessons result: Success")
|
forceRefresh = forceRefresh,
|
||||||
view?.apply {
|
refreshAdditional = true,
|
||||||
updateData(it.data!!.additional.sortedBy { item -> item.start })
|
timetableType = TimetableRepository.TimetableType.ADDITIONAL
|
||||||
showEmpty(it.data.additional.isEmpty())
|
)
|
||||||
showErrorView(false)
|
}
|
||||||
showContent(it.data.additional.isNotEmpty())
|
.logResourceStatus("load additional lessons")
|
||||||
}
|
.onResourceData {
|
||||||
analytics.logEvent(
|
view?.apply {
|
||||||
"load_data",
|
updateData(it.additional.sortedBy { item -> item.start })
|
||||||
"type" to "additional_lessons",
|
showEmpty(it.additional.isEmpty())
|
||||||
"items" to it.data!!.additional.size
|
showErrorView(false)
|
||||||
)
|
showContent(it.additional.isNotEmpty())
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading additional lessons result: An exception occurred")
|
|
||||||
errorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceSuccess {
|
||||||
view?.run {
|
analytics.logEvent(
|
||||||
hideRefresh()
|
"load_data",
|
||||||
showProgress(false)
|
"type" to "additional_lessons",
|
||||||
enableSwipe(true)
|
"items" to it.additional.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
hideRefresh()
|
||||||
|
showProgress(false)
|
||||||
|
enableSwipe(true)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,22 +1,13 @@
|
|||||||
package io.github.wulkanowy.ui.modules.timetable.completed
|
package io.github.wulkanowy.ui.modules.timetable.completed
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.*
|
||||||
import io.github.wulkanowy.data.db.entities.CompletedLesson
|
import io.github.wulkanowy.data.db.entities.CompletedLesson
|
||||||
import io.github.wulkanowy.data.repositories.CompletedLessonsRepository
|
import io.github.wulkanowy.data.repositories.CompletedLessonsRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.utils.AnalyticsHelper
|
import io.github.wulkanowy.utils.*
|
||||||
import io.github.wulkanowy.utils.afterLoading
|
|
||||||
import io.github.wulkanowy.utils.capitalise
|
|
||||||
import io.github.wulkanowy.utils.flowWithResourceIn
|
|
||||||
import io.github.wulkanowy.utils.getLastSchoolDayIfHoliday
|
|
||||||
import io.github.wulkanowy.utils.isHolidays
|
|
||||||
import io.github.wulkanowy.utils.nextOrSameSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.nextSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.previousSchoolDay
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
|
||||||
import kotlinx.coroutines.flow.catch
|
import kotlinx.coroutines.flow.catch
|
||||||
import kotlinx.coroutines.flow.flow
|
import kotlinx.coroutines.flow.flow
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
@ -111,51 +102,46 @@ class CompletedLessonsPresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData(forceRefresh: Boolean = false) {
|
private fun loadData(forceRefresh: Boolean = false) {
|
||||||
Timber.i("Loading completed lessons data started")
|
flatResourceFlow {
|
||||||
|
|
||||||
flowWithResourceIn {
|
|
||||||
val student = studentRepository.getCurrentStudent()
|
val student = studentRepository.getCurrentStudent()
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
completedLessonsRepository.getCompletedLessons(student, semester, currentDate, currentDate, forceRefresh)
|
completedLessonsRepository.getCompletedLessons(
|
||||||
}.onEach {
|
student = student,
|
||||||
when (it.status) {
|
semester = semester,
|
||||||
Status.LOADING -> {
|
start = currentDate,
|
||||||
if (!it.data.isNullOrEmpty()) {
|
end = currentDate,
|
||||||
view?.run {
|
forceRefresh = forceRefresh
|
||||||
enableSwipe(true)
|
)
|
||||||
showRefresh(true)
|
}
|
||||||
showProgress(false)
|
.logResourceStatus("load completed lessons")
|
||||||
showContent(true)
|
.mapResourceData { it.sortedBy { lesson -> lesson.number } }
|
||||||
updateData(it.data.sortedBy { item -> item.number })
|
.onResourceData {
|
||||||
}
|
view?.run {
|
||||||
}
|
enableSwipe(true)
|
||||||
}
|
showProgress(false)
|
||||||
Status.SUCCESS -> {
|
showErrorView(false)
|
||||||
Timber.i("Loading completed lessons lessons result: Success")
|
showContent(it.isNotEmpty())
|
||||||
view?.apply {
|
showEmpty(it.isEmpty())
|
||||||
updateData(it.data!!.sortedBy { item -> item.number })
|
updateData(it)
|
||||||
showEmpty(it.data.isEmpty())
|
|
||||||
showErrorView(false)
|
|
||||||
showContent(it.data.isNotEmpty())
|
|
||||||
}
|
|
||||||
analytics.logEvent(
|
|
||||||
"load_data",
|
|
||||||
"type" to "completed_lessons",
|
|
||||||
"items" to it.data!!.size
|
|
||||||
)
|
|
||||||
}
|
|
||||||
Status.ERROR -> {
|
|
||||||
Timber.i("Loading completed lessons result: An exception occurred")
|
|
||||||
completedLessonsErrorHandler.dispatch(it.error!!)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.afterLoading {
|
.onResourceIntermediate { view?.showRefresh(true) }
|
||||||
view?.run {
|
.onResourceSuccess {
|
||||||
showRefresh(false)
|
analytics.logEvent(
|
||||||
showProgress(false)
|
"load_data",
|
||||||
enableSwipe(true)
|
"type" to "completed_lessons",
|
||||||
|
"items" to it.size
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}.launch()
|
.onResourceNotLoading {
|
||||||
|
view?.run {
|
||||||
|
enableSwipe(true)
|
||||||
|
showProgress(false)
|
||||||
|
showRefresh(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onResourceError(errorHandler::dispatch)
|
||||||
|
.launch()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showErrorViewOnError(message: String, error: Throwable) {
|
private fun showErrorViewOnError(message: String, error: Throwable) {
|
||||||
|
@ -1,14 +1,14 @@
|
|||||||
package io.github.wulkanowy.ui.modules.timetablewidget
|
package io.github.wulkanowy.ui.modules.timetablewidget
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.Resource
|
||||||
import io.github.wulkanowy.data.db.SharedPrefProvider
|
import io.github.wulkanowy.data.db.SharedPrefProvider
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.ui.base.BasePresenter
|
import io.github.wulkanowy.ui.base.BasePresenter
|
||||||
import io.github.wulkanowy.ui.base.ErrorHandler
|
import io.github.wulkanowy.ui.base.ErrorHandler
|
||||||
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getStudentWidgetKey
|
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getStudentWidgetKey
|
||||||
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getThemeWidgetKey
|
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getThemeWidgetKey
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
import kotlinx.coroutines.flow.onEach
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
@ -56,16 +56,15 @@ class TimetableWidgetConfigurePresenter @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun loadData() {
|
private fun loadData() {
|
||||||
flowWithResource { studentRepository.getSavedStudents(false) }.onEach {
|
resourceFlow { studentRepository.getSavedStudents(false) }.onEach {
|
||||||
when (it.status) {
|
when (it) {
|
||||||
Status.LOADING -> Timber.d("Timetable widget configure students data load")
|
is Resource.Loading -> Timber.d("Timetable widget configure students data load")
|
||||||
Status.SUCCESS -> {
|
is Resource.Success -> {
|
||||||
val selectedStudentId = appWidgetId?.let { id ->
|
val selectedStudentId = appWidgetId?.let { id ->
|
||||||
sharedPref.getLong(getStudentWidgetKey(id), 0)
|
sharedPref.getLong(getStudentWidgetKey(id), 0)
|
||||||
} ?: -1
|
} ?: -1
|
||||||
|
|
||||||
when {
|
when {
|
||||||
it.data!!.isEmpty() -> view?.openLoginView()
|
it.data.isEmpty() -> view?.openLoginView()
|
||||||
it.data.size == 1 && !isFromProvider -> {
|
it.data.size == 1 && !isFromProvider -> {
|
||||||
selectedStudent = it.data.single().student
|
selectedStudent = it.data.single().student
|
||||||
view?.showThemeDialog()
|
view?.showThemeDialog()
|
||||||
@ -73,7 +72,7 @@ class TimetableWidgetConfigurePresenter @Inject constructor(
|
|||||||
else -> view?.updateData(it.data, selectedStudentId)
|
else -> view?.updateData(it.data, selectedStudentId)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Status.ERROR -> errorHandler.dispatch(it.error!!)
|
is Resource.Error -> errorHandler.dispatch(it.error)
|
||||||
}
|
}
|
||||||
}.launch()
|
}.launch()
|
||||||
}
|
}
|
||||||
|
@ -12,6 +12,7 @@ import android.widget.AdapterView.INVALID_POSITION
|
|||||||
import android.widget.RemoteViews
|
import android.widget.RemoteViews
|
||||||
import android.widget.RemoteViewsService
|
import android.widget.RemoteViewsService
|
||||||
import io.github.wulkanowy.R
|
import io.github.wulkanowy.R
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.SharedPrefProvider
|
import io.github.wulkanowy.data.db.SharedPrefProvider
|
||||||
import io.github.wulkanowy.data.db.entities.Timetable
|
import io.github.wulkanowy.data.db.entities.Timetable
|
||||||
import io.github.wulkanowy.data.enums.TimetableMode
|
import io.github.wulkanowy.data.enums.TimetableMode
|
||||||
@ -19,12 +20,12 @@ import io.github.wulkanowy.data.repositories.PreferencesRepository
|
|||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
import io.github.wulkanowy.data.repositories.StudentRepository
|
import io.github.wulkanowy.data.repositories.StudentRepository
|
||||||
import io.github.wulkanowy.data.repositories.TimetableRepository
|
import io.github.wulkanowy.data.repositories.TimetableRepository
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getCurrentThemeWidgetKey
|
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getCurrentThemeWidgetKey
|
||||||
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getDateWidgetKey
|
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getDateWidgetKey
|
||||||
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getStudentWidgetKey
|
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getStudentWidgetKey
|
||||||
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getTodayLastLessonEndDateTimeWidgetKey
|
import io.github.wulkanowy.ui.modules.timetablewidget.TimetableWidgetProvider.Companion.getTodayLastLessonEndDateTimeWidgetKey
|
||||||
import io.github.wulkanowy.utils.getCompatColor
|
import io.github.wulkanowy.utils.getCompatColor
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
|
||||||
import io.github.wulkanowy.utils.toFormattedString
|
import io.github.wulkanowy.utils.toFormattedString
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
@ -118,7 +119,7 @@ class TimetableWidgetFactory(
|
|||||||
|
|
||||||
val semester = semesterRepository.getCurrentSemester(student)
|
val semester = semesterRepository.getCurrentSemester(student)
|
||||||
timetableRepository.getTimetable(student, semester, date, date, false)
|
timetableRepository.getTimetable(student, semester, date, date, false)
|
||||||
.toFirstResult().data?.lessons.orEmpty()
|
.toFirstResult().dataOrNull?.lessons.orEmpty()
|
||||||
.sortedWith(compareBy({ it.number }, { !it.isStudentPlan }))
|
.sortedWith(compareBy({ it.number }, { !it.isStudentPlan }))
|
||||||
.filter {
|
.filter {
|
||||||
if (prefRepository.showWholeClassPlan == TimetableMode.ONLY_CURRENT_GROUP) {
|
if (prefRepository.showWholeClassPlan == TimetableMode.ONLY_CURRENT_GROUP) {
|
||||||
|
@ -1,96 +0,0 @@
|
|||||||
package io.github.wulkanowy.utils
|
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Resource
|
|
||||||
import io.github.wulkanowy.data.Status
|
|
||||||
import kotlinx.coroutines.FlowPreview
|
|
||||||
import kotlinx.coroutines.flow.Flow
|
|
||||||
import kotlinx.coroutines.flow.catch
|
|
||||||
import kotlinx.coroutines.flow.collect
|
|
||||||
import kotlinx.coroutines.flow.emitAll
|
|
||||||
import kotlinx.coroutines.flow.filter
|
|
||||||
import kotlinx.coroutines.flow.first
|
|
||||||
import kotlinx.coroutines.flow.flow
|
|
||||||
import kotlinx.coroutines.flow.map
|
|
||||||
import kotlinx.coroutines.flow.onEach
|
|
||||||
import kotlinx.coroutines.flow.takeWhile
|
|
||||||
import kotlinx.coroutines.sync.Mutex
|
|
||||||
import kotlinx.coroutines.sync.withLock
|
|
||||||
|
|
||||||
inline fun <ResultType, RequestType> networkBoundResource(
|
|
||||||
mutex: Mutex = Mutex(),
|
|
||||||
showSavedOnLoading: Boolean = true,
|
|
||||||
crossinline query: () -> Flow<ResultType>,
|
|
||||||
crossinline fetch: suspend (ResultType) -> RequestType,
|
|
||||||
crossinline saveFetchResult: suspend (old: ResultType, new: RequestType) -> Unit,
|
|
||||||
crossinline onFetchFailed: (Throwable) -> Unit = { },
|
|
||||||
crossinline shouldFetch: (ResultType) -> Boolean = { true },
|
|
||||||
crossinline filterResult: (ResultType) -> ResultType = { it }
|
|
||||||
) = flow {
|
|
||||||
emit(Resource.loading())
|
|
||||||
|
|
||||||
val data = query().first()
|
|
||||||
emitAll(if (shouldFetch(data)) {
|
|
||||||
if (showSavedOnLoading) emit(Resource.loading(filterResult(data)))
|
|
||||||
|
|
||||||
try {
|
|
||||||
val newData = fetch(data)
|
|
||||||
mutex.withLock { saveFetchResult(query().first(), newData) }
|
|
||||||
query().map { Resource.success(filterResult(it)) }
|
|
||||||
} catch (throwable: Throwable) {
|
|
||||||
onFetchFailed(throwable)
|
|
||||||
query().map { Resource.error(throwable, filterResult(it)) }
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
query().map { Resource.success(filterResult(it)) }
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmName("networkBoundResourceWithMap")
|
|
||||||
inline fun <ResultType, RequestType, T> networkBoundResource(
|
|
||||||
mutex: Mutex = Mutex(),
|
|
||||||
showSavedOnLoading: Boolean = true,
|
|
||||||
crossinline query: () -> Flow<ResultType>,
|
|
||||||
crossinline fetch: suspend (ResultType) -> RequestType,
|
|
||||||
crossinline saveFetchResult: suspend (old: ResultType, new: RequestType) -> Unit,
|
|
||||||
crossinline onFetchFailed: (Throwable) -> Unit = { },
|
|
||||||
crossinline shouldFetch: (ResultType) -> Boolean = { true },
|
|
||||||
crossinline mapResult: (ResultType) -> T
|
|
||||||
) = flow {
|
|
||||||
emit(Resource.loading())
|
|
||||||
|
|
||||||
val data = query().first()
|
|
||||||
emitAll(if (shouldFetch(data)) {
|
|
||||||
if (showSavedOnLoading) emit(Resource.loading(mapResult(data)))
|
|
||||||
|
|
||||||
try {
|
|
||||||
val newData = fetch(data)
|
|
||||||
mutex.withLock { saveFetchResult(query().first(), newData) }
|
|
||||||
query().map { Resource.success(mapResult(it)) }
|
|
||||||
} catch (throwable: Throwable) {
|
|
||||||
onFetchFailed(throwable)
|
|
||||||
query().map { Resource.error(throwable, mapResult(it)) }
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
query().map { Resource.success(mapResult(it)) }
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
fun <T> flowWithResource(block: suspend () -> T) = flow {
|
|
||||||
emit(Resource.loading())
|
|
||||||
emit(Resource.success(block()))
|
|
||||||
}.catch { emit(Resource.error(it)) }
|
|
||||||
|
|
||||||
@OptIn(FlowPreview::class)
|
|
||||||
fun <T> flowWithResourceIn(block: suspend () -> Flow<Resource<T>>) = flow {
|
|
||||||
emit(Resource.loading())
|
|
||||||
emitAll(block().filter { it.status != Status.LOADING || (it.status == Status.LOADING && it.data != null) })
|
|
||||||
}.catch { emit(Resource.error(it)) }
|
|
||||||
|
|
||||||
fun <T> Flow<Resource<T>>.afterLoading(callback: () -> Unit) = onEach {
|
|
||||||
if (it.status != Status.LOADING) callback()
|
|
||||||
}
|
|
||||||
|
|
||||||
suspend fun <T> Flow<Resource<T>>.toFirstResult() = filter { it.status != Status.LOADING }.first()
|
|
||||||
|
|
||||||
suspend fun <T> Flow<Resource<T>>.waitForResult() =
|
|
||||||
takeWhile { it.status == Status.LOADING }.collect()
|
|
@ -1,4 +1,4 @@
|
|||||||
package io.github.wulkanowy.utils
|
package io.github.wulkanowy.data
|
||||||
|
|
||||||
import io.mockk.*
|
import io.mockk.*
|
||||||
import kotlinx.coroutines.ExperimentalCoroutinesApi
|
import kotlinx.coroutines.ExperimentalCoroutinesApi
|
||||||
@ -13,7 +13,7 @@ import org.junit.Test
|
|||||||
import kotlin.test.assertEquals
|
import kotlin.test.assertEquals
|
||||||
|
|
||||||
@OptIn(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
class FlowUtilsKtTest {
|
class ResourceTest {
|
||||||
|
|
||||||
private val testScope = TestScope(UnconfinedTestDispatcher())
|
private val testScope = TestScope(UnconfinedTestDispatcher())
|
||||||
|
|
||||||
@ -41,6 +41,7 @@ class FlowUtilsKtTest {
|
|||||||
|
|
||||||
// first
|
// first
|
||||||
networkBoundResource(
|
networkBoundResource(
|
||||||
|
isResultEmpty = { false },
|
||||||
showSavedOnLoading = false,
|
showSavedOnLoading = false,
|
||||||
query = { repo.query() },
|
query = { repo.query() },
|
||||||
fetch = {
|
fetch = {
|
||||||
@ -55,6 +56,7 @@ class FlowUtilsKtTest {
|
|||||||
|
|
||||||
// second
|
// second
|
||||||
networkBoundResource(
|
networkBoundResource(
|
||||||
|
isResultEmpty = { false },
|
||||||
showSavedOnLoading = false,
|
showSavedOnLoading = false,
|
||||||
query = { repo.query() },
|
query = { repo.query() },
|
||||||
fetch = {
|
fetch = {
|
||||||
@ -120,6 +122,7 @@ class FlowUtilsKtTest {
|
|||||||
|
|
||||||
// first
|
// first
|
||||||
networkBoundResource(
|
networkBoundResource(
|
||||||
|
isResultEmpty = { false },
|
||||||
mutex = saveResultMutex,
|
mutex = saveResultMutex,
|
||||||
showSavedOnLoading = false,
|
showSavedOnLoading = false,
|
||||||
query = { repo.query() },
|
query = { repo.query() },
|
||||||
@ -138,6 +141,7 @@ class FlowUtilsKtTest {
|
|||||||
|
|
||||||
// second
|
// second
|
||||||
networkBoundResource(
|
networkBoundResource(
|
||||||
|
isResultEmpty = { false },
|
||||||
mutex = saveResultMutex,
|
mutex = saveResultMutex,
|
||||||
showSavedOnLoading = false,
|
showSavedOnLoading = false,
|
||||||
query = { repo.query() },
|
query = { repo.query() },
|
@ -1,20 +1,17 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.AttendanceDao
|
import io.github.wulkanowy.data.db.dao.AttendanceDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
import io.mockk.*
|
||||||
import io.mockk.MockKAnnotations
|
|
||||||
import io.mockk.Runs
|
|
||||||
import io.mockk.coEvery
|
|
||||||
import io.mockk.coVerify
|
|
||||||
import io.mockk.every
|
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
import io.mockk.just
|
|
||||||
import kotlinx.coroutines.flow.flowOf
|
import kotlinx.coroutines.flow.flowOf
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import org.junit.Assert.assertEquals
|
import org.junit.Assert.assertEquals
|
||||||
@ -73,8 +70,8 @@ class AttendanceRepositoryTest {
|
|||||||
val res = runBlocking { attendanceRepository.getAttendance(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { attendanceRepository.getAttendance(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.size)
|
assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getAttendance(startDate, endDate, 1) }
|
coVerify { sdk.getAttendance(startDate, endDate, 1) }
|
||||||
coVerify { attendanceDb.loadAll(1, 1, startDate, endDate) }
|
coVerify { attendanceDb.loadAll(1, 1, startDate, endDate) }
|
||||||
coVerify { attendanceDb.insertAll(match { it.isEmpty() }) }
|
coVerify { attendanceDb.insertAll(match { it.isEmpty() }) }
|
||||||
@ -97,8 +94,8 @@ class AttendanceRepositoryTest {
|
|||||||
val res = runBlocking { attendanceRepository.getAttendance(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { attendanceRepository.getAttendance(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.size)
|
assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getAttendance(startDate, endDate, 1) }
|
coVerify { sdk.getAttendance(startDate, endDate, 1) }
|
||||||
coVerify { attendanceDb.loadAll(1, 1, startDate, endDate) }
|
coVerify { attendanceDb.loadAll(1, 1, startDate, endDate) }
|
||||||
coVerify {
|
coVerify {
|
||||||
@ -125,8 +122,8 @@ class AttendanceRepositoryTest {
|
|||||||
val res = runBlocking { attendanceRepository.getAttendance(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { attendanceRepository.getAttendance(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(1, res.data?.size)
|
assertEquals(1, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getAttendance(startDate, endDate, 1) }
|
coVerify { sdk.getAttendance(startDate, endDate, 1) }
|
||||||
coVerify { attendanceDb.loadAll(1, 1, startDate, endDate) }
|
coVerify { attendanceDb.loadAll(1, 1, startDate, endDate) }
|
||||||
coVerify { attendanceDb.insertAll(match { it.isEmpty() }) }
|
coVerify { attendanceDb.insertAll(match { it.isEmpty() }) }
|
||||||
|
@ -1,20 +1,17 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.CompletedLessonsDao
|
import io.github.wulkanowy.data.db.dao.CompletedLessonsDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
import io.mockk.*
|
||||||
import io.mockk.MockKAnnotations
|
|
||||||
import io.mockk.Runs
|
|
||||||
import io.mockk.coEvery
|
|
||||||
import io.mockk.coVerify
|
|
||||||
import io.mockk.every
|
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
import io.mockk.just
|
|
||||||
import kotlinx.coroutines.flow.flowOf
|
import kotlinx.coroutines.flow.flowOf
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import org.junit.Assert.assertEquals
|
import org.junit.Assert.assertEquals
|
||||||
@ -73,8 +70,8 @@ class CompletedLessonsRepositoryTest {
|
|||||||
val res = runBlocking { completedLessonRepository.getCompletedLessons(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { completedLessonRepository.getCompletedLessons(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.size)
|
assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getCompletedLessons(startDate, endDate) }
|
coVerify { sdk.getCompletedLessons(startDate, endDate) }
|
||||||
coVerify { completedLessonDb.loadAll(1, 1, startDate, endDate) }
|
coVerify { completedLessonDb.loadAll(1, 1, startDate, endDate) }
|
||||||
coVerify { completedLessonDb.insertAll(match { it.isEmpty() }) }
|
coVerify { completedLessonDb.insertAll(match { it.isEmpty() }) }
|
||||||
@ -97,8 +94,8 @@ class CompletedLessonsRepositoryTest {
|
|||||||
val res = runBlocking { completedLessonRepository.getCompletedLessons(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { completedLessonRepository.getCompletedLessons(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.size)
|
assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getCompletedLessons(startDate, endDate) }
|
coVerify { sdk.getCompletedLessons(startDate, endDate) }
|
||||||
coVerify { completedLessonDb.loadAll(1, 1, startDate, endDate) }
|
coVerify { completedLessonDb.loadAll(1, 1, startDate, endDate) }
|
||||||
coVerify {
|
coVerify {
|
||||||
@ -125,8 +122,8 @@ class CompletedLessonsRepositoryTest {
|
|||||||
val res = runBlocking { completedLessonRepository.getCompletedLessons(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { completedLessonRepository.getCompletedLessons(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(1, res.data?.size)
|
assertEquals(1, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getCompletedLessons(startDate, endDate) }
|
coVerify { sdk.getCompletedLessons(startDate, endDate) }
|
||||||
coVerify { completedLessonDb.loadAll(1, 1, startDate, endDate) }
|
coVerify { completedLessonDb.loadAll(1, 1, startDate, endDate) }
|
||||||
coVerify { completedLessonDb.insertAll(match { it.isEmpty() }) }
|
coVerify { completedLessonDb.insertAll(match { it.isEmpty() }) }
|
||||||
|
@ -1,20 +1,17 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.ExamDao
|
import io.github.wulkanowy.data.db.dao.ExamDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
import io.mockk.*
|
||||||
import io.mockk.MockKAnnotations
|
|
||||||
import io.mockk.Runs
|
|
||||||
import io.mockk.coEvery
|
|
||||||
import io.mockk.coVerify
|
|
||||||
import io.mockk.every
|
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
import io.mockk.just
|
|
||||||
import kotlinx.coroutines.flow.flowOf
|
import kotlinx.coroutines.flow.flowOf
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import org.junit.Assert.assertEquals
|
import org.junit.Assert.assertEquals
|
||||||
@ -74,8 +71,8 @@ class ExamRemoteTest {
|
|||||||
val res = runBlocking { examRepository.getExams(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { examRepository.getExams(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.size)
|
assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getExams(startDate, realEndDate, 1) }
|
coVerify { sdk.getExams(startDate, realEndDate, 1) }
|
||||||
coVerify { examDb.loadAll(1, 1, startDate, realEndDate) }
|
coVerify { examDb.loadAll(1, 1, startDate, realEndDate) }
|
||||||
coVerify { examDb.insertAll(match { it.isEmpty() }) }
|
coVerify { examDb.insertAll(match { it.isEmpty() }) }
|
||||||
@ -98,8 +95,8 @@ class ExamRemoteTest {
|
|||||||
val res = runBlocking { examRepository.getExams(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { examRepository.getExams(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.size)
|
assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getExams(startDate, realEndDate, 1) }
|
coVerify { sdk.getExams(startDate, realEndDate, 1) }
|
||||||
coVerify { examDb.loadAll(1, 1, startDate, realEndDate) }
|
coVerify { examDb.loadAll(1, 1, startDate, realEndDate) }
|
||||||
coVerify {
|
coVerify {
|
||||||
@ -126,8 +123,8 @@ class ExamRemoteTest {
|
|||||||
val res = runBlocking { examRepository.getExams(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { examRepository.getExams(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(1, res.data?.size)
|
assertEquals(1, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getExams(startDate, realEndDate, 1) }
|
coVerify { sdk.getExams(startDate, realEndDate, 1) }
|
||||||
coVerify { examDb.loadAll(1, 1, startDate, realEndDate) }
|
coVerify { examDb.loadAll(1, 1, startDate, realEndDate) }
|
||||||
coVerify { examDb.insertAll(match { it.isEmpty() }) }
|
coVerify { examDb.insertAll(match { it.isEmpty() }) }
|
||||||
|
@ -1,13 +1,15 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.GradeDao
|
import io.github.wulkanowy.data.db.dao.GradeDao
|
||||||
import io.github.wulkanowy.data.db.dao.GradeSummaryDao
|
import io.github.wulkanowy.data.db.dao.GradeSummaryDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
|
||||||
import io.mockk.*
|
import io.mockk.*
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
@ -88,8 +90,8 @@ class GradeRepositoryTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(4, res.data?.first?.size)
|
assertEquals(4, res.dataOrNull?.first?.size)
|
||||||
coVerify {
|
coVerify {
|
||||||
gradeDb.insertAll(withArg {
|
gradeDb.insertAll(withArg {
|
||||||
assertEquals(4, it.size)
|
assertEquals(4, it.size)
|
||||||
@ -142,8 +144,8 @@ class GradeRepositoryTest {
|
|||||||
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(4, res.data?.first?.size)
|
assertEquals(4, res.dataOrNull?.first?.size)
|
||||||
coVerify {
|
coVerify {
|
||||||
gradeDb.insertAll(withArg {
|
gradeDb.insertAll(withArg {
|
||||||
assertEquals(3, it.size)
|
assertEquals(3, it.size)
|
||||||
@ -184,8 +186,8 @@ class GradeRepositoryTest {
|
|||||||
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.first?.size)
|
assertEquals(2, res.dataOrNull?.first?.size)
|
||||||
coVerify { gradeDb.insertAll(match { it.isEmpty() }) }
|
coVerify { gradeDb.insertAll(match { it.isEmpty() }) }
|
||||||
coVerify { gradeDb.deleteAll(match { it.size == 1 }) } // ... here
|
coVerify { gradeDb.deleteAll(match { it.size == 1 }) } // ... here
|
||||||
}
|
}
|
||||||
@ -214,8 +216,8 @@ class GradeRepositoryTest {
|
|||||||
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(3, res.data?.first?.size)
|
assertEquals(3, res.dataOrNull?.first?.size)
|
||||||
coVerify { gradeDb.insertAll(match { it.size == 1 }) } // ... here
|
coVerify { gradeDb.insertAll(match { it.size == 1 }) } // ... here
|
||||||
coVerify { gradeDb.deleteAll(match { it.isEmpty() }) }
|
coVerify { gradeDb.deleteAll(match { it.isEmpty() }) }
|
||||||
}
|
}
|
||||||
@ -240,8 +242,8 @@ class GradeRepositoryTest {
|
|||||||
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(3, res.data?.first?.size)
|
assertEquals(3, res.dataOrNull?.first?.size)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -263,8 +265,8 @@ class GradeRepositoryTest {
|
|||||||
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
val res = runBlocking { gradeRepository.getGrades(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(0, res.data?.first?.size)
|
assertEquals(0, res.dataOrNull?.first?.size)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun createGradeApi(value: Int, weight: Double, date: LocalDate, desc: String) =
|
private fun createGradeApi(value: Int, weight: Double, date: LocalDate, desc: String) =
|
||||||
|
@ -1,16 +1,18 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.GradePartialStatisticsDao
|
import io.github.wulkanowy.data.db.dao.GradePartialStatisticsDao
|
||||||
import io.github.wulkanowy.data.db.dao.GradePointsStatisticsDao
|
import io.github.wulkanowy.data.db.dao.GradePointsStatisticsDao
|
||||||
import io.github.wulkanowy.data.db.dao.GradeSemesterStatisticsDao
|
import io.github.wulkanowy.data.db.dao.GradeSemesterStatisticsDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.sdk.pojo.GradeStatisticsItem
|
import io.github.wulkanowy.sdk.pojo.GradeStatisticsItem
|
||||||
import io.github.wulkanowy.sdk.pojo.GradeStatisticsSubject
|
import io.github.wulkanowy.sdk.pojo.GradeStatisticsSubject
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
|
||||||
import io.mockk.*
|
import io.mockk.*
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
@ -81,11 +83,11 @@ class GradeStatisticsRepositoryTest {
|
|||||||
forceRefresh = true,
|
forceRefresh = true,
|
||||||
).toFirstResult()
|
).toFirstResult()
|
||||||
}
|
}
|
||||||
val items = res.data.orEmpty()
|
val items = res.dataOrNull.orEmpty()
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2 + 1, res.data?.size)
|
assertEquals(2 + 1, res.dataOrNull?.size)
|
||||||
assertEquals("", items[0].partial?.studentAverage)
|
assertEquals("", items[0].partial?.studentAverage)
|
||||||
assertEquals("", items[1].partial?.studentAverage)
|
assertEquals("", items[1].partial?.studentAverage)
|
||||||
assertEquals("", items[2].partial?.studentAverage)
|
assertEquals("", items[2].partial?.studentAverage)
|
||||||
@ -119,11 +121,11 @@ class GradeStatisticsRepositoryTest {
|
|||||||
forceRefresh = true,
|
forceRefresh = true,
|
||||||
).toFirstResult()
|
).toFirstResult()
|
||||||
}
|
}
|
||||||
val items = res.data.orEmpty()
|
val items = res.dataOrNull.orEmpty()
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2 + 1, res.data?.size)
|
assertEquals(2 + 1, res.dataOrNull?.size)
|
||||||
assertEquals("3,00", items[0].partial?.studentAverage)
|
assertEquals("3,00", items[0].partial?.studentAverage)
|
||||||
assertEquals("1.0", items[1].partial?.studentAverage)
|
assertEquals("1.0", items[1].partial?.studentAverage)
|
||||||
assertEquals("5.0", items[2].partial?.studentAverage)
|
assertEquals("5.0", items[2].partial?.studentAverage)
|
||||||
|
@ -1,17 +1,15 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.LuckyNumberDao
|
import io.github.wulkanowy.data.db.dao.LuckyNumberDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntity
|
import io.github.wulkanowy.data.mappers.mapToEntity
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
import io.mockk.*
|
||||||
import io.mockk.MockKAnnotations
|
|
||||||
import io.mockk.Runs
|
|
||||||
import io.mockk.coEvery
|
|
||||||
import io.mockk.coVerify
|
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
import io.mockk.just
|
|
||||||
import kotlinx.coroutines.flow.flowOf
|
import kotlinx.coroutines.flow.flowOf
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import org.junit.Assert.assertEquals
|
import org.junit.Assert.assertEquals
|
||||||
@ -58,8 +56,8 @@ class LuckyNumberRemoteTest {
|
|||||||
val res = runBlocking { luckyNumberRepository.getLuckyNumber(student, true).toFirstResult() }
|
val res = runBlocking { luckyNumberRepository.getLuckyNumber(student, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(luckyNumber.number, res.data?.luckyNumber)
|
assertEquals(luckyNumber.number, res.dataOrNull?.luckyNumber)
|
||||||
coVerify { sdk.getLuckyNumber(student.schoolShortName) }
|
coVerify { sdk.getLuckyNumber(student.schoolShortName) }
|
||||||
coVerify { luckyNumberDb.load(1, date) }
|
coVerify { luckyNumberDb.load(1, date) }
|
||||||
coVerify(exactly = 0) { luckyNumberDb.insertAll(any()) }
|
coVerify(exactly = 0) { luckyNumberDb.insertAll(any()) }
|
||||||
@ -82,8 +80,8 @@ class LuckyNumberRemoteTest {
|
|||||||
val res = runBlocking { luckyNumberRepository.getLuckyNumber(student, true).toFirstResult() }
|
val res = runBlocking { luckyNumberRepository.getLuckyNumber(student, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(luckyNumber.number, res.data?.luckyNumber)
|
assertEquals(luckyNumber.number, res.dataOrNull?.luckyNumber)
|
||||||
coVerify { sdk.getLuckyNumber(student.schoolShortName) }
|
coVerify { sdk.getLuckyNumber(student.schoolShortName) }
|
||||||
coVerify { luckyNumberDb.load(1, date) }
|
coVerify { luckyNumberDb.load(1, date) }
|
||||||
coVerify {
|
coVerify {
|
||||||
@ -112,8 +110,8 @@ class LuckyNumberRemoteTest {
|
|||||||
val res = runBlocking { luckyNumberRepository.getLuckyNumber(student, true).toFirstResult() }
|
val res = runBlocking { luckyNumberRepository.getLuckyNumber(student, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(luckyNumber.number, res.data?.luckyNumber)
|
assertEquals(luckyNumber.number, res.dataOrNull?.luckyNumber)
|
||||||
coVerify { sdk.getLuckyNumber(student.schoolShortName) }
|
coVerify { sdk.getLuckyNumber(student.schoolShortName) }
|
||||||
coVerify { luckyNumberDb.load(1, date) }
|
coVerify { luckyNumberDb.load(1, date) }
|
||||||
coVerify {
|
coVerify {
|
||||||
|
@ -1,13 +1,15 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.SharedPrefProvider
|
import io.github.wulkanowy.data.db.SharedPrefProvider
|
||||||
import io.github.wulkanowy.data.db.dao.MessageAttachmentDao
|
import io.github.wulkanowy.data.db.dao.MessageAttachmentDao
|
||||||
import io.github.wulkanowy.data.db.dao.MessagesDao
|
import io.github.wulkanowy.data.db.dao.MessagesDao
|
||||||
import io.github.wulkanowy.data.db.entities.Message
|
import io.github.wulkanowy.data.db.entities.Message
|
||||||
import io.github.wulkanowy.data.db.entities.MessageWithAttachment
|
import io.github.wulkanowy.data.db.entities.MessageWithAttachment
|
||||||
import io.github.wulkanowy.data.enums.MessageFolder
|
import io.github.wulkanowy.data.enums.MessageFolder
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
@ -15,7 +17,8 @@ import io.github.wulkanowy.sdk.pojo.Folder
|
|||||||
import io.github.wulkanowy.sdk.pojo.MessageDetails
|
import io.github.wulkanowy.sdk.pojo.MessageDetails
|
||||||
import io.github.wulkanowy.sdk.pojo.Sender
|
import io.github.wulkanowy.sdk.pojo.Sender
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
import io.github.wulkanowy.utils.Status
|
||||||
|
import io.github.wulkanowy.utils.status
|
||||||
import io.mockk.*
|
import io.mockk.*
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
@ -102,7 +105,7 @@ class MessageRepositoryTest {
|
|||||||
folder = MessageFolder.RECEIVED,
|
folder = MessageFolder.RECEIVED,
|
||||||
forceRefresh = true,
|
forceRefresh = true,
|
||||||
notify = true, // all new messages will be marked as not notified
|
notify = true, // all new messages will be marked as not notified
|
||||||
).toFirstResult().data.orEmpty()
|
).toFirstResult().dataOrNull.orEmpty()
|
||||||
|
|
||||||
coVerify(exactly = 1) { messageDb.deleteAll(emptyList()) }
|
coVerify(exactly = 1) { messageDb.deleteAll(emptyList()) }
|
||||||
coVerify(exactly = 1) { messageDb.insertAll(emptyList()) }
|
coVerify(exactly = 1) { messageDb.insertAll(emptyList()) }
|
||||||
@ -133,7 +136,7 @@ class MessageRepositoryTest {
|
|||||||
folder = MessageFolder.RECEIVED,
|
folder = MessageFolder.RECEIVED,
|
||||||
forceRefresh = true,
|
forceRefresh = true,
|
||||||
notify = false,
|
notify = false,
|
||||||
).toFirstResult().data.orEmpty()
|
).toFirstResult().dataOrNull.orEmpty()
|
||||||
|
|
||||||
coVerify(exactly = 1) { messageDb.deleteAll(withArg { checkEquals(emptyList<Message>()) }) }
|
coVerify(exactly = 1) { messageDb.deleteAll(withArg { checkEquals(emptyList<Message>()) }) }
|
||||||
coVerify {
|
coVerify {
|
||||||
@ -165,9 +168,9 @@ class MessageRepositoryTest {
|
|||||||
|
|
||||||
val res = runBlocking { repository.getMessage(student, testMessage).toFirstResult() }
|
val res = runBlocking { repository.getMessage(student, testMessage).toFirstResult() }
|
||||||
|
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(Status.SUCCESS, res.status)
|
assertEquals(Status.SUCCESS, res.status)
|
||||||
assertEquals("Test", res.data!!.message.content)
|
assertEquals("Test", res.dataOrNull!!.message.content)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -197,9 +200,9 @@ class MessageRepositoryTest {
|
|||||||
|
|
||||||
val res = runBlocking { repository.getMessage(student, testMessage).toFirstResult() }
|
val res = runBlocking { repository.getMessage(student, testMessage).toFirstResult() }
|
||||||
|
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(Status.SUCCESS, res.status)
|
assertEquals(Status.SUCCESS, res.status)
|
||||||
assertEquals("Test", res.data!!.message.content)
|
assertEquals("Test", res.dataOrNull!!.message.content)
|
||||||
coVerify { messageDb.updateAll(listOf(testMessageWithContent)) }
|
coVerify { messageDb.updateAll(listOf(testMessageWithContent)) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,21 +1,18 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.MobileDeviceDao
|
import io.github.wulkanowy.data.db.dao.MobileDeviceDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.sdk.pojo.Device
|
import io.github.wulkanowy.sdk.pojo.Device
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
import io.mockk.*
|
||||||
import io.mockk.MockKAnnotations
|
|
||||||
import io.mockk.Runs
|
|
||||||
import io.mockk.coEvery
|
|
||||||
import io.mockk.coVerify
|
|
||||||
import io.mockk.every
|
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
import io.mockk.just
|
|
||||||
import kotlinx.coroutines.flow.flowOf
|
import kotlinx.coroutines.flow.flowOf
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import org.junit.Assert
|
import org.junit.Assert
|
||||||
@ -69,8 +66,8 @@ class MobileDeviceRepositoryTest {
|
|||||||
val res = runBlocking { mobileDeviceRepository.getDevices(student, semester, true).toFirstResult() }
|
val res = runBlocking { mobileDeviceRepository.getDevices(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
Assert.assertEquals(null, res.error)
|
Assert.assertEquals(null, res.errorOrNull)
|
||||||
Assert.assertEquals(2, res.data?.size)
|
Assert.assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getRegisteredDevices() }
|
coVerify { sdk.getRegisteredDevices() }
|
||||||
coVerify { mobileDeviceDb.loadAll(1) }
|
coVerify { mobileDeviceDb.loadAll(1) }
|
||||||
coVerify { mobileDeviceDb.insertAll(match { it.isEmpty() }) }
|
coVerify { mobileDeviceDb.insertAll(match { it.isEmpty() }) }
|
||||||
@ -93,8 +90,8 @@ class MobileDeviceRepositoryTest {
|
|||||||
val res = runBlocking { mobileDeviceRepository.getDevices(student, semester, true).toFirstResult() }
|
val res = runBlocking { mobileDeviceRepository.getDevices(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
Assert.assertEquals(null, res.error)
|
Assert.assertEquals(null, res.errorOrNull)
|
||||||
Assert.assertEquals(2, res.data?.size)
|
Assert.assertEquals(2, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getRegisteredDevices() }
|
coVerify { sdk.getRegisteredDevices() }
|
||||||
coVerify { mobileDeviceDb.loadAll(1) }
|
coVerify { mobileDeviceDb.loadAll(1) }
|
||||||
coVerify {
|
coVerify {
|
||||||
@ -121,8 +118,8 @@ class MobileDeviceRepositoryTest {
|
|||||||
val res = runBlocking { mobileDeviceRepository.getDevices(student, semester, true).toFirstResult() }
|
val res = runBlocking { mobileDeviceRepository.getDevices(student, semester, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
Assert.assertEquals(null, res.error)
|
Assert.assertEquals(null, res.errorOrNull)
|
||||||
Assert.assertEquals(1, res.data?.size)
|
Assert.assertEquals(1, res.dataOrNull?.size)
|
||||||
coVerify { sdk.getRegisteredDevices() }
|
coVerify { sdk.getRegisteredDevices() }
|
||||||
coVerify { mobileDeviceDb.loadAll(1) }
|
coVerify { mobileDeviceDb.loadAll(1) }
|
||||||
coVerify { mobileDeviceDb.insertAll(match { it.isEmpty() }) }
|
coVerify { mobileDeviceDb.insertAll(match { it.isEmpty() }) }
|
||||||
|
@ -1,24 +1,21 @@
|
|||||||
package io.github.wulkanowy.data.repositories
|
package io.github.wulkanowy.data.repositories
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.dao.TimetableAdditionalDao
|
import io.github.wulkanowy.data.db.dao.TimetableAdditionalDao
|
||||||
import io.github.wulkanowy.data.db.dao.TimetableDao
|
import io.github.wulkanowy.data.db.dao.TimetableDao
|
||||||
import io.github.wulkanowy.data.db.dao.TimetableHeaderDao
|
import io.github.wulkanowy.data.db.dao.TimetableHeaderDao
|
||||||
|
import io.github.wulkanowy.data.errorOrNull
|
||||||
import io.github.wulkanowy.data.mappers.mapToEntities
|
import io.github.wulkanowy.data.mappers.mapToEntities
|
||||||
|
import io.github.wulkanowy.data.toFirstResult
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.getStudentEntity
|
import io.github.wulkanowy.getStudentEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.sdk.pojo.TimetableFull
|
import io.github.wulkanowy.sdk.pojo.TimetableFull
|
||||||
import io.github.wulkanowy.services.alarm.TimetableNotificationSchedulerHelper
|
import io.github.wulkanowy.services.alarm.TimetableNotificationSchedulerHelper
|
||||||
import io.github.wulkanowy.utils.AutoRefreshHelper
|
import io.github.wulkanowy.utils.AutoRefreshHelper
|
||||||
import io.github.wulkanowy.utils.toFirstResult
|
import io.mockk.*
|
||||||
import io.mockk.MockKAnnotations
|
|
||||||
import io.mockk.Runs
|
|
||||||
import io.mockk.coEvery
|
|
||||||
import io.mockk.coVerify
|
|
||||||
import io.mockk.every
|
|
||||||
import io.mockk.impl.annotations.MockK
|
import io.mockk.impl.annotations.MockK
|
||||||
import io.mockk.impl.annotations.SpyK
|
import io.mockk.impl.annotations.SpyK
|
||||||
import io.mockk.just
|
|
||||||
import kotlinx.coroutines.flow.flowOf
|
import kotlinx.coroutines.flow.flowOf
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
import org.junit.Assert.assertEquals
|
import org.junit.Assert.assertEquals
|
||||||
@ -96,8 +93,8 @@ class TimetableRepositoryTest {
|
|||||||
val res = runBlocking { timetableRepository.getTimetable(student, semester, startDate, endDate, true).toFirstResult() }
|
val res = runBlocking { timetableRepository.getTimetable(student, semester, startDate, endDate, true).toFirstResult() }
|
||||||
|
|
||||||
// verify
|
// verify
|
||||||
assertEquals(null, res.error)
|
assertEquals(null, res.errorOrNull)
|
||||||
assertEquals(2, res.data?.lessons?.size)
|
assertEquals(2, res.dataOrNull!!.lessons.size)
|
||||||
coVerify { sdk.getTimetableFull(startDate, endDate) }
|
coVerify { sdk.getTimetableFull(startDate, endDate) }
|
||||||
coVerify { timetableDb.loadAll(1, 1, startDate, endDate) }
|
coVerify { timetableDb.loadAll(1, 1, startDate, endDate) }
|
||||||
coVerify { timetableDb.insertAll(match { it.isEmpty() }) }
|
coVerify { timetableDb.insertAll(match { it.isEmpty() }) }
|
||||||
|
@ -1,16 +1,18 @@
|
|||||||
package io.github.wulkanowy.ui.modules.grade
|
package io.github.wulkanowy.ui.modules.grade
|
||||||
|
|
||||||
import io.github.wulkanowy.data.Resource
|
import io.github.wulkanowy.data.Resource
|
||||||
import io.github.wulkanowy.data.Status
|
import io.github.wulkanowy.data.dataOrNull
|
||||||
import io.github.wulkanowy.data.db.entities.Grade
|
import io.github.wulkanowy.data.db.entities.Grade
|
||||||
import io.github.wulkanowy.data.db.entities.GradeSummary
|
import io.github.wulkanowy.data.db.entities.GradeSummary
|
||||||
import io.github.wulkanowy.data.db.entities.Student
|
import io.github.wulkanowy.data.db.entities.Student
|
||||||
import io.github.wulkanowy.data.repositories.GradeRepository
|
import io.github.wulkanowy.data.repositories.GradeRepository
|
||||||
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
import io.github.wulkanowy.data.repositories.PreferencesRepository
|
||||||
import io.github.wulkanowy.data.repositories.SemesterRepository
|
import io.github.wulkanowy.data.repositories.SemesterRepository
|
||||||
|
import io.github.wulkanowy.data.resourceFlow
|
||||||
import io.github.wulkanowy.getSemesterEntity
|
import io.github.wulkanowy.getSemesterEntity
|
||||||
import io.github.wulkanowy.sdk.Sdk
|
import io.github.wulkanowy.sdk.Sdk
|
||||||
import io.github.wulkanowy.utils.flowWithResource
|
import io.github.wulkanowy.utils.Status
|
||||||
|
import io.github.wulkanowy.utils.status
|
||||||
import io.mockk.MockKAnnotations
|
import io.mockk.MockKAnnotations
|
||||||
import io.mockk.coEvery
|
import io.mockk.coEvery
|
||||||
import io.mockk.every
|
import io.mockk.every
|
||||||
@ -29,7 +31,7 @@ import java.time.LocalDate.of
|
|||||||
|
|
||||||
class GradeAverageProviderTest {
|
class GradeAverageProviderTest {
|
||||||
|
|
||||||
private suspend fun <T> Flow<Resource<T>>.getResult() = toList()[1].data!!
|
private suspend fun <T> Flow<Resource<T>>.getResult() = toList()[1].dataOrNull!!
|
||||||
|
|
||||||
@MockK
|
@MockK
|
||||||
lateinit var preferencesRepository: PreferencesRepository
|
lateinit var preferencesRepository: PreferencesRepository
|
||||||
@ -144,7 +146,13 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageForceCalc } returns false
|
every { preferencesRepository.gradeAverageForceCalc } returns false
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { noWeightGrades to noWeightGradesSummary }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { noWeightGrades to noWeightGradesSummary }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -156,7 +164,13 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageForceCalc } returns false
|
every { preferencesRepository.gradeAverageForceCalc } returns false
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns true
|
every { preferencesRepository.isOptionalArithmeticAverage } returns true
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { noWeightGrades to noWeightGradesArithmeticSummary }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { noWeightGrades to noWeightGradesArithmeticSummary }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -170,27 +184,27 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
emit(Resource.loading(secondGradeWithModifier to secondSummariesWithModifier))
|
emit(Resource.Intermediate(secondGradeWithModifier to secondSummariesWithModifier))
|
||||||
emit(Resource.success(secondGradeWithModifier to secondSummariesWithModifier))
|
emit(Resource.Success(secondGradeWithModifier to secondSummariesWithModifier))
|
||||||
}
|
}
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).toList() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).toList() }
|
||||||
|
|
||||||
with(items[0]) {
|
with(items[0]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(null, data)
|
assertEquals(null, dataOrNull)
|
||||||
}
|
}
|
||||||
with(items[1]) {
|
with(items[1]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(1, data!!.size)
|
assertEquals(1, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
with(items[2]) {
|
with(items[2]) {
|
||||||
assertEquals(Status.SUCCESS, status)
|
assertEquals(Status.SUCCESS, status)
|
||||||
assertEquals(1, data!!.size)
|
assertEquals(1, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
|
|
||||||
assertEquals(3.5, items[1].data?.single { it.subject == "Język polski" }!!.average, .0) // from details and after set custom plus/minus
|
assertEquals(3.5, items[1].dataOrNull?.single { it.subject == "Język polski" }?.average ?: 0.0, .0) // from details and after set custom plus/minus
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -201,27 +215,27 @@ class GradeAverageProviderTest {
|
|||||||
|
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], false) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[2], false) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
delay(1000)
|
delay(1000)
|
||||||
emit(Resource.success(secondGradeWithModifier to secondSummariesWithModifier))
|
emit(Resource.Success(secondGradeWithModifier to secondSummariesWithModifier))
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], false) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[1], false) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
emit(Resource.success(secondGradeWithModifier to secondSummariesWithModifier))
|
emit(Resource.Success(secondGradeWithModifier to secondSummariesWithModifier))
|
||||||
}
|
}
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, false).toList() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, false).toList() }
|
||||||
|
|
||||||
with(items[0]) {
|
with(items[0]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(null, data)
|
assertEquals(null, dataOrNull)
|
||||||
}
|
}
|
||||||
with(items[1]) {
|
with(items[1]) {
|
||||||
assertEquals(Status.SUCCESS, status)
|
assertEquals(Status.SUCCESS, status)
|
||||||
assertEquals(1, data!!.size)
|
assertEquals(1, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
|
|
||||||
assertEquals(3.5, items[1].data?.single { it.subject == "Język polski" }!!.average, .0) // from details and after set custom plus/minus
|
assertEquals(3.5, items[1].dataOrNull?.single { it.subject == "Język polski" }?.average ?: 0.0, .0) // from details and after set custom plus/minus
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -230,12 +244,26 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], false) } returns flowWithResource { secondGradeWithModifier to secondSummariesWithModifier }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], false) } returns flowWithResource {
|
gradeRepository.getGrades(
|
||||||
listOf(getGrade(semesters[2].semesterId, "Język polski", .0, .0, .0)) to listOf(getSummary(semesters[2].semesterId, "Język polski", 2.5))
|
student,
|
||||||
|
semesters[1],
|
||||||
|
false
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGradeWithModifier to secondSummariesWithModifier }
|
||||||
|
coEvery { gradeRepository.getGrades(student, semesters[2], false) } returns resourceFlow {
|
||||||
|
listOf(getGrade(semesters[2].semesterId, "Język polski", .0, .0, .0)) to listOf(
|
||||||
|
getSummary(semesters[2].semesterId, "Język polski", 2.5)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, false).getResult() }
|
val items = runBlocking {
|
||||||
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
student,
|
||||||
|
semesters[2].semesterId,
|
||||||
|
false
|
||||||
|
).getResult()
|
||||||
|
}
|
||||||
|
|
||||||
assertEquals(3.5, items.single { it.subject == "Język polski" }.average, .0)
|
assertEquals(3.5, items.single { it.subject == "Język polski" }.average, .0)
|
||||||
}
|
}
|
||||||
@ -246,10 +274,28 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], false) } returns flowWithResource { secondGradeWithModifier to secondSummariesWithModifier }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], false) } returns flowWithResource { emptyList<Grade>() to listOf(getSummary(24, "Język polski", .0))}
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
false
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGradeWithModifier to secondSummariesWithModifier }
|
||||||
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
false
|
||||||
|
)
|
||||||
|
} returns resourceFlow { emptyList<Grade>() to listOf(getSummary(24, "Język polski", .0)) }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, false).getResult() }
|
val items = runBlocking {
|
||||||
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
student,
|
||||||
|
semesters[2].semesterId,
|
||||||
|
false
|
||||||
|
).getResult()
|
||||||
|
}
|
||||||
|
|
||||||
assertEquals(3.49, items.single { it.subject == "Język polski" }.average, .0)
|
assertEquals(3.49, items.single { it.subject == "Język polski" }.average, .0)
|
||||||
}
|
}
|
||||||
@ -260,10 +306,28 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource { emptyList<Grade>() to emptyList() }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { emptyList<Grade>() to emptyList() }
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { emptyList<Grade>() to emptyList() }
|
||||||
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { emptyList<Grade>() to emptyList() }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking {
|
||||||
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
student,
|
||||||
|
semesters[2].semesterId,
|
||||||
|
true
|
||||||
|
).getResult()
|
||||||
|
}
|
||||||
|
|
||||||
assertEquals(0, items.size)
|
assertEquals(0, items.size)
|
||||||
}
|
}
|
||||||
@ -274,7 +338,13 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGradeWithModifier to secondSummariesWithModifier }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGradeWithModifier to secondSummariesWithModifier }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -292,7 +362,13 @@ class GradeAverageProviderTest {
|
|||||||
|
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGradeWithModifier to secondSummariesWithModifier }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGradeWithModifier to secondSummariesWithModifier }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -310,7 +386,13 @@ class GradeAverageProviderTest {
|
|||||||
|
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGradeWithModifier to secondSummariesWithModifier }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGradeWithModifier to secondSummariesWithModifier }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -328,7 +410,13 @@ class GradeAverageProviderTest {
|
|||||||
|
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGradeWithModifier to secondSummariesWithModifier }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGradeWithModifier to secondSummariesWithModifier }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -340,7 +428,13 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageForceCalc } returns false
|
every { preferencesRepository.gradeAverageForceCalc } returns false
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGrades to secondSummaries }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGrades to secondSummaries }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -354,7 +448,13 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageForceCalc } returns true
|
every { preferencesRepository.gradeAverageForceCalc } returns true
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ONE_SEMESTER
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGrades to secondSummaries }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGrades to secondSummaries }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -368,7 +468,13 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageForceCalc } returns true
|
every { preferencesRepository.gradeAverageForceCalc } returns true
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource { firstGrades to firstSummaries }
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { firstGrades to firstSummaries }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[1].semesterId, true).getResult() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[1].semesterId, true).getResult() }
|
||||||
|
|
||||||
@ -384,29 +490,29 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
emit(Resource.loading(firstGrades to firstSummaries))
|
emit(Resource.Intermediate(firstGrades to firstSummaries))
|
||||||
emit(Resource.success(firstGrades to firstSummaries))
|
emit(Resource.Success(firstGrades to firstSummaries))
|
||||||
}
|
}
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[1].semesterId, true).toList() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[1].semesterId, true).toList() }
|
||||||
|
|
||||||
with(items[0]) {
|
with(items[0]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(null, data)
|
assertEquals(null, dataOrNull)
|
||||||
}
|
}
|
||||||
with(items[1]) {
|
with(items[1]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(2, data!!.size)
|
assertEquals(2, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
with(items[2]) {
|
with(items[2]) {
|
||||||
assertEquals(Status.SUCCESS, status)
|
assertEquals(Status.SUCCESS, status)
|
||||||
assertEquals(2, data!!.size)
|
assertEquals(2, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
|
|
||||||
assertEquals(2, items[2].data!!.size)
|
assertEquals(2, items[2].dataOrNull?.size)
|
||||||
assertEquals(3.5, items[2].data!!.single { it.subject == "Matematyka" }.average, .0) // (from summary): 3,5
|
assertEquals(3.5, items[2].dataOrNull?.single { it.subject == "Matematyka" }?.average ?: 0.0, .0) // (from summary): 3,5
|
||||||
assertEquals(3.5, items[2].data!!.single { it.subject == "Fizyka" }.average, .0) // (from summary): 3,5
|
assertEquals(3.5, items[2].dataOrNull?.single { it.subject == "Fizyka" }?.average ?: 0.0, .0) // (from summary): 3,5
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -414,13 +520,13 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
every { preferencesRepository.gradeAverageForceCalc } returns false
|
every { preferencesRepository.gradeAverageForceCalc } returns false
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns resourceFlow {
|
||||||
firstGrades to listOf(
|
firstGrades to listOf(
|
||||||
getSummary(22, "Matematyka", 3.0),
|
getSummary(22, "Matematyka", 3.0),
|
||||||
getSummary(22, "Fizyka", 3.5)
|
getSummary(22, "Fizyka", 3.5)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns resourceFlow {
|
||||||
secondGrades to listOf(
|
secondGrades to listOf(
|
||||||
getSummary(22, "Matematyka", 3.5),
|
getSummary(22, "Matematyka", 3.5),
|
||||||
getSummary(22, "Fizyka", 4.0)
|
getSummary(22, "Fizyka", 4.0)
|
||||||
@ -440,46 +546,62 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageForceCalc } returns false
|
every { preferencesRepository.gradeAverageForceCalc } returns false
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
emit(Resource.loading(firstGrades to listOf(
|
emit(
|
||||||
getSummary(22, "Matematyka", 3.0),
|
Resource.Intermediate(
|
||||||
getSummary(22, "Fizyka", 3.5)
|
firstGrades to listOf(
|
||||||
)))
|
getSummary(22, "Matematyka", 3.0),
|
||||||
emit(Resource.success(firstGrades to listOf(
|
getSummary(22, "Fizyka", 3.5)
|
||||||
getSummary(22, "Matematyka", 3.0),
|
)
|
||||||
getSummary(22, "Fizyka", 3.5)
|
)
|
||||||
)))
|
)
|
||||||
|
emit(
|
||||||
|
Resource.Success(
|
||||||
|
firstGrades to listOf(
|
||||||
|
getSummary(22, "Matematyka", 3.0),
|
||||||
|
getSummary(22, "Fizyka", 3.5)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
emit(Resource.loading(secondGrades to listOf(
|
emit(
|
||||||
getSummary(22, "Matematyka", 3.5),
|
Resource.Intermediate(
|
||||||
getSummary(22, "Fizyka", 4.0)
|
secondGrades to listOf(
|
||||||
)))
|
getSummary(22, "Matematyka", 3.5),
|
||||||
emit(Resource.success(secondGrades to listOf(
|
getSummary(22, "Fizyka", 4.0)
|
||||||
getSummary(22, "Matematyka", 3.5),
|
)
|
||||||
getSummary(22, "Fizyka", 4.0)
|
)
|
||||||
)))
|
)
|
||||||
|
emit(
|
||||||
|
Resource.Success(
|
||||||
|
secondGrades to listOf(
|
||||||
|
getSummary(22, "Matematyka", 3.5),
|
||||||
|
getSummary(22, "Fizyka", 4.0)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).toList() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).toList() }
|
||||||
|
|
||||||
with(items[0]) {
|
with(items[0]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(null, data)
|
assertEquals(null, dataOrNull)
|
||||||
}
|
}
|
||||||
with(items[1]) {
|
with(items[1]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(2, data!!.size)
|
assertEquals(2, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
with(items[2]) {
|
with(items[2]) {
|
||||||
assertEquals(Status.SUCCESS, status)
|
assertEquals(Status.SUCCESS, status)
|
||||||
assertEquals(2, data!!.size)
|
assertEquals(2, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
|
|
||||||
assertEquals(2, items[2].data!!.size)
|
assertEquals(2, items[2].dataOrNull?.size)
|
||||||
assertEquals(3.25, items[2].data!!.single { it.subject == "Matematyka" }.average, .0) // (from summaries ↑): 3,0 + 3,5 → 3,25
|
assertEquals(3.25, items[2].dataOrNull?.single { it.subject == "Matematyka" }?.average ?: 0.0, .0) // (from summaries ↑): 3,0 + 3,5 → 3,25
|
||||||
assertEquals(3.75, items[2].data!!.single { it.subject == "Fizyka" }.average, .0) // (from summaries ↑): 3,5 + 4,0 → 3,75
|
assertEquals(3.75, items[2].dataOrNull?.single { it.subject == "Fizyka" }?.average ?: 0.0, .0) // (from summaries ↑): 3,5 + 4,0 → 3,75
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -487,8 +609,14 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageForceCalc } returns true
|
every { preferencesRepository.gradeAverageForceCalc } returns true
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource { firstGrades to firstSummaries }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource {
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { firstGrades to firstSummaries }
|
||||||
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns resourceFlow {
|
||||||
secondGrades to listOf(
|
secondGrades to listOf(
|
||||||
getSummary(22, "Matematyka", 1.1),
|
getSummary(22, "Matematyka", 1.1),
|
||||||
getSummary(22, "Fizyka", 7.26)
|
getSummary(22, "Fizyka", 7.26)
|
||||||
@ -527,7 +655,7 @@ class GradeAverageProviderTest {
|
|||||||
semesters[1],
|
semesters[1],
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
} returns flowWithResource {
|
} returns resourceFlow {
|
||||||
firstGrades to listOf(
|
firstGrades to listOf(
|
||||||
getSummary(22, "Matematyka", .0),
|
getSummary(22, "Matematyka", .0),
|
||||||
getSummary(22, "Fizyka", .0)
|
getSummary(22, "Fizyka", .0)
|
||||||
@ -539,7 +667,7 @@ class GradeAverageProviderTest {
|
|||||||
semesters[2],
|
semesters[2],
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
} returns flowWithResource {
|
} returns resourceFlow {
|
||||||
secondGrades to listOf(
|
secondGrades to listOf(
|
||||||
getSummary(22, "Matematyka", .0),
|
getSummary(22, "Matematyka", .0),
|
||||||
getSummary(22, "Fizyka", .0)
|
getSummary(22, "Fizyka", .0)
|
||||||
@ -566,40 +694,48 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
emit(Resource.loading(firstGrades to firstSummaries))
|
emit(Resource.Intermediate(firstGrades to firstSummaries))
|
||||||
emit(Resource.success(firstGrades to firstSummaries))
|
emit(Resource.Success(firstGrades to firstSummaries))
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flow {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flow {
|
||||||
emit(Resource.loading())
|
emit(Resource.Loading())
|
||||||
emit(Resource.loading(secondGrades to listOf(
|
emit(
|
||||||
getSummary(22, "Matematyka", 1.1),
|
Resource.Intermediate(
|
||||||
getSummary(22, "Fizyka", 7.26)
|
secondGrades to listOf(
|
||||||
)))
|
getSummary(22, "Matematyka", 1.1),
|
||||||
emit(Resource.success(secondGrades to listOf(
|
getSummary(22, "Fizyka", 7.26)
|
||||||
getSummary(22, "Matematyka", 1.1),
|
)
|
||||||
getSummary(22, "Fizyka", 7.26)
|
)
|
||||||
)))
|
)
|
||||||
|
emit(
|
||||||
|
Resource.Success(
|
||||||
|
secondGrades to listOf(
|
||||||
|
getSummary(22, "Matematyka", 1.1),
|
||||||
|
getSummary(22, "Fizyka", 7.26)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).toList() }
|
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).toList() }
|
||||||
|
|
||||||
with(items[0]) {
|
with(items[0]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(null, data)
|
assertEquals(null, dataOrNull)
|
||||||
}
|
}
|
||||||
with(items[1]) {
|
with(items[1]) {
|
||||||
assertEquals(Status.LOADING, status)
|
assertEquals(Status.LOADING, status)
|
||||||
assertEquals(2, data!!.size)
|
assertEquals(2, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
with(items[2]) {
|
with(items[2]) {
|
||||||
assertEquals(Status.SUCCESS, status)
|
assertEquals(Status.SUCCESS, status)
|
||||||
assertEquals(2, data!!.size)
|
assertEquals(2, dataOrNull?.size)
|
||||||
}
|
}
|
||||||
|
|
||||||
assertEquals(2, items[2].data!!.size)
|
assertEquals(2, items[2].dataOrNull?.size)
|
||||||
assertEquals(3.0, items[2].data!!.single { it.subject == "Matematyka" }.average, .0) // (from details): 3,5 + 2,5 → 3,0
|
assertEquals(3.0, items[2].dataOrNull?.single { it.subject == "Matematyka" }?.average ?: 0.0, .0) // (from details): 3,5 + 2,5 → 3,0
|
||||||
assertEquals(3.25, items[2].data!!.single { it.subject == "Fizyka" }.average, .0) // (from details): 3,5 + 3,0 → 3,25
|
assertEquals(3.25, items[2].dataOrNull?.single { it.subject == "Fizyka" }?.average ?: 0.0, .0) // (from details): 3,5 + 3,0 → 3,25
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -614,14 +750,14 @@ class GradeAverageProviderTest {
|
|||||||
semesters[1],
|
semesters[1],
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
} returns flowWithResource { firstGrades to emptyList() }
|
} returns resourceFlow { firstGrades to emptyList() }
|
||||||
coEvery {
|
coEvery {
|
||||||
gradeRepository.getGrades(
|
gradeRepository.getGrades(
|
||||||
student,
|
student,
|
||||||
semesters[2],
|
semesters[2],
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
} returns flowWithResource { secondGrades to emptyList() }
|
} returns resourceFlow { secondGrades to emptyList() }
|
||||||
|
|
||||||
val items = runBlocking {
|
val items = runBlocking {
|
||||||
gradeAverageProvider.getGradesDetailsWithAverage(
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
@ -646,14 +782,40 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource { firstGrades to emptyList() }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGrades to emptyList() }
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { firstGrades to emptyList() }
|
||||||
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGrades to emptyList() }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking {
|
||||||
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
student,
|
||||||
|
semesters[2].semesterId,
|
||||||
|
true
|
||||||
|
).getResult()
|
||||||
|
}
|
||||||
|
|
||||||
assertEquals(2, items.size)
|
assertEquals(2, items.size)
|
||||||
assertEquals(3.0, items.single { it.subject == "Matematyka" }.average, .0) // (from details): 3,5 + 2,5 → 3,0
|
assertEquals(
|
||||||
assertEquals(3.25, items.single { it.subject == "Fizyka" }.average, .0) // (from details): 3,5 + 3,0 → 3,25
|
3.0,
|
||||||
|
items.single { it.subject == "Matematyka" }.average,
|
||||||
|
.0
|
||||||
|
) // (from details): 3,5 + 2,5 → 3,0
|
||||||
|
assertEquals(
|
||||||
|
3.25,
|
||||||
|
items.single { it.subject == "Fizyka" }.average,
|
||||||
|
.0
|
||||||
|
) // (from details): 3,5 + 3,0 → 3,25
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -662,12 +824,12 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns resourceFlow {
|
||||||
firstGrades to listOf(
|
firstGrades to listOf(
|
||||||
getSummary(22, "Matematyka", 4.0)
|
getSummary(22, "Matematyka", 4.0)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns resourceFlow {
|
||||||
secondGrades to listOf(
|
secondGrades to listOf(
|
||||||
getSummary(23, "Matematyka", 3.0)
|
getSummary(23, "Matematyka", 3.0)
|
||||||
)
|
)
|
||||||
@ -686,14 +848,40 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource { firstGrades to firstSummaries }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGrades to secondSummaries.dropLast(1) }
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { firstGrades to firstSummaries }
|
||||||
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGrades to secondSummaries.dropLast(1) }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking {
|
||||||
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
student,
|
||||||
|
semesters[2].semesterId,
|
||||||
|
true
|
||||||
|
).getResult()
|
||||||
|
}
|
||||||
|
|
||||||
assertEquals(2, items.size)
|
assertEquals(2, items.size)
|
||||||
assertEquals(3.4, items.single { it.subject == "Matematyka" }.average, .0) // (from summaries): 3,9 + 2,9 → 3,4
|
assertEquals(
|
||||||
assertEquals(3.05, items.single { it.subject == "Fizyka" }.average, .0) // 3,1 (from summary) + 3,0 (from details) → 3,05
|
3.4,
|
||||||
|
items.single { it.subject == "Matematyka" }.average,
|
||||||
|
.0
|
||||||
|
) // (from summaries): 3,9 + 2,9 → 3,4
|
||||||
|
assertEquals(
|
||||||
|
3.05,
|
||||||
|
items.single { it.subject == "Fizyka" }.average,
|
||||||
|
.0
|
||||||
|
) // 3,1 (from summary) + 3,0 (from details) → 3,05
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -702,14 +890,40 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource { firstGrades to firstSummaries.dropLast(1) }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGrades to secondSummaries }
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { firstGrades to firstSummaries.dropLast(1) }
|
||||||
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGrades to secondSummaries }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking {
|
||||||
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
student,
|
||||||
|
semesters[2].semesterId,
|
||||||
|
true
|
||||||
|
).getResult()
|
||||||
|
}
|
||||||
|
|
||||||
assertEquals(2, items.size)
|
assertEquals(2, items.size)
|
||||||
assertEquals(3.4, items.single { it.subject == "Matematyka" }.average, .0) // (from summaries): 3,9 + 2,9 → 3,4
|
assertEquals(
|
||||||
assertEquals(3.45, items.single { it.subject == "Fizyka" }.average, .0) // 3,5 (from details) + 3,4 (from summary) → 3,45
|
3.4,
|
||||||
|
items.single { it.subject == "Matematyka" }.average,
|
||||||
|
.0
|
||||||
|
) // (from summaries): 3,9 + 2,9 → 3,4
|
||||||
|
assertEquals(
|
||||||
|
3.45,
|
||||||
|
items.single { it.subject == "Fizyka" }.average,
|
||||||
|
.0
|
||||||
|
) // 3,5 (from details) + 3,4 (from summary) → 3,45
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -718,14 +932,40 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource { firstGrades to firstSummaries.dropLast(1) }
|
coEvery {
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource { secondGrades to secondSummaries }
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[1],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { firstGrades to firstSummaries.dropLast(1) }
|
||||||
|
coEvery {
|
||||||
|
gradeRepository.getGrades(
|
||||||
|
student,
|
||||||
|
semesters[2],
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} returns resourceFlow { secondGrades to secondSummaries }
|
||||||
|
|
||||||
val items = runBlocking { gradeAverageProvider.getGradesDetailsWithAverage(student, semesters[2].semesterId, true).getResult() }
|
val items = runBlocking {
|
||||||
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
student,
|
||||||
|
semesters[2].semesterId,
|
||||||
|
true
|
||||||
|
).getResult()
|
||||||
|
}
|
||||||
|
|
||||||
assertEquals(2, items.size)
|
assertEquals(2, items.size)
|
||||||
assertEquals(3.0, items.single { it.subject == "Matematyka" }.average, .0) // (from details): 3,5 + 2,5 → 3,0
|
assertEquals(
|
||||||
assertEquals(3.25, items.single { it.subject == "Fizyka" }.average, .0) // (from details): 3,5 + 3,0 → 3,25
|
3.0,
|
||||||
|
items.single { it.subject == "Matematyka" }.average,
|
||||||
|
.0
|
||||||
|
) // (from details): 3,5 + 2,5 → 3,0
|
||||||
|
assertEquals(
|
||||||
|
3.25,
|
||||||
|
items.single { it.subject == "Fizyka" }.average,
|
||||||
|
.0
|
||||||
|
) // (from details): 3,5 + 3,0 → 3,25
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -734,7 +974,7 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
||||||
@ -746,7 +986,7 @@ class GradeAverageProviderTest {
|
|||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
||||||
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
||||||
@ -765,7 +1005,7 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
||||||
@ -777,7 +1017,7 @@ class GradeAverageProviderTest {
|
|||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
||||||
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
||||||
@ -802,7 +1042,7 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.BOTH_SEMESTERS
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
||||||
@ -814,7 +1054,7 @@ class GradeAverageProviderTest {
|
|||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
||||||
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
||||||
@ -839,7 +1079,7 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
every { preferencesRepository.gradeAverageMode } returns GradeAverageMode.ALL_YEAR
|
||||||
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
coEvery { semesterRepository.getSemesters(student) } returns semesters
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
getGrade(22, "Fizyka", 5.0, weight = 2.0),
|
||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
getGrade(22, "Fizyka", 6.0, weight = 2.0),
|
||||||
@ -851,7 +1091,7 @@ class GradeAverageProviderTest {
|
|||||||
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
getGrade(22, "Fizyka", 6.0, weight = 2.0)
|
||||||
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
) to listOf(getSummary(semesterId = 22, subject = "Fizyka", average = .0))
|
||||||
}
|
}
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns flowWithResource {
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns resourceFlow {
|
||||||
listOf(
|
listOf(
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
getGrade(23, "Fizyka", 5.0, weight = 1.0),
|
||||||
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
getGrade(23, "Fizyka", 5.0, weight = 2.0),
|
||||||
@ -881,9 +1121,9 @@ class GradeAverageProviderTest {
|
|||||||
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
every { preferencesRepository.isOptionalArithmeticAverage } returns false
|
||||||
|
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns
|
coEvery { gradeRepository.getGrades(student, semesters[1], true) } returns
|
||||||
flowWithResource { firstGrades to firstSummaries }
|
resourceFlow { firstGrades to firstSummaries }
|
||||||
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns
|
coEvery { gradeRepository.getGrades(student, semesters[2], true) } returns
|
||||||
flowWithResource { listOf<Grade>() to firstSummaries }
|
resourceFlow { listOf<Grade>() to firstSummaries }
|
||||||
|
|
||||||
val items = runBlocking {
|
val items = runBlocking {
|
||||||
gradeAverageProvider.getGradesDetailsWithAverage(
|
gradeAverageProvider.getGradesDetailsWithAverage(
|
||||||
|
14
app/src/test/java/io/github/wulkanowy/utils/ResourceUtils.kt
Normal file
14
app/src/test/java/io/github/wulkanowy/utils/ResourceUtils.kt
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
package io.github.wulkanowy.utils
|
||||||
|
|
||||||
|
import io.github.wulkanowy.data.Resource
|
||||||
|
|
||||||
|
enum class Status {
|
||||||
|
LOADING, SUCCESS, ERROR
|
||||||
|
}
|
||||||
|
|
||||||
|
val <T> Resource<T>.status
|
||||||
|
get() = when (this) {
|
||||||
|
is Resource.Error -> Status.ERROR
|
||||||
|
is Resource.Loading -> Status.LOADING
|
||||||
|
is Resource.Success -> Status.SUCCESS
|
||||||
|
}
|
2
gradle/wrapper/gradle-wrapper.properties
vendored
2
gradle/wrapper/gradle-wrapper.properties
vendored
@ -1,5 +1,5 @@
|
|||||||
distributionBase=GRADLE_USER_HOME
|
distributionBase=GRADLE_USER_HOME
|
||||||
distributionPath=wrapper/dists
|
distributionPath=wrapper/dists
|
||||||
distributionUrl=https\://services.gradle.org/distributions/gradle-7.2-all.zip
|
distributionUrl=https\://services.gradle.org/distributions/gradle-7.4.1-all.zip
|
||||||
zipStoreBase=GRADLE_USER_HOME
|
zipStoreBase=GRADLE_USER_HOME
|
||||||
zipStorePath=wrapper/dists
|
zipStorePath=wrapper/dists
|
||||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user