diff --git a/Corona-Warn-App/src/androidTest/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorkerTest.kt b/Corona-Warn-App/src/androidTest/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorkerTest.kt
deleted file mode 100644
index 33e0ef13ed9ee0a6009621b4ed3dc3a16548398e..0000000000000000000000000000000000000000
--- a/Corona-Warn-App/src/androidTest/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorkerTest.kt
+++ /dev/null
@@ -1,205 +0,0 @@
-package de.rki.coronawarnapp.worker
-
-import android.content.Context
-import androidx.test.core.app.ApplicationProvider
-import androidx.test.ext.junit.runners.AndroidJUnit4
-import androidx.work.WorkInfo
-import androidx.work.WorkManager
-import androidx.work.WorkRequest
-import androidx.work.testing.TestDriver
-import androidx.work.testing.WorkManagerTestInitHelper
-import de.rki.coronawarnapp.playbook.Playbook
-import de.rki.coronawarnapp.service.submission.SubmissionService
-import de.rki.coronawarnapp.storage.LocalData
-import de.rki.coronawarnapp.util.TimeAndDateExtensions.daysToMilliseconds
-import de.rki.coronawarnapp.util.formatter.TestResult
-import io.mockk.coEvery
-import io.mockk.every
-import io.mockk.impl.annotations.MockK
-import io.mockk.mockk
-import io.mockk.mockkObject
-import io.mockk.slot
-import io.mockk.unmockkAll
-import org.hamcrest.CoreMatchers.`is`
-import org.hamcrest.CoreMatchers.notNullValue
-import org.hamcrest.MatcherAssert.assertThat
-import org.junit.After
-import org.junit.Before
-import org.junit.Ignore
-import org.junit.Test
-import org.junit.runner.RunWith
-import java.util.Date
-
-/**
- * DiagnosisTestResultRetrievalPeriodicWorker test.
- */
-@Ignore("FixMe:DiagnosisTestResultRetrievalPeriodicWorkerTest")
-@RunWith(AndroidJUnit4::class)
-class DiagnosisTestResultRetrievalPeriodicWorkerTest {
-    private lateinit var context: Context
-    private lateinit var workManager: WorkManager
-    private lateinit var request: WorkRequest
-    @MockK lateinit var playbook: Playbook
-    private val submissionService = SubmissionService(playbook)
-    // small delay because WorkManager does not run work instantly when delay is off
-    private val delay = 500L
-
-    @Before
-    fun setUp() {
-        LocalData.registrationToken("test token")
-        LocalData.isTestResultAvailableNotificationSent(false)
-        mockkObject(LocalData)
-        mockkObject(BackgroundWorkScheduler)
-
-        // do not init Test WorkManager instance again between tests
-        // leads to all tests instead of first one to fail
-        context = ApplicationProvider.getApplicationContext()
-        if (WorkManager.getInstance(context) !is TestDriver) {
-            WorkManagerTestInitHelper.initializeTestWorkManager(context)
-        }
-        workManager = WorkManager.getInstance(context)
-
-        every { BackgroundWorkScheduler["buildDiagnosisTestResultRetrievalPeriodicWork"]() } answers {
-            request = this.callOriginal() as WorkRequest
-            request
-        }
-
-        val slot = slot<String>()
-        every { BackgroundWorkScheduler["isWorkActive"](capture(slot)) } answers {
-            !(slot.isCaptured && slot.captured ==
-                    BackgroundWorkScheduler.WorkTag.DIAGNOSIS_TEST_RESULT_RETRIEVAL_PERIODIC_WORKER.tag)
-        }
-    }
-
-    /**
-     * Test worker for running more than a set amount of days.
-     *
-     * @see [BackgroundConstants.POLLING_VALIDITY_MAX_DAYS]
-     */
-    @Test
-    fun testDiagnosisTestResultRetrievalPeriodicWorkerCancel() {
-        val past = System.currentTimeMillis() -
-            (BackgroundConstants.POLLING_VALIDITY_MAX_DAYS.toLong() + 1).daysToMilliseconds()
-        testDiagnosisTestResultRetrievalPeriodicWorkerForResult(mockk(), past, true)
-    }
-
-    /**
-     * Test worker for running less than a set amount of days, [TestResult.PENDING].
-     *
-     * @see [BackgroundConstants.POLLING_VALIDITY_MAX_DAYS]
-     */
-    @Test
-    fun testDiagnosisTestResultRetrievalPeriodicWorkerPending() {
-        val past = Date().time - (BackgroundConstants.POLLING_VALIDITY_MAX_DAYS.toLong() - 1).daysToMilliseconds()
-        testDiagnosisTestResultRetrievalPeriodicWorkerForResult(TestResult.PENDING, past)
-    }
-
-    /**
-     * Test worker for running less than a set amount of days, [TestResult.NEGATIVE]  .
-     *
-     * @see [BackgroundConstants.POLLING_VALIDITY_MAX_DAYS]
-     */
-    @Test
-    fun testDiagnosisTestResultRetrievalPeriodicWorkerSuccessNegative() {
-        val past = Date().time - (BackgroundConstants.POLLING_VALIDITY_MAX_DAYS.toLong() - 1).daysToMilliseconds()
-        testDiagnosisTestResultRetrievalPeriodicWorkerForResult(TestResult.NEGATIVE, past)
-    }
-
-    /**
-     * Test worker for running less than a set amount of days, [TestResult.POSITIVE]  .
-     *
-     * @see [BackgroundConstants.POLLING_VALIDITY_MAX_DAYS]
-     */
-    @Test
-    fun testDiagnosisTestResultRetrievalPeriodicWorkerSuccessPositive() {
-        val past = Date().time - (BackgroundConstants.POLLING_VALIDITY_MAX_DAYS.toLong() - 1).daysToMilliseconds()
-        testDiagnosisTestResultRetrievalPeriodicWorkerForResult(TestResult.POSITIVE, past)
-    }
-
-    /**
-     * Test worker for retries and fail.
-     */
-    @Test
-    fun testDiagnosisTestResultRetrievalPeriodicWorkerRetryAndFail() {
-        val past = Date().time - (BackgroundConstants.POLLING_VALIDITY_MAX_DAYS.toLong() - 1).daysToMilliseconds()
-        every { LocalData.initialPollingForTestResultTimeStamp() } returns past
-
-        BackgroundWorkScheduler.startWorkScheduler()
-
-        assertThat(request, notNullValue())
-        var workInfo = workManager.getWorkInfoById(request.id).get()
-        assertThat(workInfo, notNullValue())
-        assertThat(workInfo.state, `is`((WorkInfo.State.ENQUEUED)))
-
-        for (i in 1..BackgroundConstants.WORKER_RETRY_COUNT_THRESHOLD + 2) {
-            // run job i times
-            runPeriodicJobInitialDelayMet()
-
-            // get job run #i result
-            when (i) {
-                BackgroundConstants.WORKER_RETRY_COUNT_THRESHOLD + 2 -> {
-                    assertThat(request, notNullValue())
-                    workInfo = workManager.getWorkInfoById(request.id).get()
-                    assertThat(workInfo.runAttemptCount, `is`(0))
-                }
-                else -> {
-                    assertThat(request, notNullValue())
-                    workInfo = workManager.getWorkInfoById(request.id).get()
-                    assertThat(workInfo.runAttemptCount, `is`(i))
-                }
-            }
-        }
-    }
-
-    @After
-    fun cleanUp() {
-        workManager.cancelAllWork()
-        unmockkAll()
-    }
-
-    private fun testDiagnosisTestResultRetrievalPeriodicWorkerForResult(
-        result: TestResult,
-        past: Long,
-        isCancelTest: Boolean = false
-    ) {
-        coEvery { submissionService.asyncRequestTestResult(any()) } returns result
-        every { LocalData.initialPollingForTestResultTimeStamp() } returns past
-
-        BackgroundWorkScheduler.startWorkScheduler()
-
-        assertThat(request, notNullValue())
-
-        val workInfo = workManager.getWorkInfoById(request.id).get()
-        assertThat(workInfo, notNullValue())
-        assertThat(workInfo.state, `is`((WorkInfo.State.ENQUEUED)))
-        runPeriodicJobInitialDelayMet()
-        verifyTestResult(result, isCancelTest)
-    }
-
-    private fun verifyTestResult(result: TestResult, isCancelTest: Boolean) {
-        assertThat(request, notNullValue())
-        val workInfo = workManager.getWorkInfoById(request.id).get()
-        if (isCancelTest) {
-            assertThat(workInfo.state, `is`((WorkInfo.State.CANCELLED)))
-            assertThat(LocalData.isTestResultAvailableNotificationSent(), `is`(false))
-        } else {
-            when (result) {
-                TestResult.POSITIVE, TestResult.NEGATIVE, TestResult.INVALID -> {
-                    assertThat(workInfo.state, `is`((WorkInfo.State.CANCELLED)))
-                    assertThat(LocalData.isTestResultAvailableNotificationSent(), `is`(true))
-                }
-                TestResult.PENDING -> {
-                    assertThat(workInfo.runAttemptCount, `is`(0))
-                    assertThat(workInfo.state, `is`((WorkInfo.State.ENQUEUED)))
-                }
-            }
-        }
-    }
-
-    private fun runPeriodicJobInitialDelayMet() {
-        val testDriver = WorkManagerTestInitHelper.getTestDriver(context)
-        testDriver?.setAllConstraintsMet(request.id)
-        testDriver?.setInitialDelayMet(request.id)
-        Thread.sleep(delay)
-    }
-}
diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/task/TaskControllerExtensions.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/task/TaskControllerExtensions.kt
index 2166ace118dc16417307a1f2ec6775de7656e69e..73a26b99f22272f74973d91baf0ba23628a9d895 100644
--- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/task/TaskControllerExtensions.kt
+++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/task/TaskControllerExtensions.kt
@@ -1,6 +1,5 @@
 package de.rki.coronawarnapp.task
 
-import kotlinx.coroutines.flow.Flow
 import kotlinx.coroutines.flow.asFlow
 import kotlinx.coroutines.flow.first
 import kotlinx.coroutines.flow.flatMapMerge
@@ -17,14 +16,3 @@ suspend fun TaskController.submitBlocking(ourRequest: TaskRequest) =
     }.also {
         Timber.v("submitBlocking(request=%s) continuing with result %s", ourRequest, it)
     }
-
-suspend fun TaskController.submitAndListen(ourRequest: TaskRequest): Flow<Task.Progress> {
-    submit(ourRequest)
-    Timber.v("submitAndListen(request=%s) waiting for progress flow...", ourRequest)
-
-    return tasks.flatMapMerge { it.asFlow() }.first {
-        it.taskState.request.id == ourRequest.id
-    }.progress.also {
-        Timber.v("submitAndListen(request=%s) continuing with flow %s", ourRequest, it)
-    }
-}
diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorker.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorker.kt
index 47b8b15f2257abeefe1e5f3648be753f65a82073..bada3ae70a4bded1eeb277260d7e8f73ac04c32b 100644
--- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorker.kt
+++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorker.kt
@@ -14,13 +14,14 @@ import de.rki.coronawarnapp.service.submission.SubmissionService
 import de.rki.coronawarnapp.storage.LocalData
 import de.rki.coronawarnapp.submission.SubmissionSettings
 import de.rki.coronawarnapp.util.TimeAndDateExtensions
+import de.rki.coronawarnapp.util.TimeStamper
 import de.rki.coronawarnapp.util.formatter.TestResult
 import de.rki.coronawarnapp.util.worker.InjectedWorkerFactory
 import de.rki.coronawarnapp.worker.BackgroundWorkScheduler.stop
 import timber.log.Timber
 
 /**
- * Diagnosis Test Result Periodic retrieval
+ * Diagnosis test result retrieval by periodic polling
  *
  * @see BackgroundWorkScheduler
  */
@@ -30,16 +31,10 @@ class DiagnosisTestResultRetrievalPeriodicWorker @AssistedInject constructor(
     private val testResultAvailableNotificationService: TestResultAvailableNotificationService,
     private val notificationHelper: NotificationHelper,
     private val submissionSettings: SubmissionSettings,
-    private val submissionService: SubmissionService
+    private val submissionService: SubmissionService,
+    private val timeStamper: TimeStamper
 ) : CoroutineWorker(context, workerParams) {
 
-    /**
-     * If background job is running for less than 21 days, testResult is checked.
-     * If the job is running for more than 21 days, the job will be stopped
-     *
-     * @see LocalData.isTestResultAvailableNotificationSent
-     * @see LocalData.initialPollingForTestResultTimeStamp
-     */
     override suspend fun doWork(): Result {
         Timber.tag(TAG).d("$id: doWork() started. Run attempt: $runAttemptCount")
 
@@ -54,7 +49,7 @@ class DiagnosisTestResultRetrievalPeriodicWorker @AssistedInject constructor(
         var result = Result.success()
         try {
 
-            if (abortConditionsMet()) {
+            if (abortConditionsMet(timeStamper.nowUTC.millis)) {
                 Timber.tag(TAG).d(" $id Stopping worker.")
                 stopWorker()
             } else {
@@ -75,7 +70,7 @@ class DiagnosisTestResultRetrievalPeriodicWorker @AssistedInject constructor(
                     stopWorker()
                 }
             }
-        } catch (e: Exception) {
+        } catch (ex: Exception) {
             result = Result.retry()
         }
 
@@ -84,7 +79,7 @@ class DiagnosisTestResultRetrievalPeriodicWorker @AssistedInject constructor(
         return result
     }
 
-    private fun abortConditionsMet(): Boolean {
+    private fun abortConditionsMet(currentMillis: Long): Boolean {
         if (LocalData.isTestResultAvailableNotificationSent()) {
             Timber.tag(TAG).d("$id: Notification already sent.")
             return true
@@ -96,7 +91,7 @@ class DiagnosisTestResultRetrievalPeriodicWorker @AssistedInject constructor(
 
         if (TimeAndDateExtensions.calculateDays(
                 LocalData.initialPollingForTestResultTimeStamp(),
-                System.currentTimeMillis()
+                currentMillis
             ) >= BackgroundConstants.POLLING_VALIDITY_MAX_DAYS
         ) {
             Timber.tag(TAG)
@@ -118,12 +113,6 @@ class DiagnosisTestResultRetrievalPeriodicWorker @AssistedInject constructor(
         )
     }
 
-    /**
-     * Stops the Background Polling worker
-     *
-     * @see LocalData.initialPollingForTestResultTimeStamp
-     * @see BackgroundWorkScheduler.stop
-     */
     private fun stopWorker() {
         LocalData.initialPollingForTestResultTimeStamp(0L)
         BackgroundWorkScheduler.WorkType.DIAGNOSIS_TEST_RESULT_PERIODIC_WORKER.stop()
diff --git a/Corona-Warn-App/src/test/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorkerTest.kt b/Corona-Warn-App/src/test/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorkerTest.kt
new file mode 100644
index 0000000000000000000000000000000000000000..9de1965602d2351a0fc09046ce922b777f8d790a
--- /dev/null
+++ b/Corona-Warn-App/src/test/java/de/rki/coronawarnapp/worker/DiagnosisTestResultRetrievalPeriodicWorkerTest.kt
@@ -0,0 +1,241 @@
+package de.rki.coronawarnapp.worker
+
+import android.content.Context
+import androidx.work.ListenableWorker
+import androidx.work.Operation
+import androidx.work.WorkRequest
+import androidx.work.WorkerParameters
+import de.rki.coronawarnapp.notification.NotificationConstants
+import de.rki.coronawarnapp.notification.NotificationHelper
+import de.rki.coronawarnapp.notification.TestResultAvailableNotificationService
+import de.rki.coronawarnapp.service.submission.SubmissionService
+import de.rki.coronawarnapp.storage.LocalData
+import de.rki.coronawarnapp.submission.SubmissionSettings
+import de.rki.coronawarnapp.util.TimeAndDateExtensions.daysToMilliseconds
+import de.rki.coronawarnapp.util.TimeStamper
+import de.rki.coronawarnapp.util.di.AppInjector
+import de.rki.coronawarnapp.util.di.ApplicationComponent
+import de.rki.coronawarnapp.util.formatter.TestResult
+import de.rki.coronawarnapp.util.security.EncryptedPreferencesFactory
+import de.rki.coronawarnapp.util.security.EncryptionErrorResetTool
+import de.rki.coronawarnapp.worker.BackgroundWorkScheduler.stop
+import io.kotest.matchers.shouldBe
+import io.mockk.MockKAnnotations
+import io.mockk.Runs
+import io.mockk.coEvery
+import io.mockk.coVerify
+import io.mockk.every
+import io.mockk.impl.annotations.MockK
+import io.mockk.impl.annotations.RelaxedMockK
+import io.mockk.just
+import io.mockk.mockkObject
+import io.mockk.verify
+import kotlinx.coroutines.test.runBlockingTest
+import org.joda.time.Instant
+import org.junit.Before
+import org.junit.Test
+import testhelpers.BaseTest
+
+class DiagnosisTestResultRetrievalPeriodicWorkerTest : BaseTest() {
+    @MockK lateinit var context: Context
+    @MockK lateinit var request: WorkRequest
+    @MockK lateinit var submissionSettings: SubmissionSettings
+    @MockK lateinit var submissionService: SubmissionService
+    @MockK lateinit var testResultAvailableNotificationService: TestResultAvailableNotificationService
+    @MockK lateinit var notificationHelper: NotificationHelper
+    @MockK lateinit var appComponent: ApplicationComponent
+    @MockK lateinit var encryptedPreferencesFactory: EncryptedPreferencesFactory
+    @MockK lateinit var encryptionErrorResetTool: EncryptionErrorResetTool
+    @MockK lateinit var operation: Operation
+    @MockK lateinit var timeStamper: TimeStamper
+    @RelaxedMockK lateinit var workerParams: WorkerParameters
+    private val currentInstant = Instant.ofEpochSecond(1611764225)
+    private val registrationToken = "test token"
+
+    @Before
+    fun setUp() {
+        MockKAnnotations.init(this)
+        every { submissionSettings.hasViewedTestResult.value } returns false
+        every { timeStamper.nowUTC } returns currentInstant
+
+        mockkObject(AppInjector)
+        every { AppInjector.component } returns appComponent
+        every { appComponent.encryptedPreferencesFactory } returns encryptedPreferencesFactory
+        every { appComponent.errorResetTool } returns encryptionErrorResetTool
+
+        mockkObject(LocalData)
+        every { LocalData.registrationToken() } returns registrationToken
+        every { LocalData.isTestResultAvailableNotificationSent() } returns false
+        every { LocalData.initialPollingForTestResultTimeStamp() } returns currentInstant.millis
+        every { LocalData.initialPollingForTestResultTimeStamp(any()) } just Runs
+        every { LocalData.isTestResultAvailableNotificationSent(any()) } just Runs
+
+        mockkObject(BackgroundWorkScheduler)
+        every { BackgroundWorkScheduler.WorkType.DIAGNOSIS_TEST_RESULT_PERIODIC_WORKER.stop() } returns operation
+    }
+
+    @Test
+    fun testStopWorkerWhenResultHasBeenViewed() {
+        runBlockingTest {
+            every { submissionSettings.hasViewedTestResult.value } returns true
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify(exactly = 0) { submissionService.asyncRequestTestResult(any()) }
+            verify(exactly = 1) { BackgroundWorkScheduler.WorkType.DIAGNOSIS_TEST_RESULT_PERIODIC_WORKER.stop() }
+            assert(result is ListenableWorker.Result.Success)
+        }
+    }
+
+    @Test
+    fun testStopWorkerWhenNotificationSent() {
+        runBlockingTest {
+            every { LocalData.isTestResultAvailableNotificationSent() } returns true
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify(exactly = 0) { submissionService.asyncRequestTestResult(any()) }
+            verify(exactly = 1) { BackgroundWorkScheduler.WorkType.DIAGNOSIS_TEST_RESULT_PERIODIC_WORKER.stop() }
+            assert(result is ListenableWorker.Result.Success)
+        }
+    }
+
+    @Test
+    fun testStopWorkerWhenMaxDaysExceeded() {
+        runBlockingTest {
+            val past =
+                currentInstant - (BackgroundConstants.POLLING_VALIDITY_MAX_DAYS.toLong() + 1).daysToMilliseconds()
+            every { LocalData.initialPollingForTestResultTimeStamp() } returns past.millis
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify(exactly = 0) { submissionService.asyncRequestTestResult(any()) }
+            verify(exactly = 1) { BackgroundWorkScheduler.WorkType.DIAGNOSIS_TEST_RESULT_PERIODIC_WORKER.stop() }
+            result shouldBe ListenableWorker.Result.success()
+        }
+    }
+
+    @Test
+    fun testSendNotificationWhenPositive() {
+        runBlockingTest {
+            val testResult = TestResult.POSITIVE
+            coEvery { submissionService.asyncRequestTestResult(registrationToken) } returns testResult
+            coEvery { testResultAvailableNotificationService.showTestResultAvailableNotification(testResult) } just Runs
+            coEvery {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            } just Runs
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify { submissionService.asyncRequestTestResult(registrationToken) }
+            coVerify { LocalData.isTestResultAvailableNotificationSent(true) }
+            coVerify { testResultAvailableNotificationService.showTestResultAvailableNotification(testResult) }
+            coVerify {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            }
+            assert(result is ListenableWorker.Result.Success)
+        }
+    }
+
+    @Test
+    fun testSendNotificationWhenNegative() {
+        runBlockingTest {
+            val testResult = TestResult.NEGATIVE
+            coEvery { submissionService.asyncRequestTestResult(registrationToken) } returns testResult
+            coEvery { testResultAvailableNotificationService.showTestResultAvailableNotification(testResult) } just Runs
+            coEvery {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            } just Runs
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify { submissionService.asyncRequestTestResult(registrationToken) }
+            coVerify { LocalData.isTestResultAvailableNotificationSent(true) }
+            coVerify { testResultAvailableNotificationService.showTestResultAvailableNotification(testResult) }
+            coVerify {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            }
+            assert(result is ListenableWorker.Result.Success)
+        }
+    }
+
+    @Test
+    fun testSendNotificationWhenInvalid() {
+        runBlockingTest {
+            val testResult = TestResult.INVALID
+            coEvery { submissionService.asyncRequestTestResult(registrationToken) } returns testResult
+            coEvery { testResultAvailableNotificationService.showTestResultAvailableNotification(testResult) } just Runs
+            coEvery {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            } just Runs
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify { submissionService.asyncRequestTestResult(registrationToken) }
+            coVerify { LocalData.isTestResultAvailableNotificationSent(true) }
+            coVerify { testResultAvailableNotificationService.showTestResultAvailableNotification(testResult) }
+            coVerify {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            }
+            assert(result is ListenableWorker.Result.Success)
+        }
+    }
+
+    @Test
+    fun testSendNoNotificationWhenPending() {
+        runBlockingTest {
+            val testResult = TestResult.PENDING
+            coEvery { submissionService.asyncRequestTestResult(registrationToken) } returns testResult
+            coEvery { testResultAvailableNotificationService.showTestResultAvailableNotification(testResult) } just Runs
+            coEvery {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            } just Runs
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify { submissionService.asyncRequestTestResult(registrationToken) }
+            coVerify(exactly = 0) { LocalData.isTestResultAvailableNotificationSent(true) }
+            coVerify(exactly = 0) {
+                testResultAvailableNotificationService.showTestResultAvailableNotification(
+                    testResult
+                )
+            }
+            coVerify(exactly = 0) {
+                notificationHelper.cancelCurrentNotification(
+                    NotificationConstants.NEW_MESSAGE_RISK_LEVEL_SCORE_NOTIFICATION_ID
+                )
+            }
+            coVerify(exactly = 0) { BackgroundWorkScheduler.WorkType.DIAGNOSIS_TEST_RESULT_PERIODIC_WORKER.stop() }
+            assert(result is ListenableWorker.Result.Success)
+        }
+    }
+
+    @Test
+    fun testRetryWhenExceptionIsThrown() {
+        runBlockingTest {
+            coEvery { submissionService.asyncRequestTestResult(registrationToken) } throws Exception()
+            val worker = createWorker()
+            val result = worker.doWork()
+            coVerify(exactly = 1) { submissionService.asyncRequestTestResult(any()) }
+            coVerify(exactly = 0) { BackgroundWorkScheduler.WorkType.DIAGNOSIS_TEST_RESULT_PERIODIC_WORKER.stop() }
+            result shouldBe ListenableWorker.Result.retry()
+        }
+    }
+
+    private fun createWorker() = DiagnosisTestResultRetrievalPeriodicWorker(
+        context,
+        workerParams,
+        testResultAvailableNotificationService,
+        notificationHelper,
+        submissionSettings,
+        submissionService,
+        timeStamper
+    )
+}