Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 3c561256 authored by Steve Elliott's avatar Steve Elliott
Browse files

Replace verbose @Provider with a private @Binds

The original version of the dagger code used a Provider so that the
private SensitiveContentCoordinatorImpl class was not exposed as part of
the public API signature (which would cause a compilation error).

This change utilizes a quirk with Dagger Module "includes" where you are
able to include a private Module inside of a public one. This private
module is able to use the symbols private to the Kotlin file (in this
case, SensitiveContentCoordinatorImpl).

The downside here is that the tests have become slightly more verbose.

Test: atest SensitiveContentCoordinatorTest
Change-Id: I06d87e68e5b40f432bc39d1015b54c03f141fc4d
parent badac481
Loading
Loading
Loading
Loading
+11 −11
Original line number Diff line number Diff line
@@ -21,8 +21,9 @@ import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.dagger.qualifiers.Main
import com.android.systemui.util.ListenerSet
import com.android.systemui.util.concurrency.DelayableExecutor
import dagger.Binds
import dagger.Module
import dagger.Provides
import javax.inject.Inject

/**
 * Choreographs evaluation resulting from multiple asynchronous sources. Specifically, it exposes
@@ -46,22 +47,21 @@ interface NotifPipelineChoreographer {
    fun removeOnEvalListener(onEvalListener: Runnable)
}

@Module(includes = [PrivateModule::class])
object NotifPipelineChoreographerModule

@Module
object NotifPipelineChoreographerModule {
    @Provides
    @JvmStatic
    @SysUISingleton
    fun provideChoreographer(
        choreographer: Choreographer,
        @Main mainExecutor: DelayableExecutor
    ): NotifPipelineChoreographer = NotifPipelineChoreographerImpl(choreographer, mainExecutor)
private interface PrivateModule {
    @Binds
    fun bindChoreographer(impl: NotifPipelineChoreographerImpl): NotifPipelineChoreographer
}

private const val TIMEOUT_MS: Long = 100

private class NotifPipelineChoreographerImpl(
@SysUISingleton
private class NotifPipelineChoreographerImpl @Inject constructor(
    private val viewChoreographer: Choreographer,
    private val executor: DelayableExecutor
    @Main private val executor: DelayableExecutor
) : NotifPipelineChoreographer {

    private val listeners = ListenerSet<Runnable>()
+10 −15
Original line number Diff line number Diff line
@@ -30,29 +30,24 @@ import com.android.systemui.statusbar.notification.collection.coordinator.dagger
import com.android.systemui.statusbar.notification.collection.listbuilder.OnBeforeRenderListListener
import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.Invalidator
import com.android.systemui.statusbar.policy.KeyguardStateController
import dagger.Binds
import dagger.Module
import dagger.Provides
import javax.inject.Inject

@Module(includes = [PrivateModule::class])
interface SensitiveContentCoordinatorModule

@Module
object SensitiveContentCoordinatorModule {
    @Provides
    @JvmStatic
    @CoordinatorScope
    fun provideCoordinator(
        dynamicPrivacyController: DynamicPrivacyController,
        lockscreenUserManager: NotificationLockscreenUserManager,
        keyguardUpdateMonitor: KeyguardUpdateMonitor,
        statusBarStateController: StatusBarStateController,
        keyguardStateController: KeyguardStateController
    ): SensitiveContentCoordinator =
            SensitiveContentCoordinatorImpl(dynamicPrivacyController, lockscreenUserManager,
            keyguardUpdateMonitor, statusBarStateController, keyguardStateController)
private interface PrivateModule {
    @Binds
    fun bindCoordinator(impl: SensitiveContentCoordinatorImpl): SensitiveContentCoordinator
}

/** Coordinates re-inflation and post-processing of sensitive notification content. */
interface SensitiveContentCoordinator : Coordinator

private class SensitiveContentCoordinatorImpl(
@CoordinatorScope
private class SensitiveContentCoordinatorImpl @Inject constructor(
    private val dynamicPrivacyController: DynamicPrivacyController,
    private val lockscreenUserManager: NotificationLockscreenUserManager,
    private val keyguardUpdateMonitor: KeyguardUpdateMonitor,
+23 −2
Original line number Diff line number Diff line
@@ -20,10 +20,14 @@ import android.testing.AndroidTestingRunner
import android.view.Choreographer
import androidx.test.filters.SmallTest
import com.android.systemui.SysuiTestCase
import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.dagger.qualifiers.Main
import com.android.systemui.util.concurrency.DelayableExecutor
import com.android.systemui.util.mockito.any
import com.android.systemui.util.mockito.mock
import com.android.systemui.util.mockito.withArgCaptor
import dagger.BindsInstance
import dagger.Component
import org.junit.Assert.assertTrue
import org.junit.Test
import org.junit.runner.RunWith
@@ -41,8 +45,10 @@ class NotifPipelineChoreographerTest : SysuiTestCase() {
        whenever(it.executeDelayed(any(), anyLong())).thenReturn(timeoueSubscription)
    }

    val pipelineChoreographer: NotifPipelineChoreographer = NotifPipelineChoreographerModule
            .provideChoreographer(viewChoreographer, executor)
    val pipelineChoreographer: NotifPipelineChoreographer =
        DaggerNotifPipelineChoreographerTestComponent.factory()
                .create(viewChoreographer, executor)
                .choreographer

    @Test
    fun scheduleThenEvalFrameCallback() {
@@ -98,3 +104,18 @@ class NotifPipelineChoreographerTest : SysuiTestCase() {
        verify(timeoueSubscription).run()
    }
}

@SysUISingleton
@Component(modules = [NotifPipelineChoreographerModule::class])
interface NotifPipelineChoreographerTestComponent {

    val choreographer: NotifPipelineChoreographer

    @Component.Factory
    interface Factory {
        fun create(
            @BindsInstance viewChoreographer: Choreographer,
            @BindsInstance @Main executor: DelayableExecutor
        ): NotifPipelineChoreographerTestComponent
    }
}
 No newline at end of file
+31 −4
Original line number Diff line number Diff line
@@ -28,13 +28,16 @@ import com.android.systemui.statusbar.notification.DynamicPrivacyController
import com.android.systemui.statusbar.notification.collection.ListEntry
import com.android.systemui.statusbar.notification.collection.NotifPipeline
import com.android.systemui.statusbar.notification.collection.NotificationEntry
import com.android.systemui.statusbar.notification.collection.coordinator.dagger.CoordinatorScope
import com.android.systemui.statusbar.notification.collection.listbuilder.OnBeforeRenderListListener
import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.Invalidator
import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.Pluggable
import com.android.systemui.statusbar.policy.KeyguardStateController
import com.android.systemui.util.mockito.withArgCaptor
import com.android.systemui.util.mockito.any
import com.android.systemui.util.mockito.mock
import com.android.systemui.util.mockito.withArgCaptor
import dagger.BindsInstance
import dagger.Component
import org.junit.Test
import org.mockito.Mockito.never
import org.mockito.Mockito.verify
@@ -50,9 +53,16 @@ class SensitiveContentCoordinatorTest : SysuiTestCase() {
    val statusBarStateController: StatusBarStateController = mock()
    val keyguardStateController: KeyguardStateController = mock()

    val coordinator: SensitiveContentCoordinator = SensitiveContentCoordinatorModule
            .provideCoordinator(dynamicPrivacyController, lockscreenUserManager,
            keyguardUpdateMonitor, statusBarStateController, keyguardStateController)
    val coordinator: SensitiveContentCoordinator =
        DaggerTestSensitiveContentCoordinatorComponent
                .factory()
                .create(
                        dynamicPrivacyController,
                        lockscreenUserManager,
                        keyguardUpdateMonitor,
                        statusBarStateController,
                        keyguardStateController)
                .coordinator

    @Test
    fun onDynamicPrivacyChanged_invokeInvalidationListener() {
@@ -239,3 +249,20 @@ class SensitiveContentCoordinatorTest : SysuiTestCase() {
        }
    }
}

@CoordinatorScope
@Component(modules = [SensitiveContentCoordinatorModule::class])
interface TestSensitiveContentCoordinatorComponent {
    val coordinator: SensitiveContentCoordinator

    @Component.Factory
    interface Factory {
        fun create(
            @BindsInstance dynamicPrivacyController: DynamicPrivacyController,
            @BindsInstance lockscreenUserManager: NotificationLockscreenUserManager,
            @BindsInstance keyguardUpdateMonitor: KeyguardUpdateMonitor,
            @BindsInstance statusBarStateController: StatusBarStateController,
            @BindsInstance keyguardStateController: KeyguardStateController
        ): TestSensitiveContentCoordinatorComponent
    }
}
 No newline at end of file