Stats: Add singular strings to weekly roundup notification

Fixes #17824
This fixes using the plural form of "view" and "comment" for singular values on Weekly roundup notifications.

Additionally, this fixes false positive test cases for
- `buildNotifications should not include likes and comments with 0 count`
- `buildNotifications should not include likes with 0 count`
- `buildNotifications should not include comments with 0 count`
- `buildNotifications should include views, likes, and comments greater than zero`
in `WeeklyRoundupNotifierTest`. Before, it was always checking `"mock_string" == "mock_string`", which was always true.

-----

## To Test:

<!-- Test instructions per dependency update: https://github.com/wordpress-mobile/WordPress-Android/blob/trunk/docs/test_instructions_per_dependency_update.md -->

1. Log in.
2. Ensure one of your top 5 sites has 1 like/comment.
3. Ensure notification permission is allowed.
4. Open Me → Debug settings.
5. Tap the menu button at the top right.
6. Tap "Force show Weekly Roundup notification" button.
7. Wait for a while, ~30 seconds.
8. Tap the Weekly Roundup notification received.
9. Verify that the notification text contains "1 comment" instead of "1 comments" and/or "1 like" instead of "1 likes".

-----

## Regression Notes

1. Potential unintended areas of impact

    - None

2. What I did to test those areas of impact (or what existing automated tests I relied on)

    - N/A

4. What automated tests I added (or what prevented me from doing so)

    - Updated `WeeklyRoundupNotifierTest`.

-----

## PR Submission Checklist:

- [x] I have completed the Regression Notes.
- [x] I have considered adding accessibility improvements for my changes.
- [x] I have considered if this change warrants user-facing release notes and have added them to `RELEASE-NOTES.txt` if necessary.

-----

## Testing Checklist (strike-out the not-applying and unnecessary ones):

- [ ] ~WordPress.com sites and self-hosted Jetpack sites.~
- [ ] ~Portrait and landscape orientations.~
- [ ] ~Light and dark modes.~
- [ ] ~Fonts: Larger, smaller and bold text.~
- [ ] ~High contrast.~
- [ ] ~Talkback.~
- [ ] ~Languages with large words or with letters/accents not frequently used in English.~
- [ ] ~Right-to-left languages. (Even if translation isn’t complete, formatting should still respect the right-to-left layout)~
- [ ] ~Large and small screen sizes. (Tablet and smaller phones)~
- [ ] ~Multi-tasking: Split screen and Pop-up view. (Android 10 or higher)~

Weekly Roundup: Add singular strings to notification
### Expected behavior
The singular form of the noun is used when the value is 1.
- view
- like
- comment

### Actual behavior
The plural form of the noun is used when the value is 1.
- views
- likes
- comments

Observed in issue WPiOS issue: https://github.com/wordpress-mobile/WordPress-iOS/issues/19994

![image](https://user-images.githubusercontent.com/2092798/214689294-f9d7aa7c-2e3f-4e19-9f9a-2105074db320.png)

### Steps to reproduce the behavior
1. Trigger a Weekly Roundup notification for a site with 1 view, comment, and or like

### Notes
- [Location of strings](https://github.com/wordpress-mobile/WordPress-Android/blob/0e366ccb920be2ae1754523c7b3d73b83840a816/WordPress/src/main/res/values/strings.xml#L4062-L4065)

##### Tested on WPAndroid 21.6

      Fails

      :no_entry_sign:
      Please add a feature label to this issue. e.g. 'Stats'

  Generated by :no_entry_sign: dangerJS

      Fails

      :no_entry_sign:
      Please add a feature label to this issue. e.g. 'Stats'

  Generated by :no_entry_sign: dangerJS

iOS issue: https://github.com/wordpress-mobile/WordPress-iOS/issues/19994
Thanks for reporting! 👍

diff --git a/WordPress/src/main/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifier.kt b/WordPress/src/main/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifier.kt
index 93d7e89bf823..0e1643e929f9 100644
--- a/WordPress/src/main/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifier.kt
+++ b/WordPress/src/main/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifier.kt
@@ -90,34 +90,56 @@ class WeeklyRoundupNotifier @Inject constructor(
     }

     private fun buildContentText(data: WeeklyRoundupData) = when {
-        data.likes <= 0 && data.comments <= 0 -> {
-            resourceProvider.getString(
-                R.string.weekly_roundup_notification_text_views_only,
-                statsUtils.toFormattedString(data.views)
-            )
-        }
-        data.likes > 0 && data.comments <= 0 -> {
-            resourceProvider.getString(
-                R.string.weekly_roundup_notification_text_views_and_likes,
-                statsUtils.toFormattedString(data.views),
-                statsUtils.toFormattedString(data.likes)
-            )
-        }
-        data.likes <= 0 && data.comments > 0 -> {
-            resourceProvider.getString(
-                R.string.weekly_roundup_notification_text_views_and_comments,
-                statsUtils.toFormattedString(data.views),
-                statsUtils.toFormattedString(data.comments)
-            )
-        }
-        else -> {
-            resourceProvider.getString(
-                R.string.weekly_roundup_notification_text_all,
-                statsUtils.toFormattedString(data.views),
-                statsUtils.toFormattedString(data.likes),
-                statsUtils.toFormattedString(data.comments)
-            )
-        }
+        data.likes <= 0 && data.comments <= 0 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_only,
+            statsUtils.toFormattedString(data.views)
+        )
+
+        data.likes.toInt() == 1 && data.comments <= 0 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_and_like,
+            statsUtils.toFormattedString(data.views)
+        )
+
+        data.likes > 0 && data.comments <= 0 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_and_likes,
+            statsUtils.toFormattedString(data.views),
+            statsUtils.toFormattedString(data.likes)
+        )
+
+        data.likes <= 0 && data.comments.toInt() == 1 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_and_comment,
+            statsUtils.toFormattedString(data.views)
+        )
+
+        data.likes <= 0 && data.comments > 0 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_and_comments,
+            statsUtils.toFormattedString(data.views),
+            statsUtils.toFormattedString(data.comments)
+        )
+
+        data.likes.toInt() == 1 && data.comments.toInt() == 1 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_like_comment,
+            statsUtils.toFormattedString(data.views)
+        )
+
+        data.likes.toInt() == 1 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_like_comments,
+            statsUtils.toFormattedString(data.views),
+            statsUtils.toFormattedString(data.comments)
+        )
+
+        data.comments.toInt() == 1 -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_views_likes_comment,
+            statsUtils.toFormattedString(data.views),
+            statsUtils.toFormattedString(data.likes)
+        )
+
+        else -> resourceProvider.getString(
+            R.string.weekly_roundup_notification_text_all,
+            statsUtils.toFormattedString(data.views),
+            statsUtils.toFormattedString(data.likes),
+            statsUtils.toFormattedString(data.comments)
+        )
     }

     companion object {
diff --git a/WordPress/src/main/res/values/strings.xml b/WordPress/src/main/res/values/strings.xml
index e93b2cd4f041..56b846ca36e6 100644
--- a/WordPress/src/main/res/values/strings.xml
+++ b/WordPress/src/main/res/values/strings.xml
@@ -4198,9 +4198,14 @@ translators: %s: Select control option value e.g: "Auto, 25%". -->
     <string name="weekly_roundup">Weekly Roundup</string>
     <string name="weekly_roundup_notification_title">Weekly Roundup: %s</string>
     <string name="weekly_roundup_notification_text_all">Last week you had %1$s views, %2$s likes, and %3$s comments.</string>
+    <string name="weekly_roundup_notification_text_views_like_comments">Last week you had %1$s views, 1 like, and %2$s comments.</string>
+    <string name="weekly_roundup_notification_text_views_likes_comment">Last week you had %1$s views, %2$s likes, and 1 comment.</string>
+    <string name="weekly_roundup_notification_text_views_like_comment">Last week you had %1$s views, 1 like, and 1 comment.</string>
     <string name="weekly_roundup_notification_text_views_only">Last week you had %1$s views.</string>
     <string name="weekly_roundup_notification_text_views_and_likes">Last week you had %1$s views and %2$s likes</string>
+    <string name="weekly_roundup_notification_text_views_and_like">Last week you had %1$s views and 1 like</string>
     <string name="weekly_roundup_notification_text_views_and_comments">Last week you had %1$s views and %2$s comments</string>
+    <string name="weekly_roundup_notification_text_views_and_comment">Last week you had %1$s views and 1 comment</string>

     <!-- About -->
     <string name="about_blog">Blog</string>

diff --git a/WordPress/src/test/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifierTest.kt b/WordPress/src/test/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifierTest.kt
index 715b35f12b73..d174010e1cda 100644
--- a/WordPress/src/test/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifierTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/workers/weeklyroundup/WeeklyRoundupNotifierTest.kt
@@ -8,6 +8,7 @@ import org.junit.runner.RunWith
 import org.mockito.junit.MockitoJUnitRunner
 import org.mockito.kotlin.any
 import org.mockito.kotlin.anyVararg
+import org.mockito.kotlin.eq
 import org.mockito.kotlin.mock
 import org.mockito.kotlin.times
 import org.mockito.kotlin.verify
@@ -39,7 +40,20 @@ class WeeklyRoundupNotifierTest : BaseUnitTest() {
     }
     private val contextProvider: ContextProvider = mock()
     private val resourceProvider: ResourceProvider = mock {
-        on { getString(any(), anyVararg()) }.thenReturn("mock_string")
+        on { getString(eq(R.string.weekly_roundup_notification_title), anyVararg()) }
+            .thenReturn("weekly_roundup_notification_title")
+        on { getString(eq(R.string.weekly_roundup_notification_text_views_only), anyVararg()) }
+            .thenReturn("weekly_roundup_notification_text_views_only")
+        on { getString(eq(R.string.weekly_roundup_notification_text_views_and_comments), anyVararg()) }
+            .thenReturn("weekly_roundup_notification_text_views_and_comments")
+        on { getString(eq(R.string.weekly_roundup_notification_text_views_and_likes), anyVararg()) }
+            .thenReturn("weekly_roundup_notification_text_views_and_likes")
+        on { getString(eq(R.string.weekly_roundup_notification_text_all), anyVararg()) }
+            .thenReturn("weekly_roundup_notification_text_all")
+        on { getString(eq(R.string.weekly_roundup_notification_text_views_likes_comment), anyVararg()) }
+            .thenReturn("weekly_roundup_notification_text_views_likes_comment")
+        on { getString(eq(R.string.weekly_roundup_notification_text_views_like_comments), anyVararg()) }
+            .thenReturn("weekly_roundup_notification_text_views_like_comments")
     }
     private val weeklyRoundupScheduler: WeeklyRoundupScheduler = mock()
     private val notificationsTracker: SystemNotificationsTracker = mock()
@@ -157,7 +171,7 @@ class WeeklyRoundupNotifierTest : BaseUnitTest() {
         val mockSites = buildMockSites()
         val data1 = buildMockData(mockSites[0], views = 10, comments = 0, likes = 0)
         val data2 = buildMockData(mockSites[1], views = 9, comments = 8, likes = 8)
-        val data3 = buildMockData(mockSites[2], views = 10, comments = 1, likes = 1)
+        val data3 = buildMockData(mockSites[2], views = 10, comments = 2, likes = 2)
         val unsortedData = listOf(data1, data2, data3)
         val sortedData = listOf(data1, data3, data2)

@@ -181,7 +195,7 @@ class WeeklyRoundupNotifierTest : BaseUnitTest() {

         val list = weeklyRoundupNotifier.buildNotifications()

-        assertThat(list.first().contentTitle).isEqualTo(
+        assertThat(list.first().contentText).isEqualTo(
             resourceProvider.getString(
                 R.string.weekly_roundup_notification_text_views_only,
                 statsUtils.toFormattedString(data!!.views)
@@ -192,14 +206,14 @@ class WeeklyRoundupNotifierTest : BaseUnitTest() {
     @Test
     fun `buildNotifications should not include likes with 0 count`() = test {
         val mockSites = buildMockSites()
-        val data = buildMockData(mockSites[2], views = 10, comments = 1, likes = 0)
+        val data = buildMockData(mockSites[2], views = 10, comments = 2, likes = 0)

         whenever(siteStore.sitesAccessedViaWPComRest).thenReturn(mockSites)
         whenever(weeklyRoundupRepository.fetchWeeklyRoundupData(any())).then { data }

         val list = weeklyRoundupNotifier.buildNotifications()

-        assertThat(list.first().contentTitle).isEqualTo(
+        assertThat(list.first().contentText).isEqualTo(
             resourceProvider.getString(
                 R.string.weekly_roundup_notification_text_views_and_comments,
                 statsUtils.toFormattedString(data!!.views),
@@ -218,7 +232,7 @@ class WeeklyRoundupNotifierTest : BaseUnitTest() {

         val list = weeklyRoundupNotifier.buildNotifications()

-        assertThat(list.first().contentTitle).isEqualTo(
+        assertThat(list.first().contentText).isEqualTo(
             resourceProvider.getString(
                 R.string.weekly_roundup_notification_text_views_and_likes,
                 statsUtils.toFormattedString(data!!.views),
@@ -237,7 +251,7 @@ class WeeklyRoundupNotifierTest : BaseUnitTest() {

         val list = weeklyRoundupNotifier.buildNotifications()

-        assertThat(list.first().contentTitle).isEqualTo(
+        assertThat(list.first().contentText).isEqualTo(
             resourceProvider.getString(
                 R.string.weekly_roundup_notification_text_all,
                 statsUtils.toFormattedString(data!!.views),
@@ -247,6 +261,44 @@ class WeeklyRoundupNotifierTest : BaseUnitTest() {
         )
     }

+    @Test
+    fun `buildNotifications should include singular comment string if the comment is one`() = test {
+        val mockSites = buildMockSites()
+        val data = buildMockData(mockSites[1], views = 9, comments = 1, likes = 8)
+
+        whenever(siteStore.sitesAccessedViaWPComRest).thenReturn(mockSites)
+        whenever(weeklyRoundupRepository.fetchWeeklyRoundupData(any())).then { data }
+
+        val list = weeklyRoundupNotifier.buildNotifications()
+
+        assertThat(list.first().contentText).isEqualTo(
+            resourceProvider.getString(
+                R.string.weekly_roundup_notification_text_views_likes_comment,
+                statsUtils.toFormattedString(data!!.views),
+                statsUtils.toFormattedString(data.likes),
+            )
+        )
+    }
+
+    @Test
+    fun `buildNotifications should include singular like string if the comment is one`() = test {
+        val mockSites = buildMockSites()
+        val data = buildMockData(mockSites[1], views = 9, comments = 8, likes = 1)
+
+        whenever(siteStore.sitesAccessedViaWPComRest).thenReturn(mockSites)
+        whenever(weeklyRoundupRepository.fetchWeeklyRoundupData(any())).then { data }
+
+        val list = weeklyRoundupNotifier.buildNotifications()
+
+        assertThat(list.first().contentText).isEqualTo(
+            resourceProvider.getString(
+                R.string.weekly_roundup_notification_text_views_like_comments,
+                statsUtils.toFormattedString(data!!.views),
+                statsUtils.toFormattedString(data.comments)
+            )
+        )
+    }
+
     private companion object {
         fun buildMockSites(quantity: Int = 3) = (1..quantity).map {
             SiteModel().apply {


[Bug] Fix root cause that caused StatsGranularTabsTest to fail.

Fixes #18065

There was a failing UI test that appeared flaky, `StatsGranularTabsTest`. Retrying appears to fix it. Every once in a while I also notice stats cards don't load properly. It's super hard to reproduce, even in UI tests.

At first I figured out part of the issue. I noticed each failing stats card would have an empty `BlockListItem` list. Each card can have multiple `BlockListItem`s. When the `StatsBlock` has no `BlockListItem`, it can't do anything, so presents itself as a card with nothing in it. This is unfortunate, but not really an issue. The real issue is why a `StatsBlock` can even have an empty list.

After further testing I learned that what leads to this issue is actually a race condition. The UI is dependent on setting the `domainModel` in `BaseStatsUseCase`. In most cases, the domain model is present quickly when we load the UI. But during UI tests situations arise where the `domainModel` takes a bit longer to load, leading to a race condition. As far as I can tell, it really only happens (or noticeable) when you first login or switch to a blog for the first time. The change I made in `BaseStatsUseCase` best illustrates why I think this fixes the issue.

When a user first loads stats, there is no cache. So it must fetch from the network. When it does that, the `domainModel` is set to the cache, which technically doesn't exist yet. This happens in `evaluateState` when a network call is made.

```
domainModel = updatedCachedData
```

It's not entirely clear to me why this is being done. In `evaluateState` if we got state back, presumably we should use that as it would be the most up-to-date. So I just tried it.

```
domainModel = state.model
```

I re-ran the previously failing UI test dozens of times. Couldn't reproduce it. I also 🚬 tested stats and don't notice any differences.

-----

## To Test:

- [ ] `StatsGranularTabTest` must pass 100% of the time. If on first pass it fails, this PR is pointless 😅 .
- [ ] 🚬 test granular stats. Make sure you load all cards and that everything looks as it did before.

-----

## Regression Notes

1. Potential unintended areas of impact

    Stats cards loading.

2. What I did to test those areas of impact (or what existing automated tests I relied on)

    Manual test and UI test.

3. What automated tests I added (or what prevented me from doing so)

    n/a

-----

## PR Submission Checklist:

- [ ] I have completed the Regression Notes.
- [ ] I have considered adding accessibility improvements for my changes.
- [ ] I have considered if this change warrants user-facing release notes and have added them to `RELEASE-NOTES.txt` if necessary.

Very first Stats card is not always loaded on screen
### Expected behavior

All stats cards that can be shown on screen should be shown after opening the screen, no PTR should be required.

### Actual behavior

1. In some cases, for JP variant (I could not reproduce this on WP), the very first Stats card is loaded only after PTR:

https://user-images.githubusercontent.com/73365754/223773395-9ed971b6-c145-4a6b-a39a-2796d9c81332.mov

2. In other cases ([example](https://buildkite.com/automattic/wordpress-android/builds/10502#01876bb0-cb7e-4fa4-bd0d-d9d8fbbea206)) the stats screen does not load at all.

This causes our `e2eAllDayStatsLoad` UI test to fail for JP.

I could not reproduce this on a real device yet.

### Steps to reproduce the behavior

1. Launch JP
2. Log in and open `Stats`
3. Open `Days` tab ~> in some cases, the first card with bar chart is loaded only after PTR.

##### Tested on `Pixel 2 API 31 Emulator`, `JPAndroid 21.8-rc-2`

I could reproduce this using a real device by testing it on a high-traffic website.  You can reproduce the issue on by testing it on mobile.blog.
I removed the "[Emulator]" label from the title.

<img src="https://github.com/wordpress-mobile/WordPress-Android/assets/2471769/ac9428e3-4a11-43da-952c-3ac6febc4c6b" width=320>

diff --git a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCase.kt b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCase.kt
index d6dd4e02c4d6..eb67940aaa83 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCase.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCase.kt
@@ -123,7 +123,7 @@ class PostDayViewsUseCase
         )
     }

-    private fun onBarSelected(period: String?) {
+    internal fun onBarSelected(period: String?) {
         if (period != null && period != "empty") {
             val selectedDate = statsDateFormatter.parseStatsDate(DAYS, period)
             selectedDateProvider.selectDate(
@@ -133,7 +133,7 @@ class PostDayViewsUseCase
         }
     }

-    private fun onBarChartDrawn(visibleBarCount: Int) {
+    internal fun onBarChartDrawn(visibleBarCount: Int) {
         updateUiState { it.copy(visibleBarCount = visibleBarCount) }
     }

diff --git a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCase.kt b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCase.kt
index 7b86388e0e3a..5183aa3f56cc 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCase.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCase.kt
@@ -91,12 +91,9 @@ abstract class BaseStatsUseCase<DOMAIN_MODEL, UI_STATE>(
         val useCaseState = when (state) {
             is Error -> ERROR
             is Data -> {
-                if (!state.cached) {
-                    val updatedCachedData = loadCachedData()
-                    if (domainModel != updatedCachedData) {
-                        domainModel = updatedCachedData
-                        updateState()
-                    }
+                if (!state.cached && domainModel != state.model) {
+                    domainModel = state.model
+                    updateState()
                 }
                 SUCCESS
             }
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCase.kt b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCase.kt
index bb5fec464a69..ac4b0355433c 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCase.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCase.kt
@@ -3,7 +3,6 @@ package org.wordpress.android.ui.stats.refresh.lists.sections.granular.usecases
 import android.view.View
 import com.google.android.material.snackbar.Snackbar
 import kotlinx.coroutines.CoroutineDispatcher
-import org.wordpress.android.BuildConfig
 import org.wordpress.android.R
 import org.wordpress.android.analytics.AnalyticsTracker
 import org.wordpress.android.fluxc.model.SiteModel
@@ -46,6 +45,7 @@ import org.wordpress.android.ui.stats.refresh.utils.StatsSiteProvider
 import org.wordpress.android.ui.stats.refresh.utils.StatsUtils
 import org.wordpress.android.ui.stats.refresh.utils.trackGranular
 import org.wordpress.android.ui.utils.ListItemInteraction.Companion.create
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.util.UrlUtils
 import org.wordpress.android.util.analytics.AnalyticsTrackerWrapper
 import org.wordpress.android.viewmodel.ResourceProvider
@@ -69,6 +69,7 @@ class ReferrersUseCase(
     private val resourceProvider: ResourceProvider,
     private val useCaseMode: UseCaseMode,
     private val popupMenuHandler: ReferrerPopupMenuHandler,
+    private val buildConfigWrapper: BuildConfigWrapper,
 ) : GranularStatefulUseCase<ReferrersModel, SelectedGroup>(
     REFERRERS,
     mainDispatcher,
@@ -122,7 +123,7 @@ class ReferrersUseCase(
             items.add(Empty(R.string.stats_no_data_for_period))
         } else {
             val header = Header(R.string.stats_referrer_label, R.string.stats_referrer_views_label)
-            if (BuildConfig.IS_JETPACK_APP && useCaseMode == BLOCK_DETAIL) {
+            if (buildConfigWrapper.isJetpackApp && useCaseMode == BLOCK_DETAIL) {
                 items.add(buildPieChartItem(domainModel))
             }
             items.add(header)
@@ -349,7 +350,8 @@ class ReferrersUseCase(
         private val statsUtils: StatsUtils,
         private val resourceProvider: ResourceProvider,
         private val analyticsTracker: AnalyticsTrackerWrapper,
-        private val popupMenuHandler: ReferrerPopupMenuHandler
+        private val popupMenuHandler: ReferrerPopupMenuHandler,
+        private val buildConfigWrapper: BuildConfigWrapper,
     ) : GranularUseCaseFactory {
         override fun build(granularity: StatsGranularity, useCaseMode: UseCaseMode) =
             ReferrersUseCase(
@@ -364,7 +366,8 @@ class ReferrersUseCase(
                 statsUtils,
                 resourceProvider,
                 useCaseMode,
-                popupMenuHandler
+                popupMenuHandler,
+                buildConfigWrapper,
             )
     }

diff --git a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCase.kt b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCase.kt
index 5cd01b0db274..44c1453a3f73 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCase.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCase.kt
@@ -2,7 +2,6 @@ package org.wordpress.android.ui.stats.refresh.lists.sections.insights.usecases

 import android.view.View
 import kotlinx.coroutines.CoroutineDispatcher
-import org.wordpress.android.BuildConfig
 import org.wordpress.android.R
 import org.wordpress.android.fluxc.model.post.PostStatus
 import org.wordpress.android.fluxc.model.stats.InsightsMostPopularModel
@@ -22,6 +21,7 @@ import org.wordpress.android.ui.stats.refresh.utils.ActionCardHandler
 import org.wordpress.android.ui.stats.refresh.utils.ItemPopupMenuHandler
 import org.wordpress.android.ui.stats.refresh.utils.StatsDateUtils
 import org.wordpress.android.ui.stats.refresh.utils.StatsSiteProvider
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.util.text.PercentFormatter
 import org.wordpress.android.viewmodel.ResourceProvider
 import java.math.RoundingMode
@@ -40,7 +40,8 @@ class MostPopularInsightsUseCase
     private val resourceProvider: ResourceProvider,
     private val popupMenuHandler: ItemPopupMenuHandler,
     private val actionCardHandler: ActionCardHandler,
-    private val percentFormatter: PercentFormatter
+    private val percentFormatter: PercentFormatter,
+    private val buildConfigWrapper: BuildConfigWrapper
 ) : StatelessUseCase<InsightsMostPopularModel>(MOST_POPULAR_DAY_AND_HOUR, mainDispatcher, backgroundDispatcher) {
     override suspend fun loadCachedData(): InsightsMostPopularModel? {
         return mostPopularStore.getMostPopularInsights(statsSiteProvider.siteModel)
@@ -71,7 +72,7 @@ class MostPopularInsightsUseCase

         val noActivity = domainModel.highestDayPercent == 0.0 && domainModel.highestHourPercent == 0.0

-        if (BuildConfig.IS_JETPACK_APP && noActivity) {
+        if (buildConfigWrapper.isJetpackApp && noActivity) {
             items.add(Empty(R.string.stats_most_popular_percent_views_empty))
         } else {
             val highestDayPercent = resourceProvider.getString(
@@ -93,7 +94,7 @@ class MostPopularInsightsUseCase
                     Column(
                         R.string.stats_insights_best_day,
                         statsDateUtils.getWeekDay(domainModel.highestDayOfWeek),
-                        if (BuildConfig.IS_JETPACK_APP) {
+                        if (buildConfigWrapper.isJetpackApp) {
                             highestDayPercent
                         } else {
                             null
@@ -103,7 +104,7 @@ class MostPopularInsightsUseCase
                     Column(
                         R.string.stats_insights_best_hour,
                         statsDateUtils.getHour(domainModel.highestHour),
-                        if (BuildConfig.IS_JETPACK_APP) {
+                        if (buildConfigWrapper.isJetpackApp) {
                             highestHourPercent
                         } else {
                             null
@@ -114,7 +115,7 @@ class MostPopularInsightsUseCase
             )
         }

-        if (BuildConfig.IS_JETPACK_APP) {
+        if (buildConfigWrapper.isJetpackApp) {
             addActionCards(domainModel)
         }
         return items
@@ -131,12 +132,12 @@ class MostPopularInsightsUseCase
     }

     private fun buildTitle() = Title(
-        textResource = if (BuildConfig.IS_JETPACK_APP) {
+        textResource = if (buildConfigWrapper.isJetpackApp) {
             R.string.stats_insights_popular_title
         } else {
             R.string.stats_insights_popular
         },
-        menuAction = if (BuildConfig.IS_JETPACK_APP) {
+        menuAction = if (buildConfigWrapper.isJetpackApp) {
             null
         } else {
             this::onMenuClick
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModel.kt b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModel.kt
index 451b2f5df2e4..2eb64bdd5ca6 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModel.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModel.kt
@@ -5,11 +5,11 @@ import androidx.annotation.StringRes
 import androidx.lifecycle.LiveData
 import androidx.lifecycle.MutableLiveData
 import kotlinx.coroutines.CoroutineDispatcher
-import org.wordpress.android.BuildConfig
 import org.wordpress.android.R
 import org.wordpress.android.fluxc.store.AccountStore
 import org.wordpress.android.modules.UI_THREAD
 import org.wordpress.android.ui.prefs.AppPrefsWrapper
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.viewmodel.Event
 import org.wordpress.android.viewmodel.ScopedViewModel
 import javax.inject.Inject
@@ -19,7 +19,8 @@ class StatsColorSelectionViewModel
 @Inject constructor(
     @Named(UI_THREAD) private val mainDispatcher: CoroutineDispatcher,
     private val accountStore: AccountStore,
-    private val appPrefsWrapper: AppPrefsWrapper
+    private val appPrefsWrapper: AppPrefsWrapper,
+    private val buildConfigWrapper: BuildConfigWrapper,
 ) : ScopedViewModel(mainDispatcher) {
     private val mutableViewMode = MutableLiveData<Color>()
     val viewMode: LiveData<Color> = mutableViewMode
@@ -51,7 +52,7 @@ class StatsColorSelectionViewModel
         if (accountStore.hasAccessToken()) {
             mutableDialogOpened.postValue(Event(Unit))
         } else {
-            val message = if (BuildConfig.IS_JETPACK_APP) {
+            val message = if (buildConfigWrapper.isJetpackApp) {
                 R.string.stats_widget_log_in_to_add_message
             } else {
                 R.string.stats_widget_log_in_message
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModel.kt b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModel.kt
index b5ead27c8074..d96334ae7c9f 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModel.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModel.kt
@@ -3,13 +3,13 @@ package org.wordpress.android.ui.stats.refresh.lists.widget.configuration
 import androidx.lifecycle.LiveData
 import androidx.lifecycle.MutableLiveData
 import kotlinx.coroutines.CoroutineDispatcher
-import org.wordpress.android.BuildConfig
 import org.wordpress.android.R
 import org.wordpress.android.fluxc.model.SiteModel
 import org.wordpress.android.fluxc.store.AccountStore
 import org.wordpress.android.fluxc.store.SiteStore
 import org.wordpress.android.modules.UI_THREAD
 import org.wordpress.android.ui.prefs.AppPrefsWrapper
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.util.SiteUtils
 import org.wordpress.android.viewmodel.Event
 import org.wordpress.android.viewmodel.ScopedViewModel
@@ -21,7 +21,8 @@ class StatsSiteSelectionViewModel
     @Named(UI_THREAD) private val mainDispatcher: CoroutineDispatcher,
     private val siteStore: SiteStore,
     private val accountStore: AccountStore,
-    private val appPrefsWrapper: AppPrefsWrapper
+    private val appPrefsWrapper: AppPrefsWrapper,
+    private val buildConfigWrapper: BuildConfigWrapper,
 ) : ScopedViewModel(mainDispatcher) {
     private val mutableSelectedSite = MutableLiveData<SiteUiModel>()
     val selectedSite: LiveData<SiteUiModel> = mutableSelectedSite
@@ -73,7 +74,7 @@ class StatsSiteSelectionViewModel
         if (accountStore.hasAccessToken()) {
             mutableDialogOpened.postValue(Event(Unit))
         } else {
-            val message = if (BuildConfig.IS_JETPACK_APP) {
+            val message = if (buildConfigWrapper.isJetpackApp) {
                 R.string.stats_widget_log_in_to_add_message
             } else {
                 R.string.stats_widget_log_in_message

diff --git a/WordPress/src/androidTest/java/org/wordpress/android/e2e/StatsGranularTabsTest.kt b/WordPress/src/androidTest/java/org/wordpress/android/e2e/StatsGranularTabsTest.kt
index 89b11f852e76..ada96b9c90c6 100644
--- a/WordPress/src/androidTest/java/org/wordpress/android/e2e/StatsGranularTabsTest.kt
+++ b/WordPress/src/androidTest/java/org/wordpress/android/e2e/StatsGranularTabsTest.kt
@@ -6,12 +6,10 @@ import dagger.hilt.android.testing.HiltAndroidTest
 import org.junit.After
 import org.junit.Assume.assumeTrue
 import org.junit.Before
-import org.junit.Ignore
 import org.junit.Test
 import org.wordpress.android.BuildConfig
 import org.wordpress.android.R
 import org.wordpress.android.e2e.pages.MySitesPage
-import org.wordpress.android.rules.Retry
 import org.wordpress.android.support.BaseTest
 import org.wordpress.android.support.ComposeEspressoLink
 import org.wordpress.android.support.WPSupportUtils
@@ -38,7 +36,6 @@ class StatsGranularTabsTest : BaseTest() {
         }
     }

-    @Ignore("The 'Days' screen might occasionally not load. Disabled until tests rerun is implemented.")
     @Test
     fun e2eAllDayStatsLoad() {
         val todayVisits = StatsVisitsData("97", "28", "14", "11")
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCase.kt b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCase.kt
index 3efbedcfd70e..c6ad8c0df460 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCase.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCase.kt
@@ -2,7 +2,6 @@ package org.wordpress.android.ui.stats.refresh.lists.sections.insights.usecases

 import android.view.View
 import kotlinx.coroutines.CoroutineDispatcher
-import org.wordpress.android.BuildConfig
 import org.wordpress.android.R
 import org.wordpress.android.analytics.AnalyticsTracker.Stat.STATS_LATEST_POST_SUMMARY_ADD_NEW_POST_TAPPED
 import org.wordpress.android.analytics.AnalyticsTracker.Stat.STATS_LATEST_POST_SUMMARY_POST_ITEM_TAPPED
@@ -32,6 +31,7 @@ import org.wordpress.android.ui.stats.refresh.utils.MILLION
 import org.wordpress.android.ui.stats.refresh.utils.StatsSiteProvider
 import org.wordpress.android.ui.stats.refresh.utils.StatsUtils
 import org.wordpress.android.ui.utils.ListItemInteraction
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.util.analytics.AnalyticsTrackerWrapper
 import javax.inject.Inject
 import javax.inject.Named
@@ -46,7 +46,8 @@ class LatestPostSummaryUseCase
     private val analyticsTracker: AnalyticsTrackerWrapper,
     private val popupMenuHandler: ItemPopupMenuHandler,
     private val statsUtils: StatsUtils,
-    private val contentDescriptionHelper: ContentDescriptionHelper
+    private val contentDescriptionHelper: ContentDescriptionHelper,
+    private val buildConfigWrapper: BuildConfigWrapper
 ) : StatelessUseCase<InsightsLatestPostModel>(LATEST_POST_SUMMARY, mainDispatcher, backgroundDispatcher) {
     override suspend fun loadCachedData(): InsightsLatestPostModel? {
         return latestPostStore.getLatestPostInsights(statsSiteProvider.siteModel)
@@ -79,7 +80,7 @@ class LatestPostSummaryUseCase
     private fun buildNullableUiModel(domainModel: InsightsLatestPostModel?): MutableList<BlockListItem> {
         val items = mutableListOf<BlockListItem>()

-        if (BuildConfig.IS_JETPACK_APP) {
+        if (buildConfigWrapper.isJetpackApp) {
             items.add(buildTitleViewMore(domainModel))
             items.add(latestPostSummaryMapper.buildLatestPostItem(domainModel))
             if (domainModel != null && domainModel.hasData()) items.add(buildQuickScanItems(domainModel))
@@ -185,7 +186,7 @@ class LatestPostSummaryUseCase
                 navigateAction = ListItemInteraction.create(this::onAddNewPostClick)
             )
             model.hasData() -> {
-                if (!BuildConfig.IS_JETPACK_APP) {
+                if (!buildConfigWrapper.isJetpackApp) {
                     Link(
                         text = R.string.stats_insights_view_more,
                         navigateAction = ListItemInteraction.create(
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCaseTest.kt
index 9792f35ef772..0197ebd87e06 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/detail/PostDayViewsUseCaseTest.kt
@@ -129,31 +129,6 @@ class PostDayViewsUseCaseTest : BaseUnitTest() {
         assertThat(result.state).isEqualTo(ERROR)
     }

-    /**
-     * Note that this test covers an edge condition tracked in GitHub issue
-     * https://github.com/wordpress-mobile/WordPress-Android/issues/10830
-     * For some context see
-     * See https://github.com/wordpress-mobile/WordPress-Android/pull/10850#issuecomment-559555035
-     */
-    @Test
-    fun `manage edge condition with data available but empty list`() = test {
-        val forced = false
-
-        whenever(emptyModel.dayViews).thenReturn(listOf())
-        whenever(model.dayViews).thenReturn(listOf(Day("2019-10-10", 50)))
-        whenever(store.getPostDetail(site, postId)).thenReturn(emptyModel)
-        whenever(store.fetchPostDetail(site, postId, forced)).thenReturn(
-            OnStatsFetched(
-                model
-            )
-        )
-
-        val result = loadData(true, forced)
-
-        assertThat(result.state).isEqualTo(SUCCESS)
-        assertThat(result.data).isEmpty()
-    }
-
     @Test
     fun `maps list of empty items to empty UI model`() = test {
         val forced = false
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCaseTest.kt
index e03287cbac32..ba91233d9637 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/BaseStatsUseCaseTest.kt
@@ -49,17 +49,17 @@ class BaseStatsUseCaseTest : BaseUnitTest() {
     }

     @Test
-    fun `on fetch loads data from DB when current value is null`() = test {
+    fun `on fetch loads data from remote when current value is null`() = test {
         assertThat(result).isEmpty()

         block.fetch(false, false)
         advanceUntilIdle()

-        assertData(0, localData)
+        assertData(0, remoteData)
     }

     @Test
-    fun `on fetch returns null item when DB is empty`() = test {
+    fun `on fetch returns remote data when DB is empty`() = test {
         assertThat(result).isEmpty()
         whenever(localDataProvider.get()).thenReturn(null)

@@ -67,19 +67,19 @@ class BaseStatsUseCaseTest : BaseUnitTest() {
         advanceUntilIdle()

         assertThat(result).hasSize(1)
-        assertThat(result[0]!!.data).isNull()
+        assertData(0, remoteData)
         assertThat(result[0]!!.state).isEqualTo(UseCaseState.SUCCESS)
     }

     @Test
-    fun `on refresh calls loads data from DB and later from API`() = test {
+    fun `on refresh calls loads data from API`() = test {
         assertThat(result).isEmpty()

         block.fetch(true, false)
         advanceUntilIdle()

         assertThat(result.size).isEqualTo(1)
-        assertData(0, localData)
+        assertData(0, remoteData)
     }

     @Test
@@ -87,7 +87,7 @@ class BaseStatsUseCaseTest : BaseUnitTest() {
         block.fetch(false, false)
         advanceUntilIdle()

-        assertData(0, localData)
+        assertData(0, remoteData)

         block.clear()
         advanceUntilIdle()
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/OverviewUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/OverviewUseCaseTest.kt
index 5a790d0e13d9..8b83e8eac40a 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/OverviewUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/OverviewUseCaseTest.kt
@@ -135,7 +135,8 @@ class OverviewUseCaseTest : BaseUnitTest() {
             assertThat(this[1]).isEqualTo(barChartItem)
             assertThat(this[2]).isEqualTo(columns)
         }
-        verify(statsWidgetUpdaters, times(2)).updateViewsWidget(siteId)
+        verify(statsWidgetUpdaters, times(1)).updateViewsWidget(siteId)
+        verify(statsWidgetUpdaters, times(1)).updateWeekViewsWidget(siteId)
     }

     @Test
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCaseTest.kt
index 661d153d5bfa..78168bce0520 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/granular/usecases/ReferrersUseCaseTest.kt
@@ -43,6 +43,7 @@ import org.wordpress.android.ui.stats.refresh.utils.ContentDescriptionHelper
 import org.wordpress.android.ui.stats.refresh.utils.ReferrerPopupMenuHandler
 import org.wordpress.android.ui.stats.refresh.utils.StatsSiteProvider
 import org.wordpress.android.ui.stats.refresh.utils.StatsUtils
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.util.analytics.AnalyticsTrackerWrapper
 import org.wordpress.android.viewmodel.ResourceProvider
 import java.util.Date
@@ -118,6 +119,9 @@ class ReferrersUseCaseTest : BaseUnitTest() {
     )
     private val contentDescription = "title, views"

+    @Mock
+    private lateinit var buildConfigWrapper: BuildConfigWrapper
+
     @Before
     fun setUp() {
         useCase = ReferrersUseCase(
@@ -132,7 +136,8 @@ class ReferrersUseCaseTest : BaseUnitTest() {
             statsUtils,
             resourceProvider,
             BLOCK_DETAIL,
-            popupMenuHandler
+            popupMenuHandler,
+            buildConfigWrapper,
         )
         whenever(statsSiteProvider.siteModel).thenReturn(site)
         whenever((selectedDateProvider.getSelectedDate(statsGranularity))).thenReturn(selectedDate)
@@ -150,6 +155,7 @@ class ReferrersUseCaseTest : BaseUnitTest() {
             )
         ).thenReturn(contentDescription)
         whenever(statsUtils.toFormattedString(any<Int>(), any())).then { (it.arguments[0] as Int).toString() }
+        whenever(buildConfigWrapper.isJetpackApp).thenReturn(false)
     }

     @Test
@@ -226,7 +232,8 @@ class ReferrersUseCaseTest : BaseUnitTest() {
             statsUtils,
             resourceProvider,
             BLOCK,
-            popupMenuHandler
+            popupMenuHandler,
+            buildConfigWrapper,
         )

         val forced = false
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/AllTimeStatsUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/AllTimeStatsUseCaseTest.kt
index d6ccb4117fe9..a7990c229632 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/AllTimeStatsUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/AllTimeStatsUseCaseTest.kt
@@ -153,7 +153,7 @@ class AllTimeStatsUseCaseTest : BaseUnitTest() {
             assertThat(this.endColumn.value).isEqualTo(viewsBestDayTotal.toString())
             assertThat(this.endColumn.highest).isEqualTo(bestDayTransformed)
         }
-        verify(statsWidgetUpdaters, times(2)).updateAllTimeWidget(siteId)
+        verify(statsWidgetUpdaters, times(1)).updateAllTimeWidget(siteId)
     }

     @Test
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/FollowersUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/FollowersUseCaseTest.kt
index 3b4ceece7c29..186af514fcd2 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/FollowersUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/FollowersUseCaseTest.kt
@@ -319,7 +319,6 @@ class FollowersUseCaseTest : BaseUnitTest() {

         useCase.liveData.observeForever { if (it != null) updatedResult = it }

-        whenever(insightsStore.getEmailFollowers(site, LimitMode.All)).thenReturn(updatedEmailModel)
         button.loadMore()
         updatedResult.data!!.assertViewAllFollowersSecondLoad()
     }
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCaseTest.kt
index 24bdf9be4052..6f8344be1b52 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/LatestPostSummaryUseCaseTest.kt
@@ -32,6 +32,7 @@ import org.wordpress.android.ui.stats.refresh.utils.ContentDescriptionHelper
 import org.wordpress.android.ui.stats.refresh.utils.ItemPopupMenuHandler
 import org.wordpress.android.ui.stats.refresh.utils.StatsSiteProvider
 import org.wordpress.android.ui.stats.refresh.utils.StatsUtils
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.util.analytics.AnalyticsTrackerWrapper
 import java.util.Date

@@ -62,6 +63,9 @@ class LatestPostSummaryUseCaseTest : BaseUnitTest() {
     lateinit var statsUtils: StatsUtils
     private lateinit var useCase: LatestPostSummaryUseCase

+    @Mock
+    private lateinit var buildConfigWrapper: BuildConfigWrapper
+
     @Before
     fun setUp() = test {
         useCase = LatestPostSummaryUseCase(
@@ -73,7 +77,8 @@ class LatestPostSummaryUseCaseTest : BaseUnitTest() {
             tracker,
             popupMenuHandler,
             statsUtils,
-            contentDescriptionHelper
+            contentDescriptionHelper,
+            buildConfigWrapper
         )
         whenever(statsSiteProvider.siteModel).thenReturn(site)
         useCase.navigationTarget.observeForever {}
@@ -84,6 +89,7 @@ class LatestPostSummaryUseCaseTest : BaseUnitTest() {
             )
         ).thenReturn("likes: 10")
         whenever(statsUtils.toFormattedString(any<Int>(), any())).then { (it.arguments[0] as Int).toString() }
+        whenever(buildConfigWrapper.isJetpackApp).thenReturn(false)
     }

     @Test
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCaseTest.kt
index 1e49d0200e08..bc7a973ee75f 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/MostPopularInsightsUseCaseTest.kt
@@ -27,6 +27,7 @@ import org.wordpress.android.ui.stats.refresh.utils.ActionCardHandler
 import org.wordpress.android.ui.stats.refresh.utils.ItemPopupMenuHandler
 import org.wordpress.android.ui.stats.refresh.utils.StatsDateUtils
 import org.wordpress.android.ui.stats.refresh.utils.StatsSiteProvider
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.util.text.PercentFormatter
 import org.wordpress.android.viewmodel.ResourceProvider
 import java.math.RoundingMode
@@ -59,6 +60,9 @@ class MostPopularInsightsUseCaseTest : BaseUnitTest() {
     @Mock
     lateinit var actionCardHandler: ActionCardHandler

+    @Mock
+    private lateinit var buildConfigWrapper: BuildConfigWrapper
+
     @Mock
     private lateinit var percentFormatter: PercentFormatter
     private lateinit var useCase: MostPopularInsightsUseCase
@@ -81,7 +85,8 @@ class MostPopularInsightsUseCaseTest : BaseUnitTest() {
             resourceProvider,
             popupMenuHandler,
             actionCardHandler,
-            percentFormatter
+            percentFormatter,
+            buildConfigWrapper
         )
         whenever(
             percentFormatter.format(
@@ -111,6 +116,7 @@ class MostPopularInsightsUseCaseTest : BaseUnitTest() {
                 R.string.stats_most_popular_percent_views, "20%"
             )
         ).thenReturn("${highestHourPercent.roundToInt()}% of views")
+        whenever(buildConfigWrapper.isJetpackApp).thenReturn(false)
     }

     @Test
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/TodayStatsUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/TodayStatsUseCaseTest.kt
index 847e6723f129..4ea94dd04126 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/TodayStatsUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/TodayStatsUseCaseTest.kt
@@ -92,7 +92,7 @@ class TodayStatsUseCaseTest : BaseUnitTest() {
             assertViewsAndVisitors(this[1])
             assertLikesAndComments(this[2])
         }
-        verify(statsWidgetUpdaters, times(2)).updateTodayWidget(siteId)
+        verify(statsWidgetUpdaters, times(1)).updateTodayWidget(siteId)
     }

     @Test
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/ViewsAndVisitorsUseCaseTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/ViewsAndVisitorsUseCaseTest.kt
index 0c65f1914b49..8aed8d5d0335 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/ViewsAndVisitorsUseCaseTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/sections/insights/usecases/ViewsAndVisitorsUseCaseTest.kt
@@ -145,7 +145,7 @@ class ViewsAndVisitorsUseCaseTest : BaseUnitTest() {
             Assertions.assertThat(this[3]).isEqualTo(lineChartItem)
             Assertions.assertThat(this[5]).isEqualTo(chips)
         }
-        verify(statsWidgetUpdaters, times(2)).updateViewsWidget(siteId)
+        verify(statsWidgetUpdaters, times(1)).updateViewsWidget(siteId)
     }

     @Test
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModelTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModelTest.kt
index 2835cbdcd8de..7d1a79cc7fcc 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModelTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsColorSelectionViewModelTest.kt
@@ -14,6 +14,7 @@ import org.wordpress.android.ui.prefs.AppPrefsWrapper
 import org.wordpress.android.ui.stats.refresh.lists.widget.configuration.StatsColorSelectionViewModel.Color
 import org.wordpress.android.ui.stats.refresh.lists.widget.configuration.StatsColorSelectionViewModel.Color.DARK
 import org.wordpress.android.ui.stats.refresh.lists.widget.configuration.StatsColorSelectionViewModel.Color.LIGHT
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.viewmodel.Event

 @ExperimentalCoroutinesApi
@@ -25,13 +26,18 @@ class StatsColorSelectionViewModelTest : BaseUnitTest() {
     private lateinit var accountStore: AccountStore
     private lateinit var viewModel: StatsColorSelectionViewModel

+    @Mock
+    private lateinit var buildConfigWrapper: BuildConfigWrapper
+
     @Before
     fun setUp() {
         viewModel = StatsColorSelectionViewModel(
             testDispatcher(),
             accountStore,
-            appPrefsWrapper
+            appPrefsWrapper,
+            buildConfigWrapper,
         )
+        whenever(buildConfigWrapper.isJetpackApp).thenReturn(false)
     }

     @Test
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModelTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModelTest.kt
index 39e5176fed99..5b14f3b07320 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModelTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/stats/refresh/lists/widget/configuration/StatsSiteSelectionViewModelTest.kt
@@ -13,6 +13,7 @@ import org.wordpress.android.fluxc.store.AccountStore
 import org.wordpress.android.fluxc.store.SiteStore
 import org.wordpress.android.ui.prefs.AppPrefsWrapper
 import org.wordpress.android.ui.stats.refresh.lists.widget.configuration.StatsSiteSelectionViewModel.SiteUiModel
+import org.wordpress.android.util.BuildConfigWrapper
 import org.wordpress.android.viewmodel.Event

 @ExperimentalCoroutinesApi
@@ -36,13 +37,17 @@ class StatsSiteSelectionViewModelTest : BaseUnitTest() {
     private val siteUrl = "wordpress.com"
     private val iconUrl = "icon.jpg"

+    @Mock
+    private lateinit var buildConfigWrapper: BuildConfigWrapper
+
     @Before
     fun setUp() {
         viewModel = StatsSiteSelectionViewModel(
             testDispatcher(),
             siteStore,
             accountStore,
-            appPrefsWrapper
+            appPrefsWrapper,
+            buildConfigWrapper,
         )
         wpComSite = SiteModel()
         wpComSite.siteId = siteId
@@ -65,6 +70,7 @@ class StatsSiteSelectionViewModelTest : BaseUnitTest() {
         nonJetpackSite.iconUrl = iconUrl
         nonJetpackSite.setIsJetpackConnected(false)
         nonJetpackSite.setIsWPCom(false)
+        whenever(buildConfigWrapper.isJetpackApp).thenReturn(false)
     }

     @Test


Removes multiple calls to the WebSettings.getDefaultUserAgent api

Fixes #12259

## Description
This PR replaces multiple calls to the `WebSettings.getDefaultUserAgent`([which is not recommended](https://issuetracker.google.com/issues/289118199#comment9)) with just one, hoping to prevent the ANR of #12259 and probably reduce the crash count in #20147

The current implementation is making 27 calls to the `WebSettings.getDefaultUserAgent` function during the app startup and more later. One of those was in [the AppInitialiser](https://github.com/wordpress-mobile/WordPress-Android/blob/trunk/WordPress/src/main/java/org/wordpress/android/AppInitializer.kt#L1063) and the rest were calls to [the AppConfigModule](https://github.com/wordpress-mobile/WordPress-Android/blob/trunk/WordPress/src/main/java/org/wordpress/android/modules/AppConfigModule.java#L30) that uses [the FluxC implementation](https://github.com/wordpress-mobile/WordPress-FluxC-Android/blob/trunk/fluxc/src/main/java/org/wordpress/android/fluxc/network/UserAgent.kt).

Since I wasn't able to reproduce the ANR my plan is to monitor how this fix would affect the occurrences of the issue. If the issue persist I would probably try a more drastic approach of changing the user agent used for the api calls and keep the full user agent using the `WebSettings.getDefaultUserAgent` only for the WebViews.

Internal ref: pcdRpT-5Us-p2#comment-9676

-----

## To Test:
* Since this PR should not change the behaviour of the app but the refactored code affects all network calls a sanity check of the app is recommended.
* Test Jetpack and WordPress, rest and xmlrpc
* Verify that the `AppInitializer.userAgentString` is [logged correctly](https://github.com/wordpress-mobile/WordPress-Android/blob/fix/12259-userAgent/WordPress/src/main/java/org/wordpress/android/AppInitializer.kt#L368)
-----

## Regression Notes

1. Potential unintended areas of impact

    - All Networking 😅

2. What I did to test those areas of impact (or what existing automated tests I relied on)

    - Manual testing

3. What automated tests I added (or what prevented me from doing so)

    - Updated an existing test

-----

## PR Submission Checklist:

- [x] I have completed the Regression Notes.
- [x] I have considered adding accessibility improvements for my changes.
- [x] I have considered if this change warrants user-facing release notes and have added them to `RELEASE-NOTES.txt` if necessary.

-----

## Testing Checklist (strike-out the not-applying and unnecessary ones):

- [ ] WordPress.com sites and self-hosted Jetpack sites.
- [ ] Portrait and landscape orientations.
- [ ] Light and dark modes.
- [ ] Fonts: Larger, smaller and bold text.
- [ ] High contrast.
- [ ] Talkback.
- [ ] Languages with large words or with letters/accents not frequently used in English.
- [ ] Right-to-left languages. (Even if translation isn’t complete, formatting should still respect the right-to-left layout)
- [ ] Large and small screen sizes. (Tablet and smaller phones)
- [ ] Multi-tasking: Split screen and Pop-up view. (Android 10 or higher)

ApplicationNotResponding in UserAgent

ApplicationNotResponding in UserAgent
ANRs weren't available in Sentry until the last release, so this issue is not newly introduced. Please keep that in mind while debugging the issue so as not to limit it to the changes introduced recently.

**Sentry Url**: https://sentry.io/share/issue/09ee294fc5b3453bb0b2920117ae4387/
**User Count**: 712
**Count**: 1339
**First Release**: org.wordpress.android@15.0-rc-1+874
**First Seen**: 2020-06-03T13:44:42.073000Z
**Last Seen**: 2020-06-24T01:23:36Z
**24 Hours**: 296
**30 Days**: 1334

```
ApplicationNotResponding: Application Not Responding for at least 5000 ms.
     at org.wordpress.android.fluxc.network.UserAgent.<init>(UserAgent.java:18)
     at org.wordpress.android.modules.AppConfigModule.provideUserAgent(AppConfigModule.java:22)
     at org.wordpress.android.modules.AppConfigModule_ProvideUserAgentFactory.provideUserAgent(AppConfigModule_ProvideUserAgentFactory.java:37)
     at org.wordpress.android.modules.AppConfigModule_ProvideUserAgentFactory.get(AppConfigModule_ProvideUserAgentFactory.java:27)
     at org.wordpress.android.modules.AppConfigModule_ProvideUserAgentFactory.get(AppConfigModule_ProvideUserAgentFactory.java:10)
     at org.wordpress.android.fluxc.module.ReleaseNetworkModule_ProvideAccountRestClientFactory.get(ReleaseNetworkModule_ProvideAccountRestClientFactory.java:61)
     at org.wordpress.android.fluxc.module.ReleaseNetworkModule_ProvideAccountRestClientFactory.get(ReleaseNetworkModule_ProvideAccountRestClientFactory.java:15)
     at org.wordpress.android.fluxc.store.AccountStore_Factory.get(AccountStore_Factory.java:44)
     at org.wordpress.android.fluxc.store.AccountStore_Factory.get(AccountStore_Factory.java:12)
     at org.wordpress.android.modules.DaggerAppComponent.injectWordPress(DaggerAppComponent.java:5578)
...
(28 additional frame(s) were not displayed)
```

This issue has been marked as stale because:

 * It has been inactive for the past year.
 * It isn't in a project or a milestone.
 * It hasn’t been labeled `[Pri] Blocker`, `[Pri] High`, or `good first issue`.

Please comment with an update if you believe this issue is still valid or if it can be closed. This issue will also be reviewed for validity and priority during regularly scheduled triage sessions.

Sentry Issue: [WORDPRESS-ANDROID-2VFK](https://a8c.sentry.io/issues/5001030238/?referrer=github_integration)
Thanks for reporting! 👍 <!-- generated_by_dangermattic -->

Probably fixed with https://github.com/wordpress-mobile/WordPress-Android/pull/20296 since there are no occurrences after `24.3.1`. Feel free to reopen if the issue persist
Sentry Issue: [JETPACK-ANDROID-P3K](https://a8c.sentry.io/issues/5132003514/?referrer=github_integration)
Sentry Issue: [WORDPRESS-ANDROID-2VYY](https://a8c.sentry.io/issues/5052740778/?referrer=github_integration)
Sentry Issue: [JETPACK-ANDROID-NWK](https://a8c.sentry.io/issues/5124816194/?referrer=github_integration)
> Probably fixed with https://github.com/wordpress-mobile/WordPress-Android/pull/20296 since there are no occurrences after 24.3.1. Feel free to reopen if the issue persist

I'm reopening this issue since the ANR still persist after the fix and is related to a know limitation of the `getDefaultUserAgent` call https://issuetracker.google.com/issues/289118199#comment9

The issue seems to occur almost exclusively on low end devices.
Sentry Issue: [WORDPRESS-ANDROID-23MM](https://a8c.sentry.io/issues/3312111479/?referrer=github_integration)
Sentry Issue: [JETPACK-ANDROID-N3J](https://a8c.sentry.io/issues/5095961906/?referrer=github_integration)
Sentry Issue: [WORDPRESS-ANDROID-2WA6](https://a8c.sentry.io/issues/5083633345/?referrer=github_integration)
Sentry Issue: [WORDPRESS-ANDROID-2WCX](https://a8c.sentry.io/issues/5089808627/?referrer=github_integration)
Sentry Issue: [WORDPRESS-ANDROID-2WA4](https://a8c.sentry.io/issues/5083460695/?referrer=github_integration)
The ANR roots in two places:

1. [The AppConfigModule](https://github.com/wordpress-mobile/WordPress-Android/blob/trunk/WordPress/src/main/java/org/wordpress/android/modules/AppConfigModule.java#L30) that uses [the FluxC implemantation](https://github.com/wordpress-mobile/WordPress-FluxC-Android/blob/trunk/fluxc/src/main/java/org/wordpress/android/fluxc/network/UserAgent.kt).
```
io.sentry.android.core.ApplicationNotResponding: Background ANR
    at java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:509)
    at WV.ir.<init>(chromium-TrichromeWebViewGoogle6432.aab-stable-626111933:43)
    at WV.rC.<init>(chromium-TrichromeWebViewGoogle6432.aab-stable-626111933:8)
    at org.chromium.android_webview.AwBrowserProcess.f(chromium-TrichromeWebViewGoogle6432.aab-stable-626111933:106)
    at com.android.webview.chromium.M.e(chromium-TrichromeWebViewGoogle6432.aab-stable-626111933:208)
    at com.android.webview.chromium.M.b(chromium-TrichromeWebViewGoogle6432.aab-stable-626111933:42)
    at com.android.webview.chromium.WebViewChromiumFactoryProvider.getStatics(chromium-TrichromeWebViewGoogle6432.aab-stable-626111933:16)
    at android.webkit.WebSettings.getDefaultUserAgent(WebSettings.java:1355)
    at org.wordpress.android.fluxc.network.UserAgent.<init>(UserAgent.kt:17)
    at org.wordpress.android.modules.AppConfigModule.provideUserAgent(AppConfigModule.java:30)
```

2. [The AppInitialiser](https://github.com/wordpress-mobile/WordPress-Android/blob/trunk/WordPress/src/main/java/org/wordpress/android/AppInitializer.kt#L1063).
```
io.sentry.android.core.ApplicationNotResponding: Background ANR
    at android.webkit.WebViewFactory.getProvider(WebViewFactory.java:227)
    at android.webkit.WebSettings.getDefaultUserAgent(WebSettings.java:1355)
    at org.wordpress.android.AppInitializer$Companion$defaultUserAgent$2.invoke(AppInitializer.kt:1065)
    at org.wordpress.android.AppInitializer$Companion$defaultUserAgent$2.invoke(AppInitializer.kt:1063)
    at kotlin.SynchronizedLazyImpl.getValue(LazyJVM.kt:74)
    at org.wordpress.android.AppInitializer$Companion.getDefaultUserAgent(AppInitializer.kt:1063)
    at org.wordpress.android.AppInitializer$Companion$userAgent$2.invoke(AppInitializer.kt:1097)
    at org.wordpress.android.AppInitializer$Companion$userAgent$2.invoke(AppInitializer.kt:1096)
    at kotlin.SynchronizedLazyImpl.getValue(LazyJVM.kt:74)
    at org.wordpress.android.AppInitializer$Companion.getUserAgent(AppInitializer.kt:1096)
    at org.wordpress.android.AppInitializer.init(AppInitializer.kt:308)
    at org.wordpress.android.WordPressApp.onCreate(WordPressApp.java:20)
```
@antonis, is your investigation ongoing? Can I assign this issue and [WORDPRESS-ANDROID-2WA6](https://a8c.sentry.io/issues/5083633345/?referrer=github_integration) to you?
Hey @irfano 👋
I'll be glad to continue looking at this. I've requested feedback internally (ref pcdRpT-5Us-p2#comment-9676) to see if we can avoid calling `getDefaultUserAgent` on initialisation when possible. I think that this might also be one of the root causes of https://github.com/wordpress-mobile/WordPress-Android/issues/20147

diff --git a/RELEASE-NOTES.txt b/RELEASE-NOTES.txt
index cca5a3431484..6676965acff1 100644
--- a/RELEASE-NOTES.txt
+++ b/RELEASE-NOTES.txt
@@ -2,7 +2,7 @@

 24.7
 -----
-
+* [*] [internal] Updates the way the app retrieves the User-Agent request header [https://github.com/wordpress-mobile/WordPress-Android/pull/20603]

 24.6
 -----
diff --git a/WordPress/src/main/java/org/wordpress/android/AppInitializer.kt b/WordPress/src/main/java/org/wordpress/android/AppInitializer.kt
index 3c9a689f24f4..118e30e38f8c 100644
--- a/WordPress/src/main/java/org/wordpress/android/AppInitializer.kt
+++ b/WordPress/src/main/java/org/wordpress/android/AppInitializer.kt
@@ -22,9 +22,7 @@ import android.os.Build.VERSION_CODES
 import android.os.Bundle
 import android.os.SystemClock
 import android.text.TextUtils
-import android.util.AndroidRuntimeException
 import android.util.Log
-import android.webkit.WebSettings
 import android.webkit.WebView
 import androidx.annotation.RequiresApi
 import androidx.appcompat.app.AppCompatDelegate
@@ -55,6 +53,7 @@ import org.wordpress.android.fluxc.generated.ListActionBuilder
 import org.wordpress.android.fluxc.generated.PostActionBuilder
 import org.wordpress.android.fluxc.generated.SiteActionBuilder
 import org.wordpress.android.fluxc.generated.ThemeActionBuilder
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.fluxc.network.rest.wpcom.site.PrivateAtomicCookie
 import org.wordpress.android.fluxc.store.AccountStore
 import org.wordpress.android.fluxc.store.AccountStore.OnAccountChanged
@@ -124,6 +123,9 @@ class AppInitializer @Inject constructor(
     wellSqlInitializer: WellSqlInitializer,
     private val application: Application
 ) : DefaultLifecycleObserver {
+    @Inject
+    lateinit var userAgent: UserAgent
+
     @Inject
     lateinit var dispatcher: Dispatcher

@@ -305,7 +307,7 @@ class AppInitializer @Inject constructor(
                 .installDefaultEventBus()
         }

-        RestClientUtils.setUserAgent(userAgent)
+        RestClientUtils.setUserAgent(userAgent.toString())

         if (!initialized) {
             zendeskHelper.setupZendesk(
@@ -363,6 +365,8 @@ class AppInitializer @Inject constructor(
             initAppOpsManager()
         }

+        AppLog.i(T.UTILS, "AppInitializer.userAgentString: $userAgent")
+
         initialized = true
     }

@@ -1052,55 +1056,6 @@ class AppInitializer @Inject constructor(
             )
         }

-        /**
-         * Device's default User-Agent string.
-         * E.g.:
-         * "Mozilla/5.0 (Linux; Android 6.0; Android SDK built for x86_64 Build/MASTER; wv)
-         * AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Chrome/44.0.2403.119 Mobile
-         * Safari/537.36"
-         */
-        @Suppress("SwallowedException")
-        val defaultUserAgent: String by lazy {
-            try {
-                WebSettings.getDefaultUserAgent(context)
-            } catch (e: AndroidRuntimeException) {
-                // Catch AndroidRuntimeException that could be raised by the WebView() constructor.
-                // See https://github.com/wordpress-mobile/WordPress-Android/issues/3594
-
-                // initialize with the empty string, it's a rare issue
-                ""
-            } catch (expected: NullPointerException) {
-                // Catch NullPointerException that could be raised by WebSettings.getDefaultUserAgent()
-                // See https://github.com/wordpress-mobile/WordPress-Android/issues/3838
-
-                // initialize with the empty string, it's a rare issue
-                ""
-            } catch (e: IllegalArgumentException) {
-                // Catch IllegalArgumentException that could be raised by WebSettings.getDefaultUserAgent()
-                // See https://github.com/wordpress-mobile/WordPress-Android/issues/9015
-
-                // initialize with the empty string, it's a rare issue
-                ""
-            }
-        }
-
-        /**
-         * User-Agent string when making HTTP connections, for both API traffic and WebViews. Appends
-         * "wp-android/version" to WebView's default User-Agent string for the webservers to get the full feature list
-         * of the browser and serve content accordingly, e.g.:
-         * "Mozilla/5.0 (Linux; Android 6.0; Android SDK built for x86_64 Build/MASTER; wv)
-         * AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Chrome/44.0.2403.119 Mobile
-         * Safari/537.36 wp-android/4.7"
-         * Note that app versions prior to 2.7 simply used "wp-android" as the user agent
-         **/
-        val userAgent: String by lazy {
-            if (TextUtils.isEmpty(defaultUserAgent)) {
-                WordPress.USER_AGENT_APPNAME + "/" + PackageUtils.getVersionName(context)
-            } else {
-                (defaultUserAgent + " " + WordPress.USER_AGENT_APPNAME + "/" + PackageUtils.getVersionName(context))
-            }
-        }
-
         fun getBitmapCache(): BitmapLruCache {
             if (bitmapCache == null) {
                 // The cache size will be measured in kilobytes rather than number of items.
diff --git a/WordPress/src/main/java/org/wordpress/android/WordPress.kt b/WordPress/src/main/java/org/wordpress/android/WordPress.kt
index 928455ca34c0..1ed866d9a713 100644
--- a/WordPress/src/main/java/org/wordpress/android/WordPress.kt
+++ b/WordPress/src/main/java/org/wordpress/android/WordPress.kt
@@ -70,11 +70,5 @@ abstract class WordPress : Application() {
         fun getRestClientUtilsV2() = AppInitializer.restClientUtilsV2

         fun getRestClientUtilsV0() = AppInitializer.restClientUtilsV0
-
-        @JvmStatic
-        fun getDefaultUserAgent() = AppInitializer.defaultUserAgent
-
-        @JvmStatic
-        fun getUserAgent() = AppInitializer.userAgent
     }
 }
diff --git a/WordPress/src/main/java/org/wordpress/android/modules/AppConfigModule.java b/WordPress/src/main/java/org/wordpress/android/modules/AppConfigModule.java
index 86ec20e8b317..8845f7dbe586 100644
--- a/WordPress/src/main/java/org/wordpress/android/modules/AppConfigModule.java
+++ b/WordPress/src/main/java/org/wordpress/android/modules/AppConfigModule.java
@@ -11,6 +11,8 @@
 import org.wordpress.android.fluxc.network.UserAgent;
 import org.wordpress.android.fluxc.network.rest.wpcom.auth.AppSecrets;

+import javax.inject.Singleton;
+
 import dagger.Module;
 import dagger.Provides;
 import dagger.hilt.InstallIn;
@@ -25,6 +27,7 @@ public AppSecrets provideAppSecrets() {
         return new AppSecrets(BuildConfig.OAUTH_APP_ID, BuildConfig.OAUTH_APP_SECRET);
     }

+    @Singleton
     @Provides
     public UserAgent provideUserAgent(@ApplicationContext Context appContext) {
         return new UserAgent(appContext, WordPress.USER_AGENT_APPNAME);
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/WebViewActivity.java b/WordPress/src/main/java/org/wordpress/android/ui/WebViewActivity.java
index 1999b39538e2..9bc91fe38fa8 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/WebViewActivity.java
+++ b/WordPress/src/main/java/org/wordpress/android/ui/WebViewActivity.java
@@ -13,13 +13,15 @@
 import androidx.appcompat.widget.Toolbar;

 import org.wordpress.android.R;
-import org.wordpress.android.WordPress;
 import org.wordpress.android.analytics.AnalyticsTracker;
+import org.wordpress.android.fluxc.network.UserAgent;
 import org.wordpress.android.util.extensions.CompatExtensionsKt;

 import java.util.HashMap;
 import java.util.Map;

+import javax.inject.Inject;
+
 /**
  * Basic activity for displaying a WebView.
  */
@@ -35,6 +37,8 @@ public abstract class WebViewActivity extends LocaleAwareActivity {

     protected WebView mWebView;

+    @Inject UserAgent mUserAgent;
+
     @Override
     public void onCreate(@Nullable Bundle savedInstanceState) {
         supportRequestWindowFeature(Window.FEATURE_PROGRESS);
@@ -64,7 +68,7 @@ public void handleOnBackPressed() {
         mWebView = (WebView) findViewById(R.id.webView);
         mWebView.setScrollBarStyle(View.SCROLLBARS_INSIDE_OVERLAY);
         // Setting this user agent makes Calypso sites hide any WordPress UIs (e.g. Masterbar, banners, etc.).
-        mWebView.getSettings().setUserAgentString(WordPress.getUserAgent());
+        mWebView.getSettings().setUserAgentString(mUserAgent.toString());
         configureWebView();

         if (savedInstanceState == null) {
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/blaze/BlazeFeatureUtils.kt b/WordPress/src/main/java/org/wordpress/android/ui/blaze/BlazeFeatureUtils.kt
index ba72a052d6f5..3cace3456986 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/blaze/BlazeFeatureUtils.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/blaze/BlazeFeatureUtils.kt
@@ -1,12 +1,12 @@
 package org.wordpress.android.ui.blaze

-import org.wordpress.android.WordPress
 import org.wordpress.android.analytics.AnalyticsTracker
 import org.wordpress.android.fluxc.model.PostModel
 import org.wordpress.android.fluxc.model.SiteModel
 import org.wordpress.android.fluxc.model.page.PageModel
 import org.wordpress.android.fluxc.model.page.PageStatus
 import org.wordpress.android.fluxc.model.post.PostStatus
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.ui.WPWebViewActivity
 import org.wordpress.android.ui.blaze.blazecampaigns.campaigndetail.CampaignDetailPageSource
 import org.wordpress.android.ui.blaze.blazecampaigns.campaignlisting.CampaignListingPageSource
@@ -18,6 +18,7 @@ import org.wordpress.android.util.config.BlazeManageCampaignFeatureConfig
 import javax.inject.Inject

 class BlazeFeatureUtils @Inject constructor(
+    private val userAgent: UserAgent,
     private val analyticsTrackerWrapper: AnalyticsTrackerWrapper,
     private val appPrefsWrapper: AppPrefsWrapper,
     private val blazeFeatureConfig: BlazeFeatureConfig,
@@ -153,7 +154,7 @@ class BlazeFeatureUtils @Inject constructor(
         )
     }

-    fun getUserAgent() = WordPress.getUserAgent()
+    fun getUserAgent() = userAgent.toString()

     fun getAuthenticationPostData(authenticationUrl: String,
                                   urlToLoad: String,
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/layoutpicker/LayoutPreviewFragment.kt b/WordPress/src/main/java/org/wordpress/android/ui/layoutpicker/LayoutPreviewFragment.kt
index 03292ed578f8..83d878c0642a 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/layoutpicker/LayoutPreviewFragment.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/layoutpicker/LayoutPreviewFragment.kt
@@ -18,6 +18,7 @@ import androidx.lifecycle.ViewModelProvider
 import org.wordpress.android.R
 import org.wordpress.android.WordPress
 import org.wordpress.android.databinding.LayoutPickerPreviewFragmentBinding
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.ui.FullscreenBottomSheetDialogFragment
 import org.wordpress.android.ui.PreviewMode.DESKTOP
 import org.wordpress.android.ui.PreviewMode.MOBILE
@@ -38,6 +39,9 @@ private const val JS_EVALUATION_DELAY = 250L
 private const val JS_READY_CALLBACK_ID = 926L

 abstract class LayoutPreviewFragment : FullscreenBottomSheetDialogFragment() {
+    @Inject
+    lateinit var userAgent: UserAgent
+
     @Inject
     lateinit var displayUtilsWrapper: DisplayUtilsWrapper

@@ -125,7 +129,7 @@ abstract class LayoutPreviewFragment : FullscreenBottomSheetDialogFragment() {

         binding?.previewTypeSelectorButton?.setOnClickListener { viewModel.onPreviewModePressed() }

-        binding?.webView?.settings?.userAgentString = WordPress.getUserAgent()
+        binding?.webView?.settings?.userAgentString = userAgent.toString()
         binding?.webView?.webViewClient = object : WebViewClient() {
             override fun onPageFinished(view: WebView?, url: String?) {
                 super.onPageFinished(view, url)
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/media/ExoPlayerUtils.kt b/WordPress/src/main/java/org/wordpress/android/ui/media/ExoPlayerUtils.kt
index adc9f5779c82..1fe579a18b6f 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/media/ExoPlayerUtils.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/media/ExoPlayerUtils.kt
@@ -19,13 +19,14 @@ import com.google.android.exoplayer2.upstream.DefaultDataSourceFactory
 import com.google.android.exoplayer2.upstream.DefaultHttpDataSourceFactory
 import com.google.android.exoplayer2.util.Util
 import dagger.Reusable
-import org.wordpress.android.WordPress
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.ui.utils.AuthenticationUtils
 import javax.inject.Inject

 @Reusable
 @Suppress("DEPRECATION")
 class ExoPlayerUtils @Inject constructor(
+    private val userAgent: UserAgent,
     private val authenticationUtils: AuthenticationUtils,
     private val appContext: Context
 ) {
@@ -33,7 +34,7 @@ class ExoPlayerUtils @Inject constructor(

     fun buildHttpDataSourceFactory(url: String): DefaultHttpDataSourceFactory {
         if (httpDataSourceFactory == null) {
-            httpDataSourceFactory = DefaultHttpDataSourceFactory(WordPress.getUserAgent())
+            httpDataSourceFactory = DefaultHttpDataSourceFactory(userAgent.toString())
         }
         httpDataSourceFactory?.defaultRequestProperties?.set(authenticationUtils.getAuthHeaders(url))
         return httpDataSourceFactory as DefaultHttpDataSourceFactory
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/media/MediaSettingsActivity.java b/WordPress/src/main/java/org/wordpress/android/ui/media/MediaSettingsActivity.java
index 3d96fd3386c7..b1fe511abc3b 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/media/MediaSettingsActivity.java
+++ b/WordPress/src/main/java/org/wordpress/android/ui/media/MediaSettingsActivity.java
@@ -67,6 +67,7 @@
 import org.wordpress.android.fluxc.generated.MediaActionBuilder;
 import org.wordpress.android.fluxc.model.MediaModel;
 import org.wordpress.android.fluxc.model.SiteModel;
+import org.wordpress.android.fluxc.network.UserAgent;
 import org.wordpress.android.fluxc.store.MediaStore;
 import org.wordpress.android.fluxc.store.MediaStore.MediaPayload;
 import org.wordpress.android.fluxc.store.MediaStore.OnMediaChanged;
@@ -153,6 +154,8 @@ private enum MediaType {

     private MediaType mMediaType;

+    @Inject UserAgent mUserAgent;
+
     @Inject MediaStore mMediaStore;
     @Inject Dispatcher mDispatcher;
     @Inject ImageManager mImageManager;
@@ -1031,7 +1034,7 @@ private void saveMediaToDevice() {
         }
         request.allowScanningByMediaScanner();
         request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE);
-        request.addRequestHeader("User-Agent", WordPress.getUserAgent());
+        request.addRequestHeader("User-Agent", mUserAgent.toString());

         mDownloadId = dm.enqueue(request);
         invalidateOptionsMenu();
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/posts/EditPostActivity.kt b/WordPress/src/main/java/org/wordpress/android/ui/posts/EditPostActivity.kt
index 2f03f2e9b8c4..2a95431d0ce3 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/posts/EditPostActivity.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/posts/EditPostActivity.kt
@@ -54,7 +54,6 @@ import org.wordpress.android.BuildConfig
 import org.wordpress.android.R
 import org.wordpress.android.WordPress
 import org.wordpress.android.WordPress.Companion.getContext
-import org.wordpress.android.WordPress.Companion.getUserAgent
 import org.wordpress.android.analytics.AnalyticsTracker
 import org.wordpress.android.analytics.AnalyticsTracker.Stat
 import org.wordpress.android.editor.AztecEditorFragment
@@ -94,6 +93,7 @@ import org.wordpress.android.fluxc.model.PostImmutableModel
 import org.wordpress.android.fluxc.model.PostModel
 import org.wordpress.android.fluxc.model.SiteModel
 import org.wordpress.android.fluxc.model.post.PostStatus
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.fluxc.network.rest.wpcom.site.PrivateAtomicCookie
 import org.wordpress.android.fluxc.store.AccountStore
 import org.wordpress.android.fluxc.store.AccountStore.OnAccountChanged
@@ -323,6 +323,8 @@ class EditPostActivity : LocaleAwareActivity(), EditorFragmentActivity, EditorIm

     @Inject lateinit var dispatcher: Dispatcher

+    @Inject lateinit var userAgent: UserAgent
+
     @Inject lateinit var accountStore: AccountStore

     @Inject lateinit var siteStore: SiteStore
@@ -2387,7 +2389,7 @@ class EditPostActivity : LocaleAwareActivity(), EditorFragmentActivity, EditorIm
                             siteModel.password,
                             siteModel.isUsingWpComRestApi,
                             siteModel.webEditor,
-                            getUserAgent(),
+                            userAgent.toString(),
                             isJetpackSsoEnabled
                         )
                     return GutenbergEditorFragment.newInstance(
@@ -2424,7 +2426,7 @@ class EditPostActivity : LocaleAwareActivity(), EditorFragmentActivity, EditorIm
                         editorMediaUploadListener = editorFragment as EditorMediaUploadListener?

                         // Set up custom headers for the visual editor's internal WebView
-                        editorFragment?.setCustomHttpHeader("User-Agent", getUserAgent())
+                        editorFragment?.setCustomHttpHeader("User-Agent", userAgent.toString())
                         reattachUploadingMediaForAztec()
                     }
                 }
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/publicize/PublicizeWebViewFragment.java b/WordPress/src/main/java/org/wordpress/android/ui/publicize/PublicizeWebViewFragment.java
index 261e22903f6e..ce439e6c8deb 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/publicize/PublicizeWebViewFragment.java
+++ b/WordPress/src/main/java/org/wordpress/android/ui/publicize/PublicizeWebViewFragment.java
@@ -19,6 +19,7 @@
 import org.wordpress.android.WordPress;
 import org.wordpress.android.datasets.PublicizeTable;
 import org.wordpress.android.fluxc.model.SiteModel;
+import org.wordpress.android.fluxc.network.UserAgent;
 import org.wordpress.android.fluxc.store.AccountStore;
 import org.wordpress.android.models.PublicizeConnection;
 import org.wordpress.android.models.PublicizeService;
@@ -39,6 +40,8 @@ public class PublicizeWebViewFragment extends PublicizeBaseFragment {
     private WebView mWebView;
     private ProgressBar mProgress;

+    @Inject UserAgent mUserAgent;
+
     @Inject AccountStore mAccountStore;

     /*
@@ -106,7 +109,7 @@ public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle sa
         mWebView.getSettings().setCacheMode(WebSettings.LOAD_NO_CACHE);
         mWebView.getSettings().setJavaScriptEnabled(true);
         mWebView.getSettings().setDomStorageEnabled(true);
-        mWebView.getSettings().setUserAgentString(WordPress.getUserAgent());
+        mWebView.getSettings().setUserAgentString(mUserAgent.toString());

         return rootView;
     }
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/reader/ReaderVideoViewerActivity.java b/WordPress/src/main/java/org/wordpress/android/ui/reader/ReaderVideoViewerActivity.java
index fcfde2ea5189..5fe94065af68 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/reader/ReaderVideoViewerActivity.java
+++ b/WordPress/src/main/java/org/wordpress/android/ui/reader/ReaderVideoViewerActivity.java
@@ -10,10 +10,12 @@
 import androidx.annotation.Nullable;

 import org.wordpress.android.R;
-import org.wordpress.android.WordPress;
+import org.wordpress.android.fluxc.network.UserAgent;
 import org.wordpress.android.ui.LocaleAwareActivity;
 import org.wordpress.android.util.helpers.WebChromeClientWithVideoPoster;

+import javax.inject.Inject;
+
 /**
  * Full screen landscape video player for the reader
  */
@@ -22,6 +24,8 @@ public class ReaderVideoViewerActivity extends LocaleAwareActivity {
     private WebView mWebView;
     private ProgressBar mProgress;

+    @Inject UserAgent mUserAgent;
+
     @Override
     public void onCreate(@Nullable Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
@@ -32,7 +36,7 @@ public void onCreate(@Nullable Bundle savedInstanceState) {

         mWebView.setBackgroundColor(Color.TRANSPARENT);
         mWebView.getSettings().setJavaScriptEnabled(true);
-        mWebView.getSettings().setUserAgentString(WordPress.getUserAgent());
+        mWebView.getSettings().setUserAgentString(mUserAgent.toString());

         mWebView.setWebChromeClient(new WebChromeClientWithVideoPoster(
                 mWebView,
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/reader/views/ReaderWebView.java b/WordPress/src/main/java/org/wordpress/android/ui/reader/views/ReaderWebView.java
index 736a8883063f..4e071f8c2bd2 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/reader/views/ReaderWebView.java
+++ b/WordPress/src/main/java/org/wordpress/android/ui/reader/views/ReaderWebView.java
@@ -18,6 +18,7 @@
 import androidx.annotation.NonNull;

 import org.wordpress.android.WordPress;
+import org.wordpress.android.fluxc.network.UserAgent;
 import org.wordpress.android.fluxc.store.AccountStore;
 import org.wordpress.android.ui.WPWebView;
 import org.wordpress.android.util.AppLog;
@@ -77,6 +78,8 @@ public interface ReaderWebViewPageFinishedListener {
     private static boolean mBlogSchemeIsHttps;

     private boolean mIsDestroyed;
+
+    @Inject UserAgent mUserAgent;
     @Inject AccountStore mAccountStore;

     public ReaderWebView(Context context) {
@@ -103,8 +106,8 @@ private void init(Context context) {

             mReaderChromeClient = new ReaderWebChromeClient(this);
             this.setWebChromeClient(mReaderChromeClient);
-            this.setWebViewClient(new ReaderWebViewClient(this));
-            this.getSettings().setUserAgentString(WordPress.getUserAgent());
+            this.setWebViewClient(new ReaderWebViewClient(this, mUserAgent));
+            this.getSettings().setUserAgentString(mUserAgent.toString());

             // Enable third-party cookies since they are disabled by default;
             // we need third-party cookies to support authenticated images
@@ -261,12 +264,14 @@ public boolean onTouchEvent(MotionEvent event) {

     private static class ReaderWebViewClient extends WebViewClient {
         private final ReaderWebView mReaderWebView;
+        private final UserAgent mUserAgent;

-        ReaderWebViewClient(ReaderWebView readerWebView) {
+        ReaderWebViewClient(ReaderWebView readerWebView, UserAgent userAgent) {
             if (readerWebView == null) {
                 throw new IllegalArgumentException("ReaderWebViewClient requires readerWebView");
             }
             mReaderWebView = readerWebView;
+            mUserAgent = userAgent;
         }

@@ -309,7 +314,7 @@ public WebResourceResponse shouldInterceptRequest(WebView view, String url) {
                     conn.setRequestProperty("Authorization", "Bearer " + mToken);
                     conn.setReadTimeout(TIMEOUT_MS);
                     conn.setConnectTimeout(TIMEOUT_MS);
-                    conn.setRequestProperty("User-Agent", WordPress.getUserAgent());
+                    conn.setRequestProperty("User-Agent", mUserAgent.toString());
                     conn.setRequestProperty("Connection", "Keep-Alive");
                     return new WebResourceResponse(conn.getContentType(),
                             conn.getContentEncoding(),
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/plans/SiteCreationPlansViewModel.kt b/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/plans/SiteCreationPlansViewModel.kt
index 473a90bfecf4..1b667cf99bf4 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/plans/SiteCreationPlansViewModel.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/plans/SiteCreationPlansViewModel.kt
@@ -10,8 +10,8 @@ import kotlinx.coroutines.flow.MutableStateFlow
 import kotlinx.coroutines.flow.StateFlow
 import kotlinx.coroutines.flow.receiveAsFlow
 import kotlinx.coroutines.launch
-import org.wordpress.android.WordPress
 import org.wordpress.android.fluxc.model.SiteModel
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.fluxc.store.AccountStore
 import org.wordpress.android.fluxc.store.SiteStore
 import org.wordpress.android.ui.WPWebViewActivity
@@ -23,6 +23,7 @@ import javax.inject.Inject

 @HiltViewModel
 class SiteCreationPlansViewModel @Inject constructor(
+    private val userAgent: UserAgent,
     private val accountStore: AccountStore,
     private val siteStore: SiteStore,
     private val networkUtilsWrapper: NetworkUtilsWrapper
@@ -79,7 +80,7 @@ class SiteCreationPlansViewModel @Inject constructor(
             SiteCreationPlansModel(
                 enableJavascript = true,
                 enableDomStorage = true,
-                userAgent = WordPress.getUserAgent(),
+                userAgent = userAgent.toString(),
                 enableChromeClient = true,
                 url = url,
                 addressToLoad = addressToLoad
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/previews/SiteCreationPreviewFragment.kt b/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/previews/SiteCreationPreviewFragment.kt
index 8ab86f82a9d1..e4734fe97935 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/previews/SiteCreationPreviewFragment.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/sitecreation/previews/SiteCreationPreviewFragment.kt
@@ -18,10 +18,10 @@ import androidx.core.view.isVisible
 import androidx.fragment.app.activityViewModels
 import dagger.hilt.android.AndroidEntryPoint
 import org.wordpress.android.R
-import org.wordpress.android.WordPress
 import org.wordpress.android.databinding.SiteCreationFormScreenBinding
 import org.wordpress.android.databinding.SiteCreationPreviewScreenBinding
 import org.wordpress.android.databinding.SiteCreationPreviewScreenDefaultBinding
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.ui.sitecreation.SiteCreationActivity.Companion.ARG_STATE
 import org.wordpress.android.ui.sitecreation.SiteCreationBaseFormFragment
 import org.wordpress.android.ui.sitecreation.SiteCreationState
@@ -39,6 +39,9 @@ private const val SLIDE_IN_ANIMATION_DURATION = 450L
 @AndroidEntryPoint
 class SiteCreationPreviewFragment : SiteCreationBaseFormFragment(),
     ErrorManagedWebViewClientListener {
+    @Inject
+    lateinit var userAgent: UserAgent
+
     @Inject
     internal lateinit var uiHelpers: UiHelpers

@@ -106,7 +109,7 @@ class SiteCreationPreviewFragment : SiteCreationBaseFormFragment(),
         viewModel.preloadPreview.observe(this) { url ->
             url?.let { urlString ->
                 webView.webViewClient = URLFilteredWebViewClient(urlString, this)
-                webView.settings.userAgentString = WordPress.getUserAgent()
+                webView.settings.userAgentString = userAgent.toString()
                 webView.loadUrl(urlString)
             }
         }
diff --git a/WordPress/src/main/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtils.kt b/WordPress/src/main/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtils.kt
index a64e92029030..6ec20e9dcf4f 100644
--- a/WordPress/src/main/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtils.kt
+++ b/WordPress/src/main/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtils.kt
@@ -1,15 +1,16 @@
 package org.wordpress.android.ui.sitemonitor

-import org.wordpress.android.WordPress
 import org.wordpress.android.analytics.AnalyticsTracker
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.ui.WPWebViewActivity
 import org.wordpress.android.util.analytics.AnalyticsTrackerWrapper
 import javax.inject.Inject

 class SiteMonitorUtils @Inject constructor(
+    private val userAgent: UserAgent,
     private val analyticsTrackerWrapper: AnalyticsTrackerWrapper
 ) {
-    fun getUserAgent() = WordPress.getUserAgent()
+    fun getUserAgent() = userAgent.toString()

     fun getAuthenticationPostData(authenticationUrl: String,
                                   urlToLoad: String,

diff --git a/WordPress/src/androidTest/java/org/wordpress/android/UserAgentTest.java b/WordPress/src/androidTest/java/org/wordpress/android/UserAgentTest.java
index 8e93118c2d07..79ec7c5bec52 100644
--- a/WordPress/src/androidTest/java/org/wordpress/android/UserAgentTest.java
+++ b/WordPress/src/androidTest/java/org/wordpress/android/UserAgentTest.java
@@ -1,7 +1,13 @@
 package org.wordpress.android;

+import android.webkit.WebSettings;
+
+import org.junit.Before;
 import org.junit.Rule;
 import org.junit.Test;
+import org.wordpress.android.fluxc.network.UserAgent;
+
+import javax.inject.Inject;

 import static junit.framework.TestCase.assertFalse;
 import static junit.framework.TestCase.assertNotNull;
@@ -24,14 +30,21 @@ public class UserAgentTest {
     @Rule(order = 1)
     public InitializationRule initRule = new InitializationRule();

+    @Inject UserAgent mUserAgent;
+
+    @Before
+    public void setUp() {
+        hiltRule.inject();
+    }
+
     @Test
     public void testGetUserAgentAndGetDefaultUserAgent() {
-        String userAgent = WordPress.getUserAgent();
+        String userAgent = mUserAgent.toString();
         assertNotNull("User-Agent must be set", userAgent);
         assertTrue("User-Agent must not be an empty string", userAgent.length() > 0);
         assertTrue("User-Agent must contain app name substring", userAgent.contains(USER_AGENT_APPNAME));

-        String defaultUserAgent = WordPress.getDefaultUserAgent();
+        String defaultUserAgent = WebSettings.getDefaultUserAgent(AppInitializer.Companion.getContext());
         assertNotNull("Default User-Agent must be set", defaultUserAgent);
         assertTrue("Default User-Agent must not be an empty string", defaultUserAgent.length() > 0);
         assertFalse("Default User-Agent must not contain app name", defaultUserAgent.contains(USER_AGENT_APPNAME));
diff --git a/WordPress/src/test/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtilsTest.kt b/WordPress/src/test/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtilsTest.kt
index 0bf5076d32d5..77d2051b539d 100644
--- a/WordPress/src/test/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtilsTest.kt
+++ b/WordPress/src/test/java/org/wordpress/android/ui/sitemonitor/SiteMonitorUtilsTest.kt
@@ -8,10 +8,14 @@ import org.mockito.Mock
 import org.mockito.junit.MockitoJUnitRunner
 import org.mockito.kotlin.verify
 import org.wordpress.android.analytics.AnalyticsTracker
+import org.wordpress.android.fluxc.network.UserAgent
 import org.wordpress.android.util.analytics.AnalyticsTrackerWrapper

 @RunWith(MockitoJUnitRunner::class)
 class SiteMonitorUtilsTest {
+    @Mock
+    lateinit var userAgent: UserAgent
+
     @Mock
     lateinit var analyticsTrackerWrapper: AnalyticsTrackerWrapper

@@ -19,7 +23,7 @@ class SiteMonitorUtilsTest {

     @Before
     fun setup() {
-        siteMonitorUtils = SiteMonitorUtils(analyticsTrackerWrapper)
+        siteMonitorUtils = SiteMonitorUtils(userAgent, analyticsTrackerWrapper)
     }

     @Test