diff --git a/app/metrics.yaml b/app/metrics.yaml index 50735ac006fe..cb18c9e3e9eb 100644 --- a/app/metrics.yaml +++ b/app/metrics.yaml @@ -4095,8 +4095,10 @@ collections: extra_keys: tabs_open: description: "The number of tabs open in the current session" + type: string tabs_selected: description: "The number of tabs added to the collection" + type: string bugs: - https://github.com/mozilla-mobile/fenix/issues/969 - https://github.com/mozilla-mobile/fenix/issues/19923 @@ -4123,8 +4125,10 @@ collections: extra_keys: tabs_open: description: The number of tabs open in the current session + type: string tabs_selected: description: The number of tabs added to the collection + type: string bugs: - https://github.com/mozilla-mobile/fenix/issues/969 - https://github.com/mozilla-mobile/fenix/issues/19923 @@ -4238,6 +4242,7 @@ collections: description: | A string representing the screen from which the user pressed the save button. Currently one of: `browserMenu`, `homeMenu` or `home` + type: string metadata: tags: - Collections diff --git a/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationController.kt b/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationController.kt index ae8d779f1ac2..9c963ef02ef2 100644 --- a/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationController.kt +++ b/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationController.kt @@ -14,9 +14,9 @@ import mozilla.components.browser.state.selector.normalTabs import mozilla.components.browser.state.state.TabSessionState import mozilla.components.browser.state.store.BrowserStore import mozilla.components.feature.tab.collections.TabCollection +import mozilla.telemetry.glean.private.NoExtras +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.components.TabCollectionStorage -import org.mozilla.fenix.components.metrics.Event -import org.mozilla.fenix.components.metrics.MetricController import org.mozilla.fenix.ext.getDefaultCollectionNumber interface CollectionCreationController { @@ -67,7 +67,6 @@ fun List.toTabSessionStateList(store: BrowserStore): List * @param store Store used to hold in-memory collection state. * @param browserStore The global `BrowserStore` instance. * @param dismiss Callback to dismiss the collection creation dialog. - * @param metrics Controller that handles telemetry events. * @param tabCollectionStorage Storage used to save tab collections to disk. * @param scope Coroutine scope to launch coroutines. */ @@ -75,7 +74,6 @@ class DefaultCollectionCreationController( private val store: CollectionCreationStore, private val browserStore: BrowserStore, private val dismiss: () -> Unit, - private val metrics: MetricController, private val tabCollectionStorage: TabCollectionStorage, private val scope: CoroutineScope ) : CollectionCreationController { @@ -93,8 +91,11 @@ class DefaultCollectionCreationController( tabCollectionStorage.createCollection(name, sessionBundle) } - metrics.track( - Event.CollectionSaved(browserStore.state.normalTabs.size, sessionBundle.size) + Collections.saved.record( + Collections.SavedExtra( + browserStore.state.normalTabs.size.toString(), + sessionBundle.size.toString() + ) ) } @@ -103,7 +104,7 @@ class DefaultCollectionCreationController( scope.launch { tabCollectionStorage.renameCollection(collection, name) } - metrics.track(Event.CollectionRenamed) + Collections.renamed.record(NoExtras()) } override fun backPressed(fromStep: SaveCollectionStep) { @@ -135,8 +136,11 @@ class DefaultCollectionCreationController( .addTabsToCollection(collection, sessionBundle) } - metrics.track( - Event.CollectionTabsAdded(browserStore.state.normalTabs.size, sessionBundle.size) + Collections.tabsAdded.record( + Collections.TabsAddedExtra( + browserStore.state.normalTabs.size.toString(), + sessionBundle.size.toString() + ) ) } diff --git a/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationFragment.kt b/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationFragment.kt index 3618e4295a88..a7b586b21f36 100644 --- a/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationFragment.kt +++ b/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationFragment.kt @@ -58,7 +58,6 @@ class CollectionCreationFragment : DialogFragment() { collectionCreationStore, requireComponents.core.store, ::dismiss, - requireComponents.analytics.metrics, requireComponents.core.tabCollectionStorage, scope = lifecycleScope ) diff --git a/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationView.kt b/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationView.kt index 1e87a82f9be2..7d953e03d119 100644 --- a/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationView.kt +++ b/app/src/main/java/org/mozilla/fenix/collections/CollectionCreationView.kt @@ -20,8 +20,9 @@ import androidx.transition.TransitionManager import mozilla.components.feature.tab.collections.TabCollection import mozilla.components.support.ktx.android.view.hideKeyboard import mozilla.components.support.ktx.android.view.showKeyboard +import mozilla.telemetry.glean.private.NoExtras +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.R -import org.mozilla.fenix.components.metrics.Event import org.mozilla.fenix.databinding.ComponentCollectionCreationBinding import org.mozilla.fenix.ext.components import org.mozilla.fenix.ext.toShortUrl @@ -109,7 +110,7 @@ class CollectionCreationView( } private fun updateForSelectTabs(state: CollectionCreationState) { - container.context.components.analytics.metrics.track(Event.CollectionTabSelectOpened) + Collections.tabSelectOpened.record(NoExtras()) binding.tabList.isClickable = true diff --git a/app/src/main/java/org/mozilla/fenix/components/metrics/Event.kt b/app/src/main/java/org/mozilla/fenix/components/metrics/Event.kt index 1fd642920a3e..aac7c5fb2bbb 100644 --- a/app/src/main/java/org/mozilla/fenix/components/metrics/Event.kt +++ b/app/src/main/java/org/mozilla/fenix/components/metrics/Event.kt @@ -10,7 +10,6 @@ import mozilla.components.feature.top.sites.TopSite import org.mozilla.fenix.GleanMetrics.Addons import org.mozilla.fenix.GleanMetrics.AppTheme import org.mozilla.fenix.GleanMetrics.Autoplay -import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.GleanMetrics.ContextMenu import org.mozilla.fenix.GleanMetrics.Events import org.mozilla.fenix.GleanMetrics.History @@ -100,16 +99,6 @@ sealed class Event { object ReaderModeOpened : Event() object ReaderModeClosed : Event() object ReaderModeAppearanceOpened : Event() - object CollectionRenamed : Event() - object CollectionTabRestored : Event() - object CollectionAllTabsRestored : Event() - object CollectionTabRemoved : Event() - object CollectionShared : Event() - object CollectionRemoved : Event() - object CollectionTabSelectOpened : Event() - object CollectionTabLongPressed : Event() - object CollectionAddTabPressed : Event() - object CollectionRenamePressed : Event() object TabMediaPlay : Event() object TabMediaPause : Event() object MediaPlayState : Event() @@ -344,27 +333,6 @@ sealed class Event { get() = hashMapOf(Events.appOpenedKeys.source to source.name) } - data class CollectionSaveButtonPressed(val fromScreen: String) : Event() { - override val extras: Map? - get() = mapOf(Collections.saveButtonKeys.fromScreen to fromScreen) - } - - data class CollectionSaved(val tabsOpenCount: Int, val tabsSelectedCount: Int) : Event() { - override val extras: Map? - get() = mapOf( - Collections.savedKeys.tabsOpen to tabsOpenCount.toString(), - Collections.savedKeys.tabsSelected to tabsSelectedCount.toString() - ) - } - - data class CollectionTabsAdded(val tabsOpenCount: Int, val tabsSelectedCount: Int) : Event() { - override val extras: Map? - get() = mapOf( - Collections.tabsAddedKeys.tabsOpen to tabsOpenCount.toString(), - Collections.tabsAddedKeys.tabsSelected to tabsSelectedCount.toString() - ) - } - data class SearchBarTapped(val source: Source) : Event() { enum class Source { HOME, BROWSER } diff --git a/app/src/main/java/org/mozilla/fenix/components/metrics/GleanMetricsService.kt b/app/src/main/java/org/mozilla/fenix/components/metrics/GleanMetricsService.kt index c214ebf857ea..a11691ec0390 100644 --- a/app/src/main/java/org/mozilla/fenix/components/metrics/GleanMetricsService.kt +++ b/app/src/main/java/org/mozilla/fenix/components/metrics/GleanMetricsService.kt @@ -15,7 +15,6 @@ import org.mozilla.fenix.GleanMetrics.Autoplay import org.mozilla.fenix.GleanMetrics.Awesomebar import org.mozilla.fenix.GleanMetrics.BookmarksManagement import org.mozilla.fenix.GleanMetrics.BrowserSearch -import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.GleanMetrics.ContextMenu import org.mozilla.fenix.GleanMetrics.ContextualMenu import org.mozilla.fenix.GleanMetrics.CreditCards @@ -333,27 +332,6 @@ private val Event.wrapper: EventWrapper<*>? is Event.RecentlyClosedTabsExitMultiselect -> EventWrapper( { RecentlyClosedTabs.exitMultiselect.record(it) } ) - is Event.CollectionRenamed -> EventWrapper( - { Collections.renamed.record(it) } - ) - is Event.CollectionTabRestored -> EventWrapper( - { Collections.tabRestored.record(it) } - ) - is Event.CollectionAllTabsRestored -> EventWrapper( - { Collections.allTabsRestored.record(it) } - ) - is Event.CollectionTabRemoved -> EventWrapper( - { Collections.tabRemoved.record(it) } - ) - is Event.CollectionShared -> EventWrapper( - { Collections.shared.record(it) } - ) - is Event.CollectionRemoved -> EventWrapper( - { Collections.removed.record(it) } - ) - is Event.CollectionTabSelectOpened -> EventWrapper( - { Collections.tabSelectOpened.record(it) } - ) is Event.ReaderModeAvailable -> EventWrapper( { ReaderMode.available.record(it) } ) @@ -366,27 +344,6 @@ private val Event.wrapper: EventWrapper<*>? is Event.ReaderModeAppearanceOpened -> EventWrapper( { ReaderMode.appearance.record(it) } ) - is Event.CollectionTabLongPressed -> EventWrapper( - { Collections.longPress.record(it) } - ) - is Event.CollectionSaveButtonPressed -> EventWrapper( - { Collections.saveButton.record(it) }, - { Collections.saveButtonKeys.valueOf(it) } - ) - is Event.CollectionAddTabPressed -> EventWrapper( - { Collections.addTabButton.record(it) } - ) - is Event.CollectionRenamePressed -> EventWrapper( - { Collections.renameButton.record(it) } - ) - is Event.CollectionSaved -> EventWrapper( - { Collections.saved.record(it) }, - { Collections.savedKeys.valueOf(it) } - ) - is Event.CollectionTabsAdded -> EventWrapper( - { Collections.tabsAdded.record(it) }, - { Collections.tabsAddedKeys.valueOf(it) } - ) is Event.WhatsNewTapped -> EventWrapper( { Events.whatsNewTapped.record(it) } ) diff --git a/app/src/main/java/org/mozilla/fenix/components/toolbar/BrowserToolbarMenuController.kt b/app/src/main/java/org/mozilla/fenix/components/toolbar/BrowserToolbarMenuController.kt index 6bf76b9eed54..ef6b4e8643d1 100644 --- a/app/src/main/java/org/mozilla/fenix/components/toolbar/BrowserToolbarMenuController.kt +++ b/app/src/main/java/org/mozilla/fenix/components/toolbar/BrowserToolbarMenuController.kt @@ -27,6 +27,7 @@ import mozilla.components.feature.top.sites.DefaultTopSitesStorage import mozilla.components.feature.top.sites.PinnedSiteStorage import mozilla.components.feature.top.sites.TopSite import mozilla.components.support.base.feature.ViewBoundFeatureWrapper +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.HomeActivity import org.mozilla.fenix.NavGraphDirections import org.mozilla.fenix.R @@ -307,8 +308,11 @@ class DefaultBrowserToolbarMenuController( ) } is ToolbarMenu.Item.SaveToCollection -> { - metrics - .track(Event.CollectionSaveButtonPressed(TELEMETRY_BROWSER_IDENTIFIER)) + Collections.saveButton.record( + Collections.SaveButtonExtra( + TELEMETRY_BROWSER_IDENTIFIER + ) + ) currentSession?.let { currentSession -> val directions = diff --git a/app/src/main/java/org/mozilla/fenix/home/sessioncontrol/SessionControlController.kt b/app/src/main/java/org/mozilla/fenix/home/sessioncontrol/SessionControlController.kt index 6d078d81aa2c..900d8fa57e1f 100644 --- a/app/src/main/java/org/mozilla/fenix/home/sessioncontrol/SessionControlController.kt +++ b/app/src/main/java/org/mozilla/fenix/home/sessioncontrol/SessionControlController.kt @@ -27,8 +27,10 @@ import mozilla.components.feature.tabs.TabsUseCases import mozilla.components.feature.top.sites.TopSite import mozilla.components.support.ktx.android.view.showKeyboard import mozilla.components.support.ktx.kotlin.isUrl +import mozilla.telemetry.glean.private.NoExtras import org.mozilla.fenix.BrowserDirection import org.mozilla.fenix.FeatureFlags +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.GleanMetrics.Pings import org.mozilla.fenix.GleanMetrics.TopSites import org.mozilla.fenix.HomeActivity @@ -232,7 +234,7 @@ class DefaultSessionControlController( ) : SessionControlController { override fun handleCollectionAddTabTapped(collection: TabCollection) { - metrics.track(Event.CollectionAddTabPressed) + Collections.addTabButton.record(NoExtras()) showCollectionCreationFragment( step = SaveCollectionStep.SelectTabs, selectedTabCollectionId = collection.id @@ -264,7 +266,7 @@ class DefaultSessionControlController( } ) - metrics.track(Event.CollectionTabRestored) + Collections.tabRestored.record(NoExtras()) } override fun handleCollectionOpenTabsTapped(collection: TabCollection) { @@ -278,7 +280,7 @@ class DefaultSessionControlController( ) showTabTray() - metrics.track(Event.CollectionAllTabsRestored) + Collections.allTabsRestored.record(NoExtras()) } override fun handleCollectionRemoveTab( @@ -286,7 +288,7 @@ class DefaultSessionControlController( tab: ComponentTab, wasSwiped: Boolean ) { - metrics.track(Event.CollectionTabRemoved) + Collections.tabRemoved.record(NoExtras()) if (collection.tabs.size == 1) { removeCollectionWithUndo(collection) @@ -303,7 +305,7 @@ class DefaultSessionControlController( collection.title, collection.tabs.map { ShareData(url = it.url, title = it.title) } ) - metrics.track(Event.CollectionShared) + Collections.shared.record(NoExtras()) } override fun handleDeleteCollectionTapped(collection: TabCollection) { @@ -391,7 +393,7 @@ class DefaultSessionControlController( step = SaveCollectionStep.RenameCollection, selectedTabCollectionId = collection.id ) - metrics.track(Event.CollectionRenamePressed) + Collections.renameButton.record(NoExtras()) } override fun handleSelectTopSite(topSite: TopSite, position: Int) { diff --git a/app/src/main/java/org/mozilla/fenix/tabstray/NavigationInteractor.kt b/app/src/main/java/org/mozilla/fenix/tabstray/NavigationInteractor.kt index e0b2d48e65f9..39e74f00a741 100644 --- a/app/src/main/java/org/mozilla/fenix/tabstray/NavigationInteractor.kt +++ b/app/src/main/java/org/mozilla/fenix/tabstray/NavigationInteractor.kt @@ -17,6 +17,7 @@ import mozilla.components.concept.engine.prompt.ShareData import mozilla.components.service.fxa.manager.FxaAccountManager import mozilla.telemetry.glean.private.NoExtras import org.mozilla.fenix.BrowserDirection +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.GleanMetrics.TabsTray import org.mozilla.fenix.HomeActivity import org.mozilla.fenix.collections.CollectionsDialog @@ -209,16 +210,24 @@ class DefaultNavigationInteractor( onPositiveButtonClick = { id, isNewCollection -> // If collection is null, a new one was created. - val event = if (isNewCollection) { - Event.CollectionSaved(browserStore.state.normalTabs.size, tabs.size) + if (isNewCollection) { + Collections.saved.record( + Collections.SavedExtra( + browserStore.state.normalTabs.size.toString(), + tabs.size.toString() + ) + ) } else { - Event.CollectionTabsAdded(browserStore.state.normalTabs.size, tabs.size) + Collections.tabsAdded.record( + Collections.TabsAddedExtra( + browserStore.state.normalTabs.size.toString(), + tabs.size.toString() + ) + ) } id?.apply { showCollectionSnackbar(tabs.size, isNewCollection, id) } - - metrics.track(event) }, onNegativeButtonClick = {} ).show(context) diff --git a/app/src/main/java/org/mozilla/fenix/tabstray/browser/AbstractBrowserTabViewHolder.kt b/app/src/main/java/org/mozilla/fenix/tabstray/browser/AbstractBrowserTabViewHolder.kt index 76f06c00642a..0dd3385c8b9c 100644 --- a/app/src/main/java/org/mozilla/fenix/tabstray/browser/AbstractBrowserTabViewHolder.kt +++ b/app/src/main/java/org/mozilla/fenix/tabstray/browser/AbstractBrowserTabViewHolder.kt @@ -29,7 +29,9 @@ import mozilla.components.browser.toolbar.MAX_URI_LENGTH import mozilla.components.concept.base.images.ImageLoadRequest import mozilla.components.concept.base.images.ImageLoader import mozilla.components.concept.engine.mediasession.MediaSession +import mozilla.telemetry.glean.private.NoExtras import org.mozilla.fenix.FeatureFlags +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.R import org.mozilla.fenix.components.metrics.Event import org.mozilla.fenix.components.metrics.MetricController @@ -230,7 +232,7 @@ abstract class AbstractBrowserTabViewHolder( itemView.setOnLongClickListener { if (holder.selectedItems.isEmpty()) { - metrics.track(Event.CollectionTabLongPressed) + Collections.longPress.record(NoExtras()) interactor.select(item) true } else { diff --git a/app/src/test/java/org/mozilla/fenix/collections/DefaultCollectionCreationControllerTest.kt b/app/src/test/java/org/mozilla/fenix/collections/DefaultCollectionCreationControllerTest.kt index 75f3ad8be3f8..d8712cada1f2 100644 --- a/app/src/test/java/org/mozilla/fenix/collections/DefaultCollectionCreationControllerTest.kt +++ b/app/src/test/java/org/mozilla/fenix/collections/DefaultCollectionCreationControllerTest.kt @@ -11,33 +11,40 @@ import io.mockk.every import io.mockk.impl.annotations.MockK import io.mockk.mockk import io.mockk.verify -import io.mockk.verifyAll import kotlinx.coroutines.test.TestCoroutineScope import kotlinx.coroutines.test.runBlockingTest import mozilla.components.browser.state.action.TabListAction import mozilla.components.browser.state.state.createTab import mozilla.components.browser.state.store.BrowserStore import mozilla.components.feature.tab.collections.TabCollection +import mozilla.components.service.glean.testing.GleanTestRule import mozilla.components.support.test.ext.joinBlocking +import mozilla.components.support.test.robolectric.testContext import org.junit.After import org.junit.Assert.assertEquals +import org.junit.Assert.assertNotNull import org.junit.Assert.assertNull import org.junit.Assert.assertTrue import org.junit.Before +import org.junit.Rule import org.junit.Test +import org.junit.runner.RunWith +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.components.TabCollectionStorage -import org.mozilla.fenix.components.metrics.Event -import org.mozilla.fenix.components.metrics.MetricController +import org.mozilla.fenix.helpers.FenixRobolectricTestRunner +@RunWith(FenixRobolectricTestRunner::class) // For gleanTestRule class DefaultCollectionCreationControllerTest { + @get:Rule + val gleanTestRule = GleanTestRule(testContext) + private val testCoroutineScope = TestCoroutineScope() private lateinit var state: CollectionCreationState private lateinit var controller: DefaultCollectionCreationController private var dismissed = false @MockK(relaxed = true) private lateinit var store: CollectionCreationStore - @MockK(relaxUnitFun = true) private lateinit var metrics: MetricController @MockK(relaxUnitFun = true) private lateinit var tabCollectionStorage: TabCollectionStorage private lateinit var browserStore: BrowserStore @@ -60,7 +67,6 @@ class DefaultCollectionCreationControllerTest { dismiss = { dismissed = true }, - metrics, tabCollectionStorage, testCoroutineScope ) @@ -92,7 +98,16 @@ class DefaultCollectionCreationControllerTest { assertTrue(dismissed) coVerify { tabCollectionStorage.createCollection("name", listOf(tab1)) } - verify { metrics.track(Event.CollectionSaved(2, 1)) } + + assertTrue(Collections.saved.testHasValue()) + val recordedEvents = Collections.saved.testGetValue() + assertEquals(1, recordedEvents.size) + val eventExtra = recordedEvents.single().extra + assertNotNull(eventExtra) + assertTrue(eventExtra!!.containsKey("tabs_open")) + assertEquals("2", eventExtra["tabs_open"]) + assertTrue(eventExtra.containsKey("tabs_selected")) + assertEquals("1", eventExtra["tabs_selected"]) } @Test @@ -138,9 +153,12 @@ class DefaultCollectionCreationControllerTest { advanceUntilIdle() assertTrue(dismissed) - verifyAll { - metrics.track(Event.CollectionRenamed) - } + + assertTrue(Collections.renamed.testHasValue()) + val recordedEvents = Collections.renamed.testGetValue() + assertEquals(1, recordedEvents.size) + assertNull(recordedEvents.single().extra) + coVerify { tabCollectionStorage.renameCollection(collection, "name") } } @@ -186,7 +204,16 @@ class DefaultCollectionCreationControllerTest { assertTrue(dismissed) coVerify { tabCollectionStorage.addTabsToCollection(collection, listOf(tab1)) } - verify { metrics.track(Event.CollectionTabsAdded(2, 1)) } + + assertTrue(Collections.tabsAdded.testHasValue()) + val recordedEvents = Collections.tabsAdded.testGetValue() + assertEquals(1, recordedEvents.size) + val eventExtra = recordedEvents.single().extra + assertNotNull(eventExtra) + assertTrue(eventExtra!!.containsKey("tabs_open")) + assertEquals("2", eventExtra["tabs_open"]) + assertTrue(eventExtra.containsKey("tabs_selected")) + assertEquals("1", eventExtra["tabs_selected"]) } @Test diff --git a/app/src/test/java/org/mozilla/fenix/components/toolbar/DefaultBrowserToolbarMenuControllerTest.kt b/app/src/test/java/org/mozilla/fenix/components/toolbar/DefaultBrowserToolbarMenuControllerTest.kt index b40d7ef65e2c..59f6e78eb218 100644 --- a/app/src/test/java/org/mozilla/fenix/components/toolbar/DefaultBrowserToolbarMenuControllerTest.kt +++ b/app/src/test/java/org/mozilla/fenix/components/toolbar/DefaultBrowserToolbarMenuControllerTest.kt @@ -43,16 +43,20 @@ import mozilla.components.feature.top.sites.DefaultTopSitesStorage import mozilla.components.feature.top.sites.PinnedSiteStorage import mozilla.components.feature.top.sites.TopSite import mozilla.components.feature.top.sites.TopSitesUseCases +import mozilla.components.service.glean.testing.GleanTestRule import mozilla.components.support.base.feature.ViewBoundFeatureWrapper import mozilla.components.support.test.ext.joinBlocking +import mozilla.components.support.test.robolectric.testContext import mozilla.components.support.test.rule.MainCoroutineRule import org.junit.After import org.junit.Assert.assertEquals +import org.junit.Assert.assertNotNull import org.junit.Assert.assertTrue import org.junit.Before import org.junit.Rule import org.junit.Test import org.junit.runner.RunWith +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.HomeActivity import org.mozilla.fenix.NavGraphDirections import org.mozilla.fenix.R @@ -77,6 +81,8 @@ class DefaultBrowserToolbarMenuControllerTest { @get:Rule val coroutinesTestRule = MainCoroutineRule() + @get:Rule + val gleanTestRule = GleanTestRule(testContext) @MockK private lateinit var swipeRefreshLayout: SwipeRefreshLayout @RelaxedMockK private lateinit var activity: HomeActivity @@ -551,11 +557,17 @@ class DefaultBrowserToolbarMenuControllerTest { Event.BrowserMenuItemTapped(Event.BrowserMenuItemTapped.Item.SAVE_TO_COLLECTION) ) } - verify { - metrics.track( - Event.CollectionSaveButtonPressed(DefaultBrowserToolbarController.TELEMETRY_BROWSER_IDENTIFIER) - ) - } + + assertTrue(Collections.saveButton.testHasValue()) + val recordedEvents = Collections.saveButton.testGetValue() + assertEquals(1, recordedEvents.size) + val eventExtra = recordedEvents.single().extra + assertNotNull(eventExtra) + assertTrue(eventExtra!!.containsKey("from_screen")) + assertEquals( + DefaultBrowserToolbarMenuController.TELEMETRY_BROWSER_IDENTIFIER, + eventExtra["from_screen"] + ) val directions = BrowserFragmentDirections.actionGlobalCollectionCreationFragment( saveCollectionStep = SaveCollectionStep.SelectCollection, @@ -575,13 +587,18 @@ class DefaultBrowserToolbarMenuControllerTest { controller.handleToolbarItemInteraction(item) verify { metrics.track(Event.BrowserMenuItemTapped(Event.BrowserMenuItemTapped.Item.SAVE_TO_COLLECTION)) } - verify { - metrics.track( - Event.CollectionSaveButtonPressed( - DefaultBrowserToolbarController.TELEMETRY_BROWSER_IDENTIFIER - ) - ) - } + + assertTrue(Collections.saveButton.testHasValue()) + val recordedEvents = Collections.saveButton.testGetValue() + assertEquals(1, recordedEvents.size) + val eventExtra = recordedEvents.single().extra + assertNotNull(eventExtra) + assertTrue(eventExtra!!.containsKey("from_screen")) + assertEquals( + DefaultBrowserToolbarMenuController.TELEMETRY_BROWSER_IDENTIFIER, + eventExtra["from_screen"] + ) + val directions = BrowserFragmentDirections.actionGlobalCollectionCreationFragment( saveCollectionStep = SaveCollectionStep.NameCollection, tabIds = arrayOf(selectedTab.id), diff --git a/app/src/test/java/org/mozilla/fenix/home/DefaultSessionControlControllerTest.kt b/app/src/test/java/org/mozilla/fenix/home/DefaultSessionControlControllerTest.kt index 1e61dd1a4fde..7feb2f2255d9 100644 --- a/app/src/test/java/org/mozilla/fenix/home/DefaultSessionControlControllerTest.kt +++ b/app/src/test/java/org/mozilla/fenix/home/DefaultSessionControlControllerTest.kt @@ -33,7 +33,9 @@ import mozilla.components.feature.session.SessionUseCases import mozilla.components.feature.tab.collections.TabCollection import mozilla.components.feature.tabs.TabsUseCases import mozilla.components.feature.top.sites.TopSite +import mozilla.components.service.glean.testing.GleanTestRule import mozilla.components.support.test.ext.joinBlocking +import mozilla.components.support.test.robolectric.testContext import mozilla.components.support.test.rule.MainCoroutineRule import org.junit.After import org.junit.Assert.assertEquals @@ -42,7 +44,9 @@ import org.junit.Before import org.junit.Ignore import org.junit.Rule import org.junit.Test +import org.junit.runner.RunWith import org.mozilla.fenix.BrowserDirection +import org.mozilla.fenix.GleanMetrics.Collections import org.mozilla.fenix.GleanMetrics.Pings import org.mozilla.fenix.GleanMetrics.TopSites import org.mozilla.fenix.HomeActivity @@ -61,6 +65,7 @@ import org.mozilla.fenix.ext.components import org.mozilla.fenix.ext.settings import org.mozilla.fenix.gleanplumb.Message import org.mozilla.fenix.gleanplumb.MessageController +import org.mozilla.fenix.helpers.FenixRobolectricTestRunner import org.mozilla.fenix.home.recentbookmarks.RecentBookmark import org.mozilla.fenix.home.recenttabs.RecentTab import org.mozilla.fenix.home.sessioncontrol.DefaultSessionControlController @@ -68,11 +73,14 @@ import org.mozilla.fenix.settings.SupportUtils import org.mozilla.fenix.utils.Settings import mozilla.components.feature.tab.collections.Tab as ComponentTab +@RunWith(FenixRobolectricTestRunner::class) // For gleanTestRule @OptIn(ExperimentalCoroutinesApi::class) class DefaultSessionControlControllerTest { @get:Rule val coroutinesTestRule = MainCoroutineRule() + @get:Rule + val gleanTestRule = GleanTestRule(testContext) private val activity: HomeActivity = mockk(relaxed = true) private val appStore: AppStore = mockk(relaxed = true) @@ -157,7 +165,11 @@ class DefaultSessionControlControllerTest { } createController().handleCollectionAddTabTapped(collection) - verify { metrics.track(Event.CollectionAddTabPressed) } + assertTrue(Collections.addTabButton.testHasValue()) + val recordedEvents = Collections.addTabButton.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) + verify { navController.navigate( match { @@ -206,7 +218,11 @@ class DefaultSessionControlControllerTest { } createController().handleCollectionOpenTabClicked(tab) - verify { metrics.track(Event.CollectionTabRestored) } + assertTrue(Collections.tabRestored.testHasValue()) + val recordedEvents = Collections.tabRestored.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) + verify { activity.openToBrowserAndLoad( searchTermOrURL = "https://mozilla.org", @@ -243,7 +259,12 @@ class DefaultSessionControlControllerTest { store.dispatch(TabListAction.AddTabAction(restoredTab)).joinBlocking() createController().handleCollectionOpenTabClicked(tab) - verify { metrics.track(Event.CollectionTabRestored) } + + assertTrue(Collections.tabRestored.testHasValue()) + val recordedEvents = Collections.tabRestored.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) + verify { activity.openToBrowser(BrowserDirection.FromHome) } verify { selectTabUseCase.selectTab.invoke(restoredTab.id) } verify { reloadUrlUseCase.reload.invoke(restoredTab.id) } @@ -273,7 +294,12 @@ class DefaultSessionControlControllerTest { store.dispatch(TabListAction.AddTabAction(restoredTab)).joinBlocking() createController().handleCollectionOpenTabClicked(tab) - verify { metrics.track(Event.CollectionTabRestored) } + + assertTrue(Collections.tabRestored.testHasValue()) + val recordedEvents = Collections.tabRestored.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) + verify { activity.openToBrowser(BrowserDirection.FromHome) } verify { selectTabUseCase.selectTab.invoke(restoredTab.id) } verify { reloadUrlUseCase.reload.invoke(restoredTab.id) } @@ -286,7 +312,10 @@ class DefaultSessionControlControllerTest { } createController().handleCollectionOpenTabsTapped(collection) - verify { metrics.track(Event.CollectionAllTabsRestored) } + assertTrue(Collections.allTabsRestored.testHasValue()) + val recordedEvents = Collections.allTabsRestored.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) } @Test @@ -314,7 +343,10 @@ class DefaultSessionControlControllerTest { } ).handleCollectionRemoveTab(expectedCollection, tab, false) - verify { metrics.track(Event.CollectionTabRemoved) } + assertTrue(Collections.tabRemoved.testHasValue()) + val recordedEvents = Collections.tabRemoved.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) assertEquals(expectedCollection, actualCollection) } @@ -324,7 +356,11 @@ class DefaultSessionControlControllerTest { val collection: TabCollection = mockk(relaxed = true) val tab: ComponentTab = mockk(relaxed = true) createController().handleCollectionRemoveTab(collection, tab, false) - verify { metrics.track(Event.CollectionTabRemoved) } + + assertTrue(Collections.tabRemoved.testHasValue()) + val recordedEvents = Collections.tabRemoved.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) } @Test @@ -335,7 +371,11 @@ class DefaultSessionControlControllerTest { } createController().handleCollectionShareTabsClicked(collection) - verify { metrics.track(Event.CollectionShared) } + assertTrue(Collections.shared.testHasValue()) + val recordedEvents = Collections.shared.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) + verify { navController.navigate( match { it.actionId == R.id.action_global_shareFragment }, @@ -384,7 +424,11 @@ class DefaultSessionControlControllerTest { } createController().handleRenameCollectionTapped(collection) - verify { metrics.track(Event.CollectionRenamePressed) } + assertTrue(Collections.renameButton.testHasValue()) + val recordedEvents = Collections.renameButton.testGetValue() + assertEquals(1, recordedEvents.size) + assertEquals(null, recordedEvents.single().extra) + verify { navController.navigate( match { it.actionId == R.id.action_global_collectionCreationFragment },