mirror of
https://github.com/bitwarden/android.git
synced 2024-11-24 18:36:32 +03:00
BIT-289 Remove deprecated BitwardenTextField (#53)
This commit is contained in:
parent
4a49781ae1
commit
dd2ad70b52
5 changed files with 261 additions and 52 deletions
|
@ -12,6 +12,8 @@ import androidx.compose.foundation.layout.padding
|
||||||
import androidx.compose.material3.MaterialTheme
|
import androidx.compose.material3.MaterialTheme
|
||||||
import androidx.compose.material3.Text
|
import androidx.compose.material3.Text
|
||||||
import androidx.compose.runtime.Composable
|
import androidx.compose.runtime.Composable
|
||||||
|
import androidx.compose.runtime.collectAsState
|
||||||
|
import androidx.compose.runtime.getValue
|
||||||
import androidx.compose.ui.Alignment
|
import androidx.compose.ui.Alignment
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
import androidx.compose.ui.platform.LocalContext
|
import androidx.compose.ui.platform.LocalContext
|
||||||
|
@ -19,16 +21,23 @@ import androidx.compose.ui.res.stringResource
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import androidx.hilt.navigation.compose.hiltViewModel
|
import androidx.hilt.navigation.compose.hiltViewModel
|
||||||
import com.x8bit.bitwarden.R
|
import com.x8bit.bitwarden.R
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.ConfirmPasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.EmailInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordHintChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.SubmitClick
|
||||||
import com.x8bit.bitwarden.ui.platform.base.util.EventsEffect
|
import com.x8bit.bitwarden.ui.platform.base.util.EventsEffect
|
||||||
import com.x8bit.bitwarden.ui.platform.components.BitwardenTextField
|
import com.x8bit.bitwarden.ui.platform.components.BitwardenTextField
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Top level composable for the create account screen.
|
* Top level composable for the create account screen.
|
||||||
*/
|
*/
|
||||||
|
@Suppress("LongMethod")
|
||||||
@Composable
|
@Composable
|
||||||
fun CreateAccountScreen(
|
fun CreateAccountScreen(
|
||||||
viewModel: CreateAccountViewModel = hiltViewModel(),
|
viewModel: CreateAccountViewModel = hiltViewModel(),
|
||||||
) {
|
) {
|
||||||
|
val state by viewModel.stateFlow.collectAsState()
|
||||||
val context = LocalContext.current
|
val context = LocalContext.current
|
||||||
EventsEffect(viewModel) { event ->
|
EventsEffect(viewModel) { event ->
|
||||||
when (event) {
|
when (event) {
|
||||||
|
@ -61,7 +70,7 @@ fun CreateAccountScreen(
|
||||||
Text(
|
Text(
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.clickable {
|
.clickable {
|
||||||
viewModel.trySendAction(CreateAccountAction.SubmitClick)
|
viewModel.trySendAction(SubmitClick)
|
||||||
}
|
}
|
||||||
.padding(16.dp),
|
.padding(16.dp),
|
||||||
text = stringResource(id = R.string.submit),
|
text = stringResource(id = R.string.submit),
|
||||||
|
@ -69,9 +78,25 @@ fun CreateAccountScreen(
|
||||||
style = MaterialTheme.typography.bodyMedium,
|
style = MaterialTheme.typography.bodyMedium,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
BitwardenTextField(label = stringResource(id = R.string.email_address))
|
BitwardenTextField(
|
||||||
BitwardenTextField(label = stringResource(id = R.string.master_password))
|
label = stringResource(id = R.string.email_address),
|
||||||
BitwardenTextField(label = stringResource(id = R.string.retype_master_password))
|
value = state.emailInput,
|
||||||
BitwardenTextField(label = stringResource(id = R.string.master_password_hint))
|
onValueChange = { viewModel.trySendAction(EmailInputChange(it)) },
|
||||||
|
)
|
||||||
|
BitwardenTextField(
|
||||||
|
label = stringResource(id = R.string.master_password),
|
||||||
|
value = state.passwordInput,
|
||||||
|
onValueChange = { viewModel.trySendAction(PasswordInputChange(it)) },
|
||||||
|
)
|
||||||
|
BitwardenTextField(
|
||||||
|
label = stringResource(id = R.string.retype_master_password),
|
||||||
|
value = state.confirmPasswordInput,
|
||||||
|
onValueChange = { viewModel.trySendAction(ConfirmPasswordInputChange(it)) },
|
||||||
|
)
|
||||||
|
BitwardenTextField(
|
||||||
|
label = stringResource(id = R.string.master_password_hint),
|
||||||
|
value = state.passwordHintInput,
|
||||||
|
onValueChange = { viewModel.trySendAction(PasswordHintChange(it)) },
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,24 +1,72 @@
|
||||||
package com.x8bit.bitwarden.ui.auth.feature.createaccount
|
package com.x8bit.bitwarden.ui.auth.feature.createaccount
|
||||||
|
|
||||||
|
import android.os.Parcelable
|
||||||
|
import androidx.lifecycle.SavedStateHandle
|
||||||
|
import androidx.lifecycle.viewModelScope
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.ConfirmPasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.EmailInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordHintChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.SubmitClick
|
||||||
import com.x8bit.bitwarden.ui.platform.base.BaseViewModel
|
import com.x8bit.bitwarden.ui.platform.base.BaseViewModel
|
||||||
import dagger.hilt.android.lifecycle.HiltViewModel
|
import dagger.hilt.android.lifecycle.HiltViewModel
|
||||||
|
import kotlinx.coroutines.flow.launchIn
|
||||||
|
import kotlinx.coroutines.flow.onEach
|
||||||
|
import kotlinx.coroutines.flow.update
|
||||||
|
import kotlinx.parcelize.Parcelize
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
private const val KEY_STATE = "state"
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Models logic for the create account screen.
|
* Models logic for the create account screen.
|
||||||
*/
|
*/
|
||||||
@HiltViewModel
|
@HiltViewModel
|
||||||
class CreateAccountViewModel @Inject constructor() :
|
class CreateAccountViewModel @Inject constructor(
|
||||||
BaseViewModel<CreateAccountState, CreateAccountEvent, CreateAccountAction>(
|
savedStateHandle: SavedStateHandle,
|
||||||
initialState = CreateAccountState,
|
) : BaseViewModel<CreateAccountState, CreateAccountEvent, CreateAccountAction>(
|
||||||
|
initialState = savedStateHandle[KEY_STATE]
|
||||||
|
?: CreateAccountState(
|
||||||
|
emailInput = "",
|
||||||
|
passwordInput = "",
|
||||||
|
confirmPasswordInput = "",
|
||||||
|
passwordHintInput = "",
|
||||||
|
),
|
||||||
) {
|
) {
|
||||||
|
|
||||||
|
init {
|
||||||
|
// As state updates, write to saved state handle:
|
||||||
|
stateFlow
|
||||||
|
.onEach { savedStateHandle[KEY_STATE] = it }
|
||||||
|
.launchIn(viewModelScope)
|
||||||
|
}
|
||||||
|
|
||||||
override fun handleAction(action: CreateAccountAction) {
|
override fun handleAction(action: CreateAccountAction) {
|
||||||
when (action) {
|
when (action) {
|
||||||
is CreateAccountAction.SubmitClick -> handleSubmitClick()
|
is SubmitClick -> handleSubmitClick()
|
||||||
|
is ConfirmPasswordInputChange -> handleConfirmPasswordInputChanged(action)
|
||||||
|
is EmailInputChange -> handleEmailInputChanged(action)
|
||||||
|
is PasswordHintChange -> handlePasswordHintChanged(action)
|
||||||
|
is PasswordInputChange -> handlePasswordInputChanged(action)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun handleEmailInputChanged(action: EmailInputChange) {
|
||||||
|
mutableStateFlow.update { it.copy(emailInput = action.input) }
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun handlePasswordHintChanged(action: PasswordHintChange) {
|
||||||
|
mutableStateFlow.update { it.copy(passwordHintInput = action.input) }
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun handlePasswordInputChanged(action: PasswordInputChange) {
|
||||||
|
mutableStateFlow.update { it.copy(passwordInput = action.input) }
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun handleConfirmPasswordInputChanged(action: ConfirmPasswordInputChange) {
|
||||||
|
mutableStateFlow.update { it.copy(confirmPasswordInput = action.input) }
|
||||||
|
}
|
||||||
|
|
||||||
private fun handleSubmitClick() {
|
private fun handleSubmitClick() {
|
||||||
sendEvent(CreateAccountEvent.ShowToast("TODO: Handle Submit Click"))
|
sendEvent(CreateAccountEvent.ShowToast("TODO: Handle Submit Click"))
|
||||||
}
|
}
|
||||||
|
@ -27,7 +75,13 @@ class CreateAccountViewModel @Inject constructor() :
|
||||||
/**
|
/**
|
||||||
* UI state for the create account screen.
|
* UI state for the create account screen.
|
||||||
*/
|
*/
|
||||||
data object CreateAccountState
|
@Parcelize
|
||||||
|
data class CreateAccountState(
|
||||||
|
val emailInput: String,
|
||||||
|
val passwordInput: String,
|
||||||
|
val confirmPasswordInput: String,
|
||||||
|
val passwordHintInput: String,
|
||||||
|
) : Parcelable
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Models events for the create account screen.
|
* Models events for the create account screen.
|
||||||
|
@ -48,4 +102,24 @@ sealed class CreateAccountAction {
|
||||||
* User clicked submit.
|
* User clicked submit.
|
||||||
*/
|
*/
|
||||||
data object SubmitClick : CreateAccountAction()
|
data object SubmitClick : CreateAccountAction()
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Email input changed.
|
||||||
|
*/
|
||||||
|
data class EmailInputChange(val input: String) : CreateAccountAction()
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Password input changed.
|
||||||
|
*/
|
||||||
|
data class PasswordInputChange(val input: String) : CreateAccountAction()
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Confirm password input changed.
|
||||||
|
*/
|
||||||
|
data class ConfirmPasswordInputChange(val input: String) : CreateAccountAction()
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Password hint input changed.
|
||||||
|
*/
|
||||||
|
data class PasswordHintChange(val input: String) : CreateAccountAction()
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,46 +5,9 @@ import androidx.compose.foundation.layout.padding
|
||||||
import androidx.compose.material3.Text
|
import androidx.compose.material3.Text
|
||||||
import androidx.compose.material3.TextField
|
import androidx.compose.material3.TextField
|
||||||
import androidx.compose.runtime.Composable
|
import androidx.compose.runtime.Composable
|
||||||
import androidx.compose.runtime.getValue
|
|
||||||
import androidx.compose.runtime.mutableStateOf
|
|
||||||
import androidx.compose.runtime.remember
|
|
||||||
import androidx.compose.runtime.setValue
|
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
|
|
||||||
/**
|
|
||||||
* Component that allows the user to input text. This composable will manage the state of
|
|
||||||
* the user's input.
|
|
||||||
*
|
|
||||||
* @param label label for the text field.
|
|
||||||
* @param initialValue initial input text.
|
|
||||||
* @param onTextChange callback that is triggered when the input of the text field changes.
|
|
||||||
*
|
|
||||||
* TODO: remove deprecated version: BIT-289
|
|
||||||
*/
|
|
||||||
@Deprecated(
|
|
||||||
message = "Use overloaded BitwardenTextField that takes an input instead of an initialText.",
|
|
||||||
)
|
|
||||||
@Composable
|
|
||||||
fun BitwardenTextField(
|
|
||||||
label: String,
|
|
||||||
initialValue: String = "",
|
|
||||||
onTextChange: (String) -> Unit = {},
|
|
||||||
) {
|
|
||||||
var input by remember { mutableStateOf(initialValue) }
|
|
||||||
TextField(
|
|
||||||
modifier = Modifier
|
|
||||||
.fillMaxWidth()
|
|
||||||
.padding(horizontal = 16.dp),
|
|
||||||
label = { Text(text = label) },
|
|
||||||
value = input,
|
|
||||||
onValueChange = {
|
|
||||||
input = it
|
|
||||||
onTextChange.invoke(it)
|
|
||||||
},
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Component that allows the user to input text. This composable will manage the state of
|
* Component that allows the user to input text. This composable will manage the state of
|
||||||
* the user's input.
|
* the user's input.
|
||||||
|
|
|
@ -2,10 +2,17 @@ package com.x8bit.bitwarden.ui.auth.feature.createaccount
|
||||||
|
|
||||||
import androidx.compose.ui.test.onNodeWithText
|
import androidx.compose.ui.test.onNodeWithText
|
||||||
import androidx.compose.ui.test.performClick
|
import androidx.compose.ui.test.performClick
|
||||||
|
import androidx.compose.ui.test.performTextInput
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.ConfirmPasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.EmailInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordHintChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.SubmitClick
|
||||||
import com.x8bit.bitwarden.ui.platform.base.BaseComposeTest
|
import com.x8bit.bitwarden.ui.platform.base.BaseComposeTest
|
||||||
import io.mockk.every
|
import io.mockk.every
|
||||||
import io.mockk.mockk
|
import io.mockk.mockk
|
||||||
import io.mockk.verify
|
import io.mockk.verify
|
||||||
|
import kotlinx.coroutines.flow.MutableStateFlow
|
||||||
import kotlinx.coroutines.flow.emptyFlow
|
import kotlinx.coroutines.flow.emptyFlow
|
||||||
import org.junit.Test
|
import org.junit.Test
|
||||||
|
|
||||||
|
@ -14,13 +21,82 @@ class CreateAccountScreenTest : BaseComposeTest() {
|
||||||
@Test
|
@Test
|
||||||
fun `submit click should send SubmitClick action`() {
|
fun `submit click should send SubmitClick action`() {
|
||||||
val viewModel = mockk<CreateAccountViewModel>(relaxed = true) {
|
val viewModel = mockk<CreateAccountViewModel>(relaxed = true) {
|
||||||
|
every { stateFlow } returns MutableStateFlow(DEFAULT_STATE)
|
||||||
every { eventFlow } returns emptyFlow()
|
every { eventFlow } returns emptyFlow()
|
||||||
every { trySendAction(CreateAccountAction.SubmitClick) } returns Unit
|
every { trySendAction(SubmitClick) } returns Unit
|
||||||
}
|
}
|
||||||
composeTestRule.setContent {
|
composeTestRule.setContent {
|
||||||
CreateAccountScreen(viewModel)
|
CreateAccountScreen(viewModel)
|
||||||
}
|
}
|
||||||
composeTestRule.onNodeWithText("Submit").performClick()
|
composeTestRule.onNodeWithText("Submit").performClick()
|
||||||
verify { viewModel.trySendAction(CreateAccountAction.SubmitClick) }
|
verify { viewModel.trySendAction(SubmitClick) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `email input change should send EmailInputChange action`() {
|
||||||
|
val viewModel = mockk<CreateAccountViewModel>(relaxed = true) {
|
||||||
|
every { stateFlow } returns MutableStateFlow(DEFAULT_STATE)
|
||||||
|
every { eventFlow } returns emptyFlow()
|
||||||
|
every { trySendAction(EmailInputChange("input")) } returns Unit
|
||||||
|
}
|
||||||
|
composeTestRule.setContent {
|
||||||
|
CreateAccountScreen(viewModel)
|
||||||
|
}
|
||||||
|
composeTestRule.onNodeWithText("Email address").performTextInput(TEST_INPUT)
|
||||||
|
verify { viewModel.trySendAction(EmailInputChange(TEST_INPUT)) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `password input change should send PasswordInputChange action`() {
|
||||||
|
val viewModel = mockk<CreateAccountViewModel>(relaxed = true) {
|
||||||
|
every { stateFlow } returns MutableStateFlow(DEFAULT_STATE)
|
||||||
|
every { eventFlow } returns emptyFlow()
|
||||||
|
every { trySendAction(PasswordInputChange("input")) } returns Unit
|
||||||
|
}
|
||||||
|
composeTestRule.setContent {
|
||||||
|
CreateAccountScreen(viewModel)
|
||||||
|
}
|
||||||
|
composeTestRule.onNodeWithText("Master password").performTextInput(TEST_INPUT)
|
||||||
|
verify { viewModel.trySendAction(PasswordInputChange(TEST_INPUT)) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `confirm password input change should send ConfirmPasswordInputChange action`() {
|
||||||
|
val viewModel = mockk<CreateAccountViewModel>(relaxed = true) {
|
||||||
|
every { stateFlow } returns MutableStateFlow(DEFAULT_STATE)
|
||||||
|
every { eventFlow } returns emptyFlow()
|
||||||
|
every { trySendAction(ConfirmPasswordInputChange("input")) } returns Unit
|
||||||
|
}
|
||||||
|
composeTestRule.setContent {
|
||||||
|
CreateAccountScreen(viewModel)
|
||||||
|
}
|
||||||
|
composeTestRule.onNodeWithText("Re-type master password").performTextInput(TEST_INPUT)
|
||||||
|
verify { viewModel.trySendAction(ConfirmPasswordInputChange(TEST_INPUT)) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `password hint input change should send PasswordHintChange action`() {
|
||||||
|
val viewModel = mockk<CreateAccountViewModel>(relaxed = true) {
|
||||||
|
every { stateFlow } returns MutableStateFlow(DEFAULT_STATE)
|
||||||
|
every { eventFlow } returns emptyFlow()
|
||||||
|
every { trySendAction(PasswordHintChange("input")) } returns Unit
|
||||||
|
}
|
||||||
|
composeTestRule.setContent {
|
||||||
|
CreateAccountScreen(viewModel)
|
||||||
|
}
|
||||||
|
composeTestRule
|
||||||
|
.onNodeWithText("Master password hint (optional)")
|
||||||
|
.performTextInput(TEST_INPUT)
|
||||||
|
verify { viewModel.trySendAction(PasswordHintChange(TEST_INPUT)) }
|
||||||
|
}
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
private const val TEST_INPUT = "input"
|
||||||
|
private val DEFAULT_STATE = CreateAccountState(
|
||||||
|
emailInput = "",
|
||||||
|
passwordInput = "",
|
||||||
|
confirmPasswordInput = "",
|
||||||
|
passwordHintInput = "",
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,18 +1,89 @@
|
||||||
package com.x8bit.bitwarden.ui.auth.feature.createaccount
|
package com.x8bit.bitwarden.ui.auth.feature.createaccount
|
||||||
|
|
||||||
|
import androidx.lifecycle.SavedStateHandle
|
||||||
import app.cash.turbine.test
|
import app.cash.turbine.test
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.ConfirmPasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.EmailInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordHintChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.PasswordInputChange
|
||||||
|
import com.x8bit.bitwarden.ui.auth.feature.createaccount.CreateAccountAction.SubmitClick
|
||||||
import com.x8bit.bitwarden.ui.platform.base.BaseViewModelTest
|
import com.x8bit.bitwarden.ui.platform.base.BaseViewModelTest
|
||||||
import kotlinx.coroutines.test.runTest
|
import kotlinx.coroutines.test.runTest
|
||||||
|
import org.junit.jupiter.api.Assertions.assertEquals
|
||||||
import org.junit.jupiter.api.Test
|
import org.junit.jupiter.api.Test
|
||||||
|
|
||||||
class CreateAccountViewModelTest : BaseViewModelTest() {
|
class CreateAccountViewModelTest : BaseViewModelTest() {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `initial state should be correct`() {
|
||||||
|
val viewModel = CreateAccountViewModel(SavedStateHandle())
|
||||||
|
assertEquals(DEFAULT_STATE, viewModel.stateFlow.value)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `initial state should pull from saved state handle when present`() {
|
||||||
|
val savedState = CreateAccountState(
|
||||||
|
emailInput = "email",
|
||||||
|
passwordInput = "password",
|
||||||
|
confirmPasswordInput = "confirmPassword",
|
||||||
|
passwordHintInput = "hint",
|
||||||
|
)
|
||||||
|
val handle = SavedStateHandle(mapOf("state" to savedState))
|
||||||
|
val viewModel = CreateAccountViewModel(handle)
|
||||||
|
assertEquals(savedState, viewModel.stateFlow.value)
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun `SubmitClick should emit ShowToast`() = runTest {
|
fun `SubmitClick should emit ShowToast`() = runTest {
|
||||||
val viewModel = CreateAccountViewModel()
|
val viewModel = CreateAccountViewModel(SavedStateHandle())
|
||||||
viewModel.eventFlow.test {
|
viewModel.eventFlow.test {
|
||||||
viewModel.actionChannel.trySend(CreateAccountAction.SubmitClick)
|
viewModel.actionChannel.trySend(SubmitClick)
|
||||||
assert(awaitItem() is CreateAccountEvent.ShowToast)
|
assert(awaitItem() is CreateAccountEvent.ShowToast)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `ConfirmPasswordInputChange update passwordInput`() = runTest {
|
||||||
|
val viewModel = CreateAccountViewModel(SavedStateHandle())
|
||||||
|
viewModel.actionChannel.trySend(ConfirmPasswordInputChange("input"))
|
||||||
|
viewModel.stateFlow.test {
|
||||||
|
assertEquals(DEFAULT_STATE.copy(confirmPasswordInput = "input"), awaitItem())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `EmailInputChange update passwordInput`() = runTest {
|
||||||
|
val viewModel = CreateAccountViewModel(SavedStateHandle())
|
||||||
|
viewModel.actionChannel.trySend(EmailInputChange("input"))
|
||||||
|
viewModel.stateFlow.test {
|
||||||
|
assertEquals(DEFAULT_STATE.copy(emailInput = "input"), awaitItem())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `PasswordHintChange update passwordInput`() = runTest {
|
||||||
|
val viewModel = CreateAccountViewModel(SavedStateHandle())
|
||||||
|
viewModel.actionChannel.trySend(PasswordHintChange("input"))
|
||||||
|
viewModel.stateFlow.test {
|
||||||
|
assertEquals(DEFAULT_STATE.copy(passwordHintInput = "input"), awaitItem())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `PasswordInputChange update passwordInput`() = runTest {
|
||||||
|
val viewModel = CreateAccountViewModel(SavedStateHandle())
|
||||||
|
viewModel.actionChannel.trySend(PasswordInputChange("input"))
|
||||||
|
viewModel.stateFlow.test {
|
||||||
|
assertEquals(DEFAULT_STATE.copy(passwordInput = "input"), awaitItem())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
private val DEFAULT_STATE = CreateAccountState(
|
||||||
|
passwordInput = "",
|
||||||
|
emailInput = "",
|
||||||
|
confirmPasswordInput = "",
|
||||||
|
passwordHintInput = "",
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue