Closes #18948: Update tabstray telemetry (#19004)

upstream-sync
Roger Yang 3 years ago committed by GitHub
parent cea869c276
commit 8246f81c97
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -2473,6 +2473,19 @@ tabs_tray:
notification_emails: notification_emails:
- fenix-core@mozilla.com - fenix-core@mozilla.com
expires: "2021-08-01" expires: "2021-08-01"
synced_mode_tapped:
type: event
description: |
A user switched to synced mode
bugs:
- https://github.com/mozilla-mobile/fenix/issues/18948
data_reviews:
- https://github.com/mozilla-mobile/fenix/pull/19004
data_sensitivity:
- interaction
notification_emails:
- fenix-core@mozilla.com
expires: "2022-08-01"
new_tab_tapped: new_tab_tapped:
type: event type: event
description: | description: |

@ -182,6 +182,7 @@ sealed class Event {
object ClosedExistingTab : Event() object ClosedExistingTab : Event()
object TabsTrayPrivateModeTapped : Event() object TabsTrayPrivateModeTapped : Event()
object TabsTrayNormalModeTapped : Event() object TabsTrayNormalModeTapped : Event()
object TabsTraySyncedModeTapped : Event()
object NewTabTapped : Event() object NewTabTapped : Event()
object NewPrivateTabTapped : Event() object NewPrivateTabTapped : Event()
object TabsTrayMenuOpened : Event() object TabsTrayMenuOpened : Event()

@ -674,6 +674,9 @@ private val Event.wrapper: EventWrapper<*>?
is Event.TabsTrayNormalModeTapped -> EventWrapper<NoExtraKeys>( is Event.TabsTrayNormalModeTapped -> EventWrapper<NoExtraKeys>(
{ TabsTray.normalModeTapped.record(it) } { TabsTray.normalModeTapped.record(it) }
) )
is Event.TabsTraySyncedModeTapped -> EventWrapper<NoExtraKeys>(
{ TabsTray.syncedModeTapped.record(it) }
)
is Event.NewTabTapped -> EventWrapper<NoExtraKeys>( is Event.NewTabTapped -> EventWrapper<NoExtraKeys>(
{ TabsTray.newTabTapped.record(it) } { TabsTray.newTabTapped.record(it) }
) )

@ -9,8 +9,11 @@ import com.google.android.material.tabs.TabLayout
import mozilla.components.browser.state.selector.selectedTab import mozilla.components.browser.state.selector.selectedTab
import mozilla.components.browser.state.store.BrowserStore import mozilla.components.browser.state.store.BrowserStore
import mozilla.components.support.base.feature.LifecycleAwareFeature import mozilla.components.support.base.feature.LifecycleAwareFeature
import org.mozilla.fenix.components.metrics.Event
import org.mozilla.fenix.components.metrics.MetricController
import org.mozilla.fenix.tabstray.TrayPagerAdapter.Companion.POSITION_NORMAL_TABS import org.mozilla.fenix.tabstray.TrayPagerAdapter.Companion.POSITION_NORMAL_TABS
import org.mozilla.fenix.tabstray.TrayPagerAdapter.Companion.POSITION_PRIVATE_TABS import org.mozilla.fenix.tabstray.TrayPagerAdapter.Companion.POSITION_PRIVATE_TABS
import org.mozilla.fenix.utils.Do
/** /**
* Selected the selected pager depending on the [BrowserStore] state and synchronizes user actions * Selected the selected pager depending on the [BrowserStore] state and synchronizes user actions
@ -20,10 +23,11 @@ class TabLayoutMediator(
private val tabLayout: TabLayout, private val tabLayout: TabLayout,
interactor: TabsTrayInteractor, interactor: TabsTrayInteractor,
private val browserStore: BrowserStore, private val browserStore: BrowserStore,
trayStore: TabsTrayStore trayStore: TabsTrayStore,
private val metrics: MetricController
) : LifecycleAwareFeature { ) : LifecycleAwareFeature {
private val observer = TabLayoutObserver(interactor, trayStore) private val observer = TabLayoutObserver(interactor, trayStore, metrics)
/** /**
* Start observing the [TabLayout] and select the current tab for initial state. * Start observing the [TabLayout] and select the current tab for initial state.
@ -57,7 +61,8 @@ class TabLayoutMediator(
*/ */
internal class TabLayoutObserver( internal class TabLayoutObserver(
private val interactor: TabsTrayInteractor, private val interactor: TabsTrayInteractor,
private val trayStore: TabsTrayStore private val trayStore: TabsTrayStore,
private val metrics: MetricController
) : TabLayout.OnTabSelectedListener { ) : TabLayout.OnTabSelectedListener {
private var initialScroll = true private var initialScroll = true
@ -74,6 +79,12 @@ internal class TabLayoutObserver(
interactor.setCurrentTrayPosition(tab.position, animate) interactor.setCurrentTrayPosition(tab.position, animate)
trayStore.dispatch(TabsTrayAction.PageSelected(tab.toPage())) trayStore.dispatch(TabsTrayAction.PageSelected(tab.toPage()))
Do exhaustive when (tab.toPage()) {
Page.NormalTabs -> metrics.track(Event.TabsTrayNormalModeTapped)
Page.PrivateTabs -> metrics.track(Event.TabsTrayPrivateModeTapped)
Page.SyncedTabs -> metrics.track(Event.TabsTraySyncedModeTapped)
}
} }
override fun onTabUnselected(tab: TabLayout.Tab) = Unit override fun onTabUnselected(tab: TabLayout.Tab) = Unit

@ -51,6 +51,7 @@ class DefaultTabsTrayController(
"DefaultTabTrayController.onNewTabTapped", "DefaultTabTrayController.onNewTabTapped",
startTime startTime
) )
sendNewTabEvent(isPrivate)
} }
override fun onSyncStarted() { override fun onSyncStarted() {
@ -68,4 +69,14 @@ class DefaultTabsTrayController(
store.dispatch(TabsTrayAction.SyncCompleted) store.dispatch(TabsTrayAction.SyncCompleted)
} }
} }
private fun sendNewTabEvent(isPrivateModeSelected: Boolean) {
val eventToSend = if (isPrivateModeSelected) {
Event.NewPrivateTabTapped
} else {
Event.NewTabTapped
}
metrics.track(eventToSend)
}
} }

@ -92,6 +92,8 @@ class TabsTrayFragment : AppCompatDialogFragment(), TabsTrayInteractor {
super.onViewCreated(view, savedInstanceState) super.onViewCreated(view, savedInstanceState)
val activity = activity as HomeActivity val activity = activity as HomeActivity
requireComponents.analytics.metrics.track(Event.TabsTrayOpened)
val navigationInteractor = val navigationInteractor =
DefaultNavigationInteractor( DefaultNavigationInteractor(
context = requireContext(), context = requireContext(),
@ -99,8 +101,8 @@ class TabsTrayFragment : AppCompatDialogFragment(), TabsTrayInteractor {
browserStore = requireComponents.core.store, browserStore = requireComponents.core.store,
navController = findNavController(), navController = findNavController(),
metrics = requireComponents.analytics.metrics, metrics = requireComponents.analytics.metrics,
dismissTabTray = ::dismissAllowingStateLoss, dismissTabTray = ::dismissTabsTray,
dismissTabTrayAndNavigateHome = ::dismissTabTrayAndNavigateHome, dismissTabTrayAndNavigateHome = ::dismissTabsTrayAndNavigateHome,
bookmarksUseCase = requireComponents.useCases.bookmarksUseCases, bookmarksUseCase = requireComponents.useCases.bookmarksUseCases,
collectionStorage = requireComponents.core.tabCollectionStorage collectionStorage = requireComponents.core.tabCollectionStorage
) )
@ -144,8 +146,7 @@ class TabsTrayFragment : AppCompatDialogFragment(), TabsTrayInteractor {
behavior.addBottomSheetCallback( behavior.addBottomSheetCallback(
TraySheetBehaviorCallback( TraySheetBehaviorCallback(
behavior, behavior,
navigationInteractor, navigationInteractor
requireComponents.analytics.metrics
) )
) )
@ -167,7 +168,8 @@ class TabsTrayFragment : AppCompatDialogFragment(), TabsTrayInteractor {
tabLayout = tab_layout, tabLayout = tab_layout,
interactor = this, interactor = this,
browserStore = requireComponents.core.store, browserStore = requireComponents.core.store,
trayStore = tabsTrayStore trayStore = tabsTrayStore,
metrics = requireComponents.analytics.metrics
), owner = this, ), owner = this,
view = view view = view
) )
@ -233,7 +235,7 @@ class TabsTrayFragment : AppCompatDialogFragment(), TabsTrayInteractor {
} }
override fun navigateToBrowser() { override fun navigateToBrowser() {
dismissAllowingStateLoss() dismissTabsTray()
val navController = findNavController() val navController = findNavController()
@ -299,10 +301,15 @@ class TabsTrayFragment : AppCompatDialogFragment(), TabsTrayInteractor {
private val homeViewModel: HomeScreenViewModel by activityViewModels() private val homeViewModel: HomeScreenViewModel by activityViewModels()
private fun dismissTabTrayAndNavigateHome(sessionId: String) { private fun dismissTabsTrayAndNavigateHome(sessionId: String) {
homeViewModel.sessionToDelete = sessionId homeViewModel.sessionToDelete = sessionId
val directions = NavGraphDirections.actionGlobalHome() val directions = NavGraphDirections.actionGlobalHome()
findNavController().navigateBlockingForAsyncNavGraph(directions) findNavController().navigateBlockingForAsyncNavGraph(directions)
dismissTabsTray()
}
private fun dismissTabsTray() {
dismissAllowingStateLoss() dismissAllowingStateLoss()
requireComponents.analytics.metrics.track(Event.TabsTrayClosed)
} }
} }

@ -85,6 +85,7 @@ class TabsTrayInfoBannerBinding(
} }
) { ) {
navigationInteractor.onTabSettingsClicked() navigationInteractor.onTabSettingsClicked()
metrics?.track(Event.TabsTrayCfrTapped)
settings.shouldShowGridViewBanner = false settings.shouldShowGridViewBanner = false
} }
} else { } else {
@ -110,6 +111,7 @@ class TabsTrayInfoBannerBinding(
} }
) { ) {
navigationInteractor.onTabSettingsClicked() navigationInteractor.onTabSettingsClicked()
metrics?.track(Event.TabsTrayCfrTapped)
settings.shouldShowAutoCloseTabsBanner = false settings.shouldShowAutoCloseTabsBanner = false
} }
} else { } else {

@ -214,6 +214,7 @@ abstract class TabsTrayViewHolder(
itemView.setOnLongClickListener { itemView.setOnLongClickListener {
if (holder.selectedItems.isEmpty()) { if (holder.selectedItems.isEmpty()) {
metrics.track(Event.CollectionTabLongPressed)
interactor.select(item) interactor.select(item)
true true
} else { } else {

@ -8,18 +8,14 @@ import android.view.View
import androidx.constraintlayout.widget.ConstraintLayout import androidx.constraintlayout.widget.ConstraintLayout
import com.google.android.material.bottomsheet.BottomSheetBehavior import com.google.android.material.bottomsheet.BottomSheetBehavior
import com.google.android.material.bottomsheet.BottomSheetBehavior.STATE_HIDDEN import com.google.android.material.bottomsheet.BottomSheetBehavior.STATE_HIDDEN
import org.mozilla.fenix.components.metrics.Event
import org.mozilla.fenix.components.metrics.MetricController
class TraySheetBehaviorCallback( class TraySheetBehaviorCallback(
private val behavior: BottomSheetBehavior<ConstraintLayout>, private val behavior: BottomSheetBehavior<ConstraintLayout>,
private val trayInteractor: NavigationInteractor, private val trayInteractor: NavigationInteractor
private val metrics: MetricController
) : BottomSheetBehavior.BottomSheetCallback() { ) : BottomSheetBehavior.BottomSheetCallback() {
override fun onStateChanged(bottomSheet: View, newState: Int) { override fun onStateChanged(bottomSheet: View, newState: Int) {
if (newState == STATE_HIDDEN) { if (newState == STATE_HIDDEN) {
metrics.track(Event.TabsTrayClosed)
trayInteractor.onTabTrayDismissed() trayInteractor.onTabTrayDismissed()
} else if (newState == BottomSheetBehavior.STATE_HALF_EXPANDED) { } else if (newState == BottomSheetBehavior.STATE_HALF_EXPANDED) {
// We only support expanded and collapsed states. // We only support expanded and collapsed states.

@ -26,6 +26,8 @@ import org.mozilla.fenix.GleanMetrics.History
import org.mozilla.fenix.GleanMetrics.Metrics import org.mozilla.fenix.GleanMetrics.Metrics
import org.mozilla.fenix.GleanMetrics.SearchDefaultEngine import org.mozilla.fenix.GleanMetrics.SearchDefaultEngine
import org.mozilla.fenix.GleanMetrics.SyncedTabs import org.mozilla.fenix.GleanMetrics.SyncedTabs
import org.mozilla.fenix.GleanMetrics.TabsTray
import org.mozilla.fenix.GleanMetrics.TabsTrayCfr
import org.mozilla.fenix.components.toolbar.ToolbarPosition import org.mozilla.fenix.components.toolbar.ToolbarPosition
import org.mozilla.fenix.helpers.FenixRobolectricTestRunner import org.mozilla.fenix.helpers.FenixRobolectricTestRunner
import org.mozilla.fenix.utils.BrowsersCache import org.mozilla.fenix.utils.BrowsersCache
@ -258,4 +260,67 @@ class GleanMetricsServiceTest {
assertEquals(1, events[0].extra!!.size) assertEquals(1, events[0].extra!!.size)
assertEquals("123", events[0].extra!!["addon_id"]) assertEquals("123", events[0].extra!!["addon_id"])
} }
@Test
fun `TabsTray events are correctly recorded`() {
assertFalse(TabsTray.opened.testHasValue())
gleanService.track(Event.TabsTrayOpened)
assertTrue(TabsTray.opened.testHasValue())
assertFalse(TabsTray.closed.testHasValue())
gleanService.track(Event.TabsTrayClosed)
assertTrue(TabsTray.closed.testHasValue())
assertFalse(TabsTray.openedExistingTab.testHasValue())
gleanService.track(Event.OpenedExistingTab)
assertTrue(TabsTray.openedExistingTab.testHasValue())
assertFalse(TabsTray.closedExistingTab.testHasValue())
gleanService.track(Event.ClosedExistingTab)
assertTrue(TabsTray.closedExistingTab.testHasValue())
assertFalse(TabsTray.privateModeTapped.testHasValue())
gleanService.track(Event.TabsTrayPrivateModeTapped)
assertTrue(TabsTray.privateModeTapped.testHasValue())
assertFalse(TabsTray.normalModeTapped.testHasValue())
gleanService.track(Event.TabsTrayNormalModeTapped)
assertTrue(TabsTray.normalModeTapped.testHasValue())
assertFalse(TabsTray.syncedModeTapped.testHasValue())
gleanService.track(Event.TabsTraySyncedModeTapped)
assertTrue(TabsTray.syncedModeTapped.testHasValue())
assertFalse(TabsTray.newTabTapped.testHasValue())
gleanService.track(Event.NewTabTapped)
assertTrue(TabsTray.newTabTapped.testHasValue())
assertFalse(TabsTray.newPrivateTabTapped.testHasValue())
gleanService.track(Event.NewPrivateTabTapped)
assertTrue(TabsTray.newPrivateTabTapped.testHasValue())
assertFalse(TabsTray.menuOpened.testHasValue())
gleanService.track(Event.TabsTrayMenuOpened)
assertTrue(TabsTray.menuOpened.testHasValue())
assertFalse(TabsTray.saveToCollection.testHasValue())
gleanService.track(Event.TabsTraySaveToCollectionPressed)
assertTrue(TabsTray.saveToCollection.testHasValue())
assertFalse(TabsTray.shareAllTabs.testHasValue())
gleanService.track(Event.TabsTrayShareAllTabsPressed)
assertTrue(TabsTray.shareAllTabs.testHasValue())
assertFalse(TabsTray.closeAllTabs.testHasValue())
gleanService.track(Event.TabsTrayCloseAllTabsPressed)
assertTrue(TabsTray.closeAllTabs.testHasValue())
assertFalse(TabsTrayCfr.dismiss.testHasValue())
gleanService.track(Event.TabsTrayCfrDismissed)
assertTrue(TabsTrayCfr.dismiss.testHasValue())
assertFalse(TabsTrayCfr.goToSettings.testHasValue())
gleanService.track(Event.TabsTrayCfrTapped)
assertTrue(TabsTrayCfr.goToSettings.testHasValue())
}
} }

@ -26,7 +26,7 @@ class TabLayoutMediatorTest {
val store = createStore("123") val store = createStore("123")
val tabLayout: TabLayout = mockk(relaxed = true) val tabLayout: TabLayout = mockk(relaxed = true)
val tab: TabLayout.Tab = mockk(relaxed = true) val tab: TabLayout.Tab = mockk(relaxed = true)
val mediator = TabLayoutMediator(tabLayout, mockk(relaxed = true), store, mockk()) val mediator = TabLayoutMediator(tabLayout, mockk(relaxed = true), store, mockk(), mockk())
every { tabLayout.getTabAt(POSITION_NORMAL_TABS) }.answers { tab } every { tabLayout.getTabAt(POSITION_NORMAL_TABS) }.answers { tab }
@ -40,7 +40,7 @@ class TabLayoutMediatorTest {
val store = createStore("456") val store = createStore("456")
val tabLayout: TabLayout = mockk(relaxed = true) val tabLayout: TabLayout = mockk(relaxed = true)
val tab: TabLayout.Tab = mockk(relaxed = true) val tab: TabLayout.Tab = mockk(relaxed = true)
val mediator = TabLayoutMediator(tabLayout, mockk(relaxed = true), store, mockk()) val mediator = TabLayoutMediator(tabLayout, mockk(relaxed = true), store, mockk(), mockk())
every { tabLayout.getTabAt(POSITION_PRIVATE_TABS) }.answers { tab } every { tabLayout.getTabAt(POSITION_PRIVATE_TABS) }.answers { tab }
@ -53,7 +53,7 @@ class TabLayoutMediatorTest {
fun `lifecycle methods adds and removes observer`() { fun `lifecycle methods adds and removes observer`() {
val store = createStore("456") val store = createStore("456")
val tabLayout: TabLayout = mockk(relaxed = true) val tabLayout: TabLayout = mockk(relaxed = true)
val mediator = TabLayoutMediator(tabLayout, mockk(relaxed = true), store, mockk()) val mediator = TabLayoutMediator(tabLayout, mockk(relaxed = true), store, mockk(), mockk())
mediator.start() mediator.start()

@ -13,20 +13,24 @@ import mozilla.components.support.test.middleware.CaptureActionsMiddleware
import org.junit.Assert.assertTrue import org.junit.Assert.assertTrue
import org.junit.Before import org.junit.Before
import org.junit.Test import org.junit.Test
import org.mozilla.fenix.components.metrics.Event
import org.mozilla.fenix.components.metrics.MetricController
class TabLayoutObserverTest { class TabLayoutObserverTest {
private val interactor = mockk<TabsTrayInteractor>(relaxed = true) private val interactor = mockk<TabsTrayInteractor>(relaxed = true)
private lateinit var store: TabsTrayStore private lateinit var store: TabsTrayStore
private lateinit var metrics: MetricController
private val middleware = CaptureActionsMiddleware<TabsTrayState, TabsTrayAction>() private val middleware = CaptureActionsMiddleware<TabsTrayState, TabsTrayAction>()
@Before @Before
fun setup() { fun setup() {
store = TabsTrayStore(middlewares = listOf(middleware)) store = TabsTrayStore(middlewares = listOf(middleware))
metrics = mockk(relaxed = true)
} }
@Test @Test
fun `WHEN tab is selected THEN notify the interactor`() { fun `WHEN tab is selected THEN notify the interactor`() {
val observer = TabLayoutObserver(interactor, store) val observer = TabLayoutObserver(interactor, store, metrics)
val tab = mockk<TabLayout.Tab>() val tab = mockk<TabLayout.Tab>()
every { tab.position } returns 1 every { tab.position } returns 1
@ -35,25 +39,54 @@ class TabLayoutObserverTest {
store.waitUntilIdle() store.waitUntilIdle()
verify { interactor.setCurrentTrayPosition(1, false) } verify { interactor.setCurrentTrayPosition(1, false) }
verify { metrics.track(Event.TabsTrayPrivateModeTapped) }
middleware.assertLastAction(TabsTrayAction.PageSelected::class) { middleware.assertLastAction(TabsTrayAction.PageSelected::class) {
assertTrue(it.page == Page.PrivateTabs) assertTrue(it.page == Page.PrivateTabs)
} }
every { tab.position } returns 0
observer.onTabSelected(tab)
store.waitUntilIdle()
verify { interactor.setCurrentTrayPosition(0, true) }
verify { metrics.track(Event.TabsTrayNormalModeTapped) }
middleware.assertLastAction(TabsTrayAction.PageSelected::class) {
assertTrue(it.page == Page.NormalTabs)
}
every { tab.position } returns 2
observer.onTabSelected(tab)
store.waitUntilIdle()
verify { interactor.setCurrentTrayPosition(2, true) }
verify { metrics.track(Event.TabsTraySyncedModeTapped) }
middleware.assertLastAction(TabsTrayAction.PageSelected::class) {
assertTrue(it.page == Page.SyncedTabs)
}
} }
@Test @Test
fun `WHEN observer is first started THEN do not smooth scroll`() { fun `WHEN observer is first started THEN do not smooth scroll`() {
val store = TabsTrayStore() val store = TabsTrayStore()
val observer = TabLayoutObserver(interactor, store) val observer = TabLayoutObserver(interactor, store, metrics)
val tab = mockk<TabLayout.Tab>() val tab = mockk<TabLayout.Tab>()
every { tab.position } returns 1 every { tab.position } returns 1
observer.onTabSelected(tab) observer.onTabSelected(tab)
verify { interactor.setCurrentTrayPosition(1, false) } verify { interactor.setCurrentTrayPosition(1, false) }
verify { metrics.track(Event.TabsTrayPrivateModeTapped) }
observer.onTabSelected(tab) observer.onTabSelected(tab)
verify { interactor.setCurrentTrayPosition(1, true) } verify { interactor.setCurrentTrayPosition(1, true) }
verify { metrics.track(Event.TabsTrayPrivateModeTapped) }
} }
} }

@ -22,6 +22,7 @@ import org.junit.Before
import org.junit.Rule import org.junit.Rule
import org.junit.Test import org.junit.Test
import org.junit.runner.RunWith import org.junit.runner.RunWith
import org.mozilla.fenix.components.metrics.Event
import org.mozilla.fenix.components.metrics.MetricController import org.mozilla.fenix.components.metrics.MetricController
import org.mozilla.fenix.helpers.FenixRobolectricTestRunner import org.mozilla.fenix.helpers.FenixRobolectricTestRunner
import org.mozilla.fenix.tabstray.TabsTrayInfoBannerBinding.Companion.TAB_COUNT_SHOW_CFR import org.mozilla.fenix.tabstray.TabsTrayInfoBannerBinding.Companion.TAB_COUNT_SHOW_CFR
@ -100,9 +101,11 @@ class TabsTrayInfoBannerTest {
assert(view.visibility == VISIBLE) assert(view.visibility == VISIBLE)
binding.banner?.actionToPerform?.invoke() binding.banner?.actionToPerform?.invoke()
verify { interactor.onTabSettingsClicked() } verify(exactly = 1) { interactor.onTabSettingsClicked() }
assert(!settings.shouldShowGridViewBanner) assert(!settings.shouldShowGridViewBanner)
assert(settings.shouldShowAutoCloseTabsBanner) assert(settings.shouldShowAutoCloseTabsBanner)
verify(exactly = 1) { metrics.track(Event.TabsTrayCfrTapped) }
verify(exactly = 0) { metrics.track(Event.TabsTrayCfrDismissed) }
} }
@Test @Test
@ -130,9 +133,11 @@ class TabsTrayInfoBannerTest {
assert(view.visibility == VISIBLE) assert(view.visibility == VISIBLE)
binding.banner?.actionToPerform?.invoke() binding.banner?.actionToPerform?.invoke()
verify { interactor.onTabSettingsClicked() } verify(exactly = 1) { interactor.onTabSettingsClicked() }
assert(!settings.shouldShowGridViewBanner) assert(!settings.shouldShowGridViewBanner)
assert(!settings.shouldShowAutoCloseTabsBanner) assert(!settings.shouldShowAutoCloseTabsBanner)
verify(exactly = 1) { metrics.track(Event.TabsTrayCfrTapped) }
verify(exactly = 0) { metrics.track(Event.TabsTrayCfrDismissed) }
} }
@Test @Test
@ -162,6 +167,8 @@ class TabsTrayInfoBannerTest {
verify(exactly = 0) { interactor.onTabSettingsClicked() } verify(exactly = 0) { interactor.onTabSettingsClicked() }
assert(!settings.shouldShowGridViewBanner) assert(!settings.shouldShowGridViewBanner)
assert(settings.shouldShowAutoCloseTabsBanner) assert(settings.shouldShowAutoCloseTabsBanner)
verify(exactly = 0) { metrics.track(Event.TabsTrayCfrTapped) }
verify(exactly = 1) { metrics.track(Event.TabsTrayCfrDismissed) }
} }
@Test @Test
@ -191,6 +198,8 @@ class TabsTrayInfoBannerTest {
verify(exactly = 0) { interactor.onTabSettingsClicked() } verify(exactly = 0) { interactor.onTabSettingsClicked() }
assert(settings.shouldShowGridViewBanner) assert(settings.shouldShowGridViewBanner)
assert(!settings.shouldShowAutoCloseTabsBanner) assert(!settings.shouldShowAutoCloseTabsBanner)
verify(exactly = 0) { metrics.track(Event.TabsTrayCfrTapped) }
verify(exactly = 1) { metrics.track(Event.TabsTrayCfrDismissed) }
} }
@Test @Test

@ -16,27 +16,23 @@ import io.mockk.Called
import io.mockk.mockk import io.mockk.mockk
import io.mockk.verify import io.mockk.verify
import org.junit.Test import org.junit.Test
import org.mozilla.fenix.components.metrics.Event
import org.mozilla.fenix.components.metrics.MetricController
class TraySheetBehaviorCallbackTest { class TraySheetBehaviorCallbackTest {
@Test @Test
fun `WHEN state is hidden THEN invoke interactor`() { fun `WHEN state is hidden THEN invoke interactor`() {
val interactor = mockk<NavigationInteractor>(relaxed = true) val interactor = mockk<NavigationInteractor>(relaxed = true)
val metrics = mockk<MetricController>(relaxed = true) val callback = TraySheetBehaviorCallback(mockk(), interactor)
val callback = TraySheetBehaviorCallback(mockk(), interactor, metrics)
callback.onStateChanged(mockk(), STATE_HIDDEN) callback.onStateChanged(mockk(), STATE_HIDDEN)
verify { interactor.onTabTrayDismissed() } verify { interactor.onTabTrayDismissed() }
verify { metrics.track(Event.TabsTrayClosed) }
} }
@Test @Test
fun `WHEN state is half-expanded THEN close the tray`() { fun `WHEN state is half-expanded THEN close the tray`() {
val behavior = mockk<BottomSheetBehavior<ConstraintLayout>>(relaxed = true) val behavior = mockk<BottomSheetBehavior<ConstraintLayout>>(relaxed = true)
val callback = TraySheetBehaviorCallback(behavior, mockk(), mockk()) val callback = TraySheetBehaviorCallback(behavior, mockk())
callback.onStateChanged(mockk(), STATE_HALF_EXPANDED) callback.onStateChanged(mockk(), STATE_HALF_EXPANDED)
@ -47,9 +43,7 @@ class TraySheetBehaviorCallbackTest {
fun `WHEN other states are invoked THEN do nothing`() { fun `WHEN other states are invoked THEN do nothing`() {
val behavior = mockk<BottomSheetBehavior<ConstraintLayout>>(relaxed = true) val behavior = mockk<BottomSheetBehavior<ConstraintLayout>>(relaxed = true)
val interactor = mockk<NavigationInteractor>(relaxed = true) val interactor = mockk<NavigationInteractor>(relaxed = true)
val metrics = mockk<MetricController>(relaxed = true) val callback = TraySheetBehaviorCallback(behavior, interactor)
val callback = TraySheetBehaviorCallback(behavior, interactor, metrics)
callback.onStateChanged(mockk(), STATE_COLLAPSED) callback.onStateChanged(mockk(), STATE_COLLAPSED)
callback.onStateChanged(mockk(), STATE_DRAGGING) callback.onStateChanged(mockk(), STATE_DRAGGING)
@ -58,6 +52,5 @@ class TraySheetBehaviorCallbackTest {
verify { behavior wasNot Called } verify { behavior wasNot Called }
verify { interactor wasNot Called } verify { interactor wasNot Called }
verify { metrics wasNot Called }
} }
} }

@ -242,6 +242,7 @@ In addition to those built-in metrics, the following metrics are added to the pi
| tabs_tray.private_mode_tapped |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |A user switched to private mode |[mozilla-mobile/fenix#12036](https://github.com/mozilla-mobile/fenix/pull/12036), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)||2021-08-01 |2 | | tabs_tray.private_mode_tapped |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |A user switched to private mode |[mozilla-mobile/fenix#12036](https://github.com/mozilla-mobile/fenix/pull/12036), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)||2021-08-01 |2 |
| tabs_tray.save_to_collection |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |A user tapped the save to collection button in the tabs tray |[mozilla-mobile/fenix#12036](https://github.com/mozilla-mobile/fenix/pull/12036), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)||2021-08-01 |2 | | tabs_tray.save_to_collection |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |A user tapped the save to collection button in the tabs tray |[mozilla-mobile/fenix#12036](https://github.com/mozilla-mobile/fenix/pull/12036), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)||2021-08-01 |2 |
| tabs_tray.share_all_tabs |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |A user tapped the share all tabs button in the three dot menu within the tabs tray |[mozilla-mobile/fenix#12036](https://github.com/mozilla-mobile/fenix/pull/12036), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)||2021-08-01 |2 | | tabs_tray.share_all_tabs |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |A user tapped the share all tabs button in the three dot menu within the tabs tray |[mozilla-mobile/fenix#12036](https://github.com/mozilla-mobile/fenix/pull/12036), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)||2021-08-01 |2 |
| tabs_tray.synced_mode_tapped |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |A user switched to synced mode |[mozilla-mobile/fenix#19004](https://github.com/mozilla-mobile/fenix/pull/19004)||2022-08-01 |2 |
| tip.closed |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |The tip was closed |[mozilla-mobile/fenix#9836](https://github.com/mozilla-mobile/fenix/pull/9836), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)|<ul><li>identifier: The identifier of the tip closed</li></ul>|2021-08-01 |2 | | tip.closed |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |The tip was closed |[mozilla-mobile/fenix#9836](https://github.com/mozilla-mobile/fenix/pull/9836), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)|<ul><li>identifier: The identifier of the tip closed</li></ul>|2021-08-01 |2 |
| tip.displayed |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |The tip was displayed |[mozilla-mobile/fenix#9836](https://github.com/mozilla-mobile/fenix/pull/9836), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)|<ul><li>identifier: The identifier of the tip displayed</li></ul>|2021-08-01 |2 | | tip.displayed |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |The tip was displayed |[mozilla-mobile/fenix#9836](https://github.com/mozilla-mobile/fenix/pull/9836), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)|<ul><li>identifier: The identifier of the tip displayed</li></ul>|2021-08-01 |2 |
| tip.pressed |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |The tip's button was pressed |[mozilla-mobile/fenix#9836](https://github.com/mozilla-mobile/fenix/pull/9836), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)|<ul><li>identifier: The identifier of the tip the action was taken on</li></ul>|2021-08-01 |2 | | tip.pressed |[event](https://mozilla.github.io/glean/book/user/metrics/event.html) |The tip's button was pressed |[mozilla-mobile/fenix#9836](https://github.com/mozilla-mobile/fenix/pull/9836), [mozilla-mobile/fenix#15713](https://github.com/mozilla-mobile/fenix/pull/15713#issuecomment-703972068)|<ul><li>identifier: The identifier of the tip the action was taken on</li></ul>|2021-08-01 |2 |

Loading…
Cancel
Save