diff --git a/WordPress/src/test/java/org/wordpress/android/viewmodel/main/WPMainActivityViewModelTest.kt b/WordPress/src/test/java/org/wordpress/android/viewmodel/main/WPMainActivityViewModelTest.kt index 68f9e62a6174..a6c81d98b44c 100644 --- a/WordPress/src/test/java/org/wordpress/android/viewmodel/main/WPMainActivityViewModelTest.kt +++ b/WordPress/src/test/java/org/wordpress/android/viewmodel/main/WPMainActivityViewModelTest.kt @@ -35,21 +35,22 @@ import org.wordpress.android.fluxc.store.QuickStartStore.QuickStartTask import org.wordpress.android.fluxc.store.SiteStore import org.wordpress.android.fluxc.store.bloggingprompts.BloggingPromptsStore import org.wordpress.android.fluxc.store.bloggingprompts.BloggingPromptsStore.BloggingPromptsResult -import org.wordpress.android.ui.bloggingprompts.BloggingPromptsSettingsHelper import org.wordpress.android.ui.main.MainActionListItem.ActionType.ANSWER_BLOGGING_PROMPT import org.wordpress.android.ui.main.MainActionListItem.ActionType.CREATE_NEW_PAGE import org.wordpress.android.ui.main.MainActionListItem.ActionType.CREATE_NEW_POST +import org.wordpress.android.ui.main.MainActionListItem.ActionType.CREATE_NEW_POST_FROM_AUDIO import org.wordpress.android.ui.main.MainActionListItem.ActionType.NO_ACTION import org.wordpress.android.ui.main.MainActionListItem.AnswerBloggingPromptAction import org.wordpress.android.ui.main.MainActionListItem.CreateAction import org.wordpress.android.ui.main.MainFabUiState +import org.wordpress.android.ui.main.WPMainNavigationView.PageType +import org.wordpress.android.ui.main.utils.MainCreateSheetHelper import org.wordpress.android.ui.mysite.SelectedSiteRepository import org.wordpress.android.ui.mysite.cards.dashboard.bloggingprompts.BloggingPromptAttribution import org.wordpress.android.ui.mysite.cards.quickstart.QuickStartRepository import org.wordpress.android.ui.prefs.AppPrefsWrapper import org.wordpress.android.ui.prefs.privacy.banner.domain.ShouldAskPrivacyConsent import org.wordpress.android.ui.quickstart.QuickStartType -import org.wordpress.android.ui.voicetocontent.VoiceToContentFeatureUtils import org.wordpress.android.ui.whatsnew.FeatureAnnouncement import org.wordpress.android.ui.whatsnew.FeatureAnnouncementItem import org.wordpress.android.ui.whatsnew.FeatureAnnouncementProvider @@ -95,9 +96,6 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Mock lateinit var siteStore: SiteStore - @Mock - lateinit var bloggingPromptsSettingsHelper: BloggingPromptsSettingsHelper - @Mock lateinit var bloggingPromptsStore: BloggingPromptsStore @@ -111,7 +109,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { private lateinit var shouldAskPrivacyConsent: ShouldAskPrivacyConsent @Mock - private lateinit var voiceToContentFeatureUtils: VoiceToContentFeatureUtils + private lateinit var mainCreateSheetHelper: MainCreateSheetHelper private val featureAnnouncement = FeatureAnnouncement( "14.7", @@ -157,10 +155,10 @@ class WPMainActivityViewModelTest : BaseUnitTest() { activeTask = MutableLiveData() externalFocusPointEvents = mutableListOf() whenever(quickStartRepository.activeTask).thenReturn(activeTask) - whenever(bloggingPromptsSettingsHelper.shouldShowPromptsFeature()).thenReturn(false) whenever(bloggingPromptsStore.getPromptForDate(any(), any())).thenReturn(flowOf(bloggingPrompt)) whenever(shouldAskPrivacyConsent()).thenReturn(false) - whenever(voiceToContentFeatureUtils.isVoiceToContentEnabled()).thenReturn(false) + whenever(mainCreateSheetHelper.canCreatePost()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(false) viewModel = WPMainActivityViewModel( featureAnnouncementProvider, buildConfigWrapper, @@ -170,11 +168,10 @@ class WPMainActivityViewModelTest : BaseUnitTest() { selectedSiteRepository, accountStore, siteStore, - bloggingPromptsSettingsHelper, bloggingPromptsStore, NoDelayCoroutineDispatcher(), shouldAskPrivacyConsent, - voiceToContentFeatureUtils + mainCreateSheetHelper, ) viewModel.onFeatureAnnouncementRequested.observeForever( onFeatureAnnouncementRequestedObserver @@ -195,73 +192,41 @@ class WPMainActivityViewModelTest : BaseUnitTest() { /* FAB VISIBILITY */ @Test - fun `given fab enabled, when page changed to my site, then fab is visible`() { + fun `given fab enabled and page changed to supported page, then fab is visible`() { startViewModelWithDefaultParameters() + whenever(mainCreateSheetHelper.shouldShowFabForPage(any())).thenReturn(true) - viewModel.onPageChanged(isOnMySitePageWithValidSite = true, site = initSite(hasFullAccessToContent = true)) + viewModel.onPageChanged(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = mock()) assertThat(fabUiState?.isFabVisible).isTrue } @Test - fun `given fab enabled, when page changed away from my site, then fab is hidden`() { + fun `given fab disabled or page changed to non-supported page, then fab is hidden`() { startViewModelWithDefaultParameters() + whenever(mainCreateSheetHelper.shouldShowFabForPage(any())).thenReturn(false) - viewModel.onPageChanged(isOnMySitePageWithValidSite = false, site = initSite(hasFullAccessToContent = true)) + viewModel.onPageChanged(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = mock()) - assertThat(fabUiState?.isFabVisible).isFalse + assertThat(fabUiState?.isFabVisible).isFalse() } @Test - fun `given fab enabled, when my site page is resumed, then fab is visible`() { + fun `given fab enabled and supported page is resumed, then fab is visible`() { startViewModelWithDefaultParameters() + whenever(mainCreateSheetHelper.shouldShowFabForPage(any())).thenReturn(true) - viewModel.onResume(isOnMySitePageWithValidSite = true, site = initSite(hasFullAccessToContent = true)) + viewModel.onResume(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = mock()) assertThat(fabUiState?.isFabVisible).isTrue } @Test - fun `given fab enabled, when non my site page is resumed, then fab is hidden`() { + fun `given fab disabled or non-supported page is resumed, then fab is hidden`() { startViewModelWithDefaultParameters() + whenever(mainCreateSheetHelper.shouldShowFabForPage(any())).thenReturn(false) - viewModel.onResume(isOnMySitePageWithValidSite = false, site = initSite(hasFullAccessToContent = true)) - - assertThat(fabUiState?.isFabVisible).isFalse - } - - @Test - fun `given fab disabled, when page changed to my site, then fab is hidden`() { - startViewModelWithDefaultParameters(isCreateFabEnabled = false) - - viewModel.onPageChanged(isOnMySitePageWithValidSite = true, site = initSite(hasFullAccessToContent = true)) - - assertThat(fabUiState?.isFabVisible).isFalse - } - - @Test - fun `given fab disabled, when page changed away from my site, then fab is hidden`() { - startViewModelWithDefaultParameters(isCreateFabEnabled = false) - - viewModel.onPageChanged(isOnMySitePageWithValidSite = false, site = initSite(hasFullAccessToContent = true)) - - assertThat(fabUiState?.isFabVisible).isFalse - } - - @Test - fun `given fab disabled, when my site page is resumed, then fab is hidden`() { - startViewModelWithDefaultParameters(isCreateFabEnabled = false) - - viewModel.onResume(isOnMySitePageWithValidSite = true, site = initSite(hasFullAccessToContent = true)) - - assertThat(fabUiState?.isFabVisible).isFalse - } - - @Test - fun `given fab disabled, when non my site page is resumed, then fab is hidden`() { - startViewModelWithDefaultParameters(isCreateFabEnabled = false) - - viewModel.onResume(isOnMySitePageWithValidSite = false, site = initSite(hasFullAccessToContent = true)) + viewModel.onResume(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = mock()) assertThat(fabUiState?.isFabVisible).isFalse } @@ -269,8 +234,10 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `fab focus point visible when active task is PUBLISH_POST`() { startViewModelWithDefaultParameters() + whenever(mainCreateSheetHelper.shouldShowFabForPage(any())).thenReturn(true) + activeTask.value = PUBLISH_POST - viewModel.onPageChanged(isOnMySitePageWithValidSite = true, site = initSite(hasFullAccessToContent = true)) + viewModel.onPageChanged(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = mock()) assertThat(fabUiState?.isFocusPointVisible).isTrue } @@ -279,7 +246,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { fun `fab focus point gone when active task is different`() { startViewModelWithDefaultParameters() activeTask.value = UPDATE_SITE_TITLE - viewModel.onPageChanged(isOnMySitePageWithValidSite = true, site = initSite(hasFullAccessToContent = true)) + viewModel.onPageChanged(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = mock()) assertThat(fabUiState?.isFocusPointVisible).isFalse } @@ -288,7 +255,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { fun `fab focus point gone when active task is null`() { startViewModelWithDefaultParameters() activeTask.value = null - viewModel.onPageChanged(isOnMySitePageWithValidSite = true, site = initSite(hasFullAccessToContent = true)) + viewModel.onPageChanged(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = mock()) assertThat(fabUiState?.isFocusPointVisible).isFalse } @@ -304,6 +271,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `bottom sheet action is new page when new page is tapped`() { + whenever(mainCreateSheetHelper.canCreatePage(any(), any())).thenReturn(true) startViewModelWithDefaultParameters() val action = viewModel.mainActions.value?.first { it.actionType == CREATE_NEW_PAGE } as CreateAction assertThat(action).isNotNull @@ -313,7 +281,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `bottom sheet does not show prompt card when prompts feature is not active`() = test { - whenever(bloggingPromptsSettingsHelper.shouldShowPromptsFeature()).thenReturn(false) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(false) startViewModelWithDefaultParameters() val hasBloggingPromptAction = viewModel.mainActions.value?.any { it.actionType == ANSWER_BLOGGING_PROMPT } assertThat(hasBloggingPromptAction).isFalse() @@ -321,7 +289,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `bottom sheet does show prompt card when prompts feature is active`() = test { - whenever(bloggingPromptsSettingsHelper.shouldShowPromptsFeature()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(true) startViewModelWithDefaultParameters() val hasBloggingPromptAction = viewModel.mainActions.value?.any { it.actionType == ANSWER_BLOGGING_PROMPT } assertThat(hasBloggingPromptAction).isTrue() @@ -329,7 +297,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `bottom sheet action is ANSWER_BLOGGING_PROMPT when the BP answer button is clicked`() = test { - whenever(bloggingPromptsSettingsHelper.shouldShowPromptsFeature()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(true) startViewModelWithDefaultParameters() val action = viewModel.mainActions.value?.firstOrNull { it.actionType == ANSWER_BLOGGING_PROMPT @@ -345,7 +313,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `bottom sheet does not show quick start focus point by default`() { startViewModelWithDefaultParameters() - viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true)) + viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true), page = PageType.MY_SITE) assertThat(viewModel.isBottomSheetShowing.value!!.peekContent()).isTrue assertThat(viewModel.mainActions.value?.any { it is CreateAction && it.showQuickStartFocusPoint }).isEqualTo( false @@ -356,7 +324,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { fun `CREATE_NEW_POST action in bottom sheet with active Quick Start completes task and hides the focus point`() { startViewModelWithDefaultParameters() activeTask.value = PUBLISH_POST - viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true)) + viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true), page = PageType.MY_SITE) assertThat(viewModel.isBottomSheetShowing.value!!.peekContent()).isTrue assertThat(viewModel.mainActions.value?.any { it is CreateAction && it.showQuickStartFocusPoint }).isEqualTo( true @@ -376,7 +344,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { fun `CREATE_NEW_POST action sets task as done in QuickStartRepository`() { startViewModelWithDefaultParameters() activeTask.value = PUBLISH_POST - viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true)) + viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true), page = PageType.MY_SITE) val action = viewModel.mainActions.value?.first { it.actionType == CREATE_NEW_POST } as CreateAction assertThat(action).isNotNull @@ -387,9 +355,11 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `actions that are not CREATE_NEW_POST will not complete quick start task`() { + whenever(mainCreateSheetHelper.canCreatePage(any(), any())).thenReturn(true) startViewModelWithDefaultParameters() + activeTask.value = PUBLISH_POST - viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true)) + viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true), page = PageType.MY_SITE) assertThat(viewModel.isBottomSheetShowing.value!!.peekContent()).isTrue assertThat(viewModel.mainActions.value?.any { it is CreateAction && it.showQuickStartFocusPoint }).isEqualTo( true @@ -407,15 +377,29 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `new post action is triggered from FAB when no full access to content if stories unavailable`() { startViewModelWithDefaultParameters() - viewModel.onFabClicked(site = initSite(hasFullAccessToContent = false, isWpcomOrJpSite = false)) + viewModel.onFabClicked( + site = initSite(hasFullAccessToContent = false, isWpcomOrJpSite = false), + page = PageType.MY_SITE + ) assertThat(viewModel.isBottomSheetShowing.value).isNull() assertThat(viewModel.createAction.value).isEqualTo(CREATE_NEW_POST) } @Test - fun `bottom sheet is visualized when user has full access to content and has all 3 options`() { + fun `bottom sheet is visualized when user has full access to content and has 2 options`() { + whenever(mainCreateSheetHelper.canCreatePage(any(), any())).thenReturn(false) startViewModelWithDefaultParameters() - viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true)) + viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true), page = PageType.MY_SITE) + assertThat(viewModel.createAction.value).isNull() + assertThat(viewModel.mainActions.value?.size).isEqualTo(2) // 1 option plus NO_ACTION, first in list + assertThat(viewModel.isBottomSheetShowing.value!!.peekContent()).isTrue + } + + @Test + fun `bottom sheet is visualized when user has full access to content and has 3 options`() { + whenever(mainCreateSheetHelper.canCreatePage(any(), any())).thenReturn(true) + startViewModelWithDefaultParameters() + viewModel.onFabClicked(site = initSite(hasFullAccessToContent = true), page = PageType.MY_SITE) assertThat(viewModel.createAction.value).isNull() assertThat(viewModel.mainActions.value?.size).isEqualTo(3) // 2 options plus NO_ACTION, first in list assertThat(viewModel.isBottomSheetShowing.value!!.peekContent()).isTrue @@ -606,10 +590,39 @@ class WPMainActivityViewModelTest : BaseUnitTest() { } @Test - fun `bottom sheet actions are sorted in the correct order`() { + fun `bottom sheet actions are sorted in the correct order when can create post only`() { + startViewModelWithDefaultParameters() + + val expectedOrder = listOf( + NO_ACTION, + CREATE_NEW_POST, + ) + + assertThat(viewModel.mainActions.value!!.map { it.actionType }).isEqualTo(expectedOrder) + } + + @Test + fun `bottom sheet actions are sorted in the correct order when can create post, and page`() { + whenever(mainCreateSheetHelper.canCreatePage(any(), any())).thenReturn(true) + startViewModelWithDefaultParameters() + + val expectedOrder = listOf( + NO_ACTION, + CREATE_NEW_POST, + CREATE_NEW_PAGE + ) + + assertThat(viewModel.mainActions.value!!.map { it.actionType }).isEqualTo(expectedOrder) + } + + @Test + fun `bottom sheet actions are sorted in the correct order when can create post, prompts, and page`() = test { + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePage(any(), any())).thenReturn(true) startViewModelWithDefaultParameters() val expectedOrder = listOf( + ANSWER_BLOGGING_PROMPT, NO_ACTION, CREATE_NEW_POST, CREATE_NEW_PAGE @@ -618,6 +631,25 @@ class WPMainActivityViewModelTest : BaseUnitTest() { assertThat(viewModel.mainActions.value!!.map { it.actionType }).isEqualTo(expectedOrder) } + @Test + fun `bottom sheet actions are sorted in the correct order when can create post, from audio, prompts, and page`() = + test { + whenever(mainCreateSheetHelper.canCreatePostFromAudio(any())).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePage(any(), any())).thenReturn(true) + startViewModelWithDefaultParameters() + + val expectedOrder = listOf( + ANSWER_BLOGGING_PROMPT, + NO_ACTION, + CREATE_NEW_POST, + CREATE_NEW_POST_FROM_AUDIO, + CREATE_NEW_PAGE + ) + + assertThat(viewModel.mainActions.value!!.map { it.actionType }).isEqualTo(expectedOrder) + } + @Test fun `hasMultipleSites should be true when there are more than one site`() { whenever(siteStore.sitesCount).thenReturn(2) @@ -656,18 +688,18 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Test fun `Should track analytics event when onHelpPromptActionClicked is called`() = test { - whenever(bloggingPromptsSettingsHelper.shouldShowPromptsFeature()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(true) startViewModelWithDefaultParameters() val action = viewModel.mainActions.value?.first { it.actionType == ANSWER_BLOGGING_PROMPT } as AnswerBloggingPromptAction action.onHelpAction?.invoke() - verify(analyticsTrackerWrapper).track(Stat.MY_SITE_CREATE_SHEET_PROMPT_HELP_TAPPED) + verify(mainCreateSheetHelper).trackHelpPromptActionTapped(any()) } @Test fun `Should trigger openBloggingPromptsOnboarding when onHelpPromptActionClicked is called`() = test { - whenever(bloggingPromptsSettingsHelper.shouldShowPromptsFeature()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(true) startViewModelWithDefaultParameters() val action = viewModel.mainActions.value?.first { it.actionType == ANSWER_BLOGGING_PROMPT @@ -680,9 +712,9 @@ class WPMainActivityViewModelTest : BaseUnitTest() { @Suppress("MaxLineLength") fun `Should track BLOGGING_PROMPTS_CREATE_SHEET_CARD_VIEWED when onFabClicked is called and actions contains AnswerBloggingPromptAction`() = test { - whenever(bloggingPromptsSettingsHelper.shouldShowPromptsFeature()).thenReturn(true) + whenever(mainCreateSheetHelper.canCreatePromptAnswer()).thenReturn(true) startViewModelWithDefaultParameters() - viewModel.onFabClicked(initSite()) + viewModel.onFabClicked(initSite(), page = PageType.MY_SITE) verify(analyticsTrackerWrapper).track(Stat.BLOGGING_PROMPTS_CREATE_SHEET_CARD_VIEWED) } @@ -731,12 +763,14 @@ class WPMainActivityViewModelTest : BaseUnitTest() { private fun startViewModelWithDefaultParameters( isWhatsNewFeatureEnabled: Boolean = true, - isCreateFabEnabled: Boolean = true, - isWpcomOrJpSite: Boolean = true + isWpcomOrJpSite: Boolean = true, + pageType: PageType = PageType.MY_SITE, ) { whenever(buildConfigWrapper.isWhatsNewFeatureEnabled).thenReturn(isWhatsNewFeatureEnabled) - whenever(buildConfigWrapper.isCreateFabEnabled).thenReturn(isCreateFabEnabled) - viewModel.start(site = initSite(hasFullAccessToContent = true, isWpcomOrJpSite = isWpcomOrJpSite)) + viewModel.start( + site = initSite(hasFullAccessToContent = true, isWpcomOrJpSite = isWpcomOrJpSite), + page = pageType + ) } private fun setupObservers() { @@ -748,7 +782,7 @@ class WPMainActivityViewModelTest : BaseUnitTest() { } private fun resumeViewModelWithDefaultParameters() { - viewModel.onResume(site = initSite(hasFullAccessToContent = true), isOnMySitePageWithValidSite = true) + viewModel.onResume(site = initSite(hasFullAccessToContent = true), hasValidSite = true, page = PageType.MY_SITE) } private fun initSite(