Skip to content

Commit

Permalink
ad K2, base ui for userlist
Browse files Browse the repository at this point in the history
  • Loading branch information
stslex committed Aug 4, 2023
1 parent c9d7fd8 commit d024e25
Show file tree
Hide file tree
Showing 24 changed files with 334 additions and 24 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import android.app.Application
import com.stslex.aproselection.controller.AuthController
import com.stslex.aproselection.core.datastore.coreDataStoreModule
import com.stslex.aproselection.core.network.di.ModuleCoreNetwork.moduleCoreNetwork
import com.stslex.aproselection.core.user.di.moduleCoreUser
import com.stslex.aproselection.di.appModule
import com.stslex.aproselection.feature.auth.di.ModuleFeatureAuth.moduleFeatureAuth
import com.stslex.aproselection.feature.home.di.moduleFeatureHome
Expand Down Expand Up @@ -33,6 +34,7 @@ class SelectApplication : Application() {
modules(
appModule,
moduleCoreNetwork,
moduleCoreUser,
coreDataStoreModule,
moduleFeatureAuth,
moduleFeatureHome,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
* Configure Compose-specific options
*/
internal fun Project.configureAndroidCompose(
commonExtension: CommonExtension<*, *, *, *>,
commonExtension: CommonExtension<*, *, *, *, *>,
) {
val libs = extensions.getByType<VersionCatalogsExtension>().named("libs")

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
* Configure base Kotlin with Android options
*/
internal fun Project.configureKotlinAndroid(
commonExtension: CommonExtension<*, *, *, *>,
commonExtension: CommonExtension<*, *, *, *, *>,
) {
commonExtension.apply {

Expand Down Expand Up @@ -64,7 +64,7 @@ internal fun Project.configureKotlinAndroid(
}
}

private fun CommonExtension<*, *, *, *>.kotlinOptions(block: KotlinJvmOptions.() -> Unit) {
private fun CommonExtension<*, *, *, *, *>.kotlinOptions(block: KotlinJvmOptions.() -> Unit) {
(this as ExtensionAware).extensions.configure("kotlinOptions", block)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,4 +10,6 @@ interface AppDataStore {
suspend fun setUuid(uuid: String)

suspend fun setToken(token: String)

suspend fun clear()
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,4 +50,9 @@ class AppDataStoreImpl(
}
}
}

override suspend fun clear() {
setUuid("")
setToken("")
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@ package com.stslex.aproselection.core.network.clients.user
import com.stslex.aproselection.core.network.client.NetworkClient
import com.stslex.aproselection.core.network.clients.user.model.UpdateUserInfoBody
import com.stslex.aproselection.core.network.clients.user.model.UserResponse
import com.stslex.aproselection.core.network.model.PagingRequest
import io.ktor.client.call.body
import io.ktor.client.request.get
import io.ktor.client.request.post
import io.ktor.client.request.setBody
import io.ktor.http.appendPathSegments
import io.ktor.util.AttributeKey
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext

Expand All @@ -22,12 +22,10 @@ class UserNetworkClientImpl(
): List<UserResponse> = withContext(Dispatchers.IO) {
networkClient.apiClient.get {
url.appendPathSegments("user", "list")
setBody(
PagingRequest(
pageNumber = page,
pageSize = pageSize
)
)
setAttributes {
put(AttributeKey("page_size"), pageSize)
put(AttributeKey("page_number"), page)
}
}.body()
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,15 +1,33 @@
package com.stslex.aproselection.core.ui.base

import android.util.Log
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import androidx.paging.Pager
import androidx.paging.PagingData
import androidx.paging.cachedIn
import androidx.paging.map
import com.stslex.aproselection.core.core.Logger
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.SharingStarted
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.flowOn
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.flow.stateIn

open class BaseViewModel : ViewModel() {

inline fun <T : Any, R : Any> Pager<Int, T>.mapState(
crossinline transform: suspend (T) -> R
): StateFlow<PagingData<R>> = this
.flow
.map { pagingData ->
pagingData.map { item ->
transform(item)
}
}
.primaryPagingFlow

fun <T> Flow<T>.stateIn(
initialValue: T
): StateFlow<T> = this.stateIn(
Expand All @@ -18,7 +36,17 @@ open class BaseViewModel : ViewModel() {
initialValue = initialValue
)

val <T : Any> Flow<PagingData<T>>.primaryPagingFlow: StateFlow<PagingData<T>>
get() = cachedIn(viewModelScope)
.makeStateFlow(PagingData.empty())

private fun <T : Any> Flow<T>.makeStateFlow(initialValue: T): StateFlow<T> =
flowOn(Dispatchers.IO)
.stateIn(
initialValue = initialValue
)

fun handleError(throwable: Throwable) {
Log.e(javaClass.simpleName, throwable.message, throwable)
Logger.exception(throwable)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ object AppDimens {
val small = 8.dp
val medium = 16.dp
val big = 32.dp
val large = 64.dp
}

object Corners {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package com.stslex.aproselection.core.user.data.model

data class UserData(
val uuid: String,
val username: String,
val nickname: String
)
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package com.stslex.aproselection.core.user.data.model

import com.stslex.aproselection.core.network.clients.user.model.UpdateUserInfoBody
import com.stslex.aproselection.core.network.clients.user.model.UserResponse

fun List<UserResponse>.toData() = map { user ->
user.toData()
}

fun UserResponse.toData() = UserData(
uuid = uuid,
username = username,
nickname = nickname
)

fun UserUpdateData.toBody() = UpdateUserInfoBody(nickname)
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
package com.stslex.aproselection.core.user.data.model

data class UserUpdateData(
val nickname: String
)
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package com.stslex.aproselection.core.user.data.repository

import com.stslex.aproselection.core.network.clients.user.model.UpdateUserInfoBody
import com.stslex.aproselection.core.user.data.model.UserData
import com.stslex.aproselection.core.user.data.model.UserUpdateData

interface UserRepository {

suspend fun getUserList(page: Int, pageSize: Int): List<UserData>

suspend fun getUser(uuid: String): UserData

suspend fun updateUserInfo(info: UserUpdateData): UserData
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
package com.stslex.aproselection.core.user.data.repository

import com.stslex.aproselection.core.network.clients.user.UserNetworkClient
import com.stslex.aproselection.core.user.data.model.UserData
import com.stslex.aproselection.core.user.data.model.UserUpdateData
import com.stslex.aproselection.core.user.data.model.toBody
import com.stslex.aproselection.core.user.data.model.toData

class UserRepositoryImpl(
private val networkClient: UserNetworkClient
) : UserRepository {

override suspend fun getUserList(
page: Int,
pageSize: Int
): List<UserData> = networkClient
.getUserList(
page = page,
pageSize = pageSize
).toData()

override suspend fun getUser(
uuid: String
): UserData = networkClient.getUser(uuid).toData()

override suspend fun updateUserInfo(
info: UserUpdateData
): UserData = networkClient.updateUserInfo(info.toBody()).toData()
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package com.stslex.aproselection.core.user.di

import com.stslex.aproselection.core.user.data.repository.UserRepository
import com.stslex.aproselection.core.user.data.repository.UserRepositoryImpl
import org.koin.core.module.dsl.bind
import org.koin.core.module.dsl.singleOf
import org.koin.dsl.module

val moduleCoreUser = module {
singleOf(::UserRepositoryImpl) { bind<UserRepository>() }
}
Original file line number Diff line number Diff line change
@@ -1,9 +1,14 @@
package com.stslex.aproselection.feature.home.di

import com.stslex.aproselection.feature.home.domain.HomeInteractor
import com.stslex.aproselection.feature.home.domain.HomeInteractorImpl
import com.stslex.aproselection.feature.home.ui.HomeViewModel
import org.koin.androidx.viewmodel.dsl.viewModelOf
import org.koin.core.module.dsl.bind
import org.koin.core.module.dsl.singleOf
import org.koin.dsl.module

val moduleFeatureHome = module {
viewModelOf(::HomeViewModel)
singleOf(::HomeInteractorImpl) { bind<HomeInteractor>() }
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,9 @@ package com.stslex.aproselection.feature.home.domain

import com.stslex.aproselection.feature.home.domain.model.UserDomain

interface HomeScreenInteractor {
interface HomeInteractor {

suspend fun getAllUsers(page: Int, pageSize: Int): List<UserDomain>

suspend fun logOut()
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package com.stslex.aproselection.feature.home.domain

import com.stslex.aproselection.core.datastore.AppDataStore
import com.stslex.aproselection.core.user.data.repository.UserRepository
import com.stslex.aproselection.feature.home.domain.model.UserDomain
import com.stslex.aproselection.feature.home.domain.model.toDomain

class HomeInteractorImpl(
private val repository: UserRepository,
private val appDataStore: AppDataStore,
) : HomeInteractor {

override suspend fun getAllUsers(
page: Int,
pageSize: Int
): List<UserDomain> = repository
.getUserList(
page = page,
pageSize = pageSize
)
.map { user ->
user.toDomain()
}

override suspend fun logOut() {
appDataStore.clear()
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package com.stslex.aproselection.feature.home.domain.model

import com.stslex.aproselection.core.user.data.model.UserData

fun UserData.toDomain() = UserDomain(
uuid = uuid,
username = username,
nickname = nickname
)
Loading

0 comments on commit d024e25

Please sign in to comment.