Loading packages/SystemUI/aconfig/biometrics_framework.aconfig +7 −0 Original line number Diff line number Diff line Loading @@ -12,3 +12,10 @@ flag { purpose: PURPOSE_BUGFIX } } flag { name: "cont_auth_plugin" namespace: "biometrics_framework" description: "Plugin and related API hooks for contextual auth plugins" bug: "373600589" } packages/SystemUI/multivalentTests/src/com/android/systemui/biometrics/AuthContainerViewTest.kt +1 −0 Original line number Diff line number Diff line Loading @@ -667,6 +667,7 @@ open class AuthContainerViewTest : SysuiTestCase() { faceProps, wakefulnessLifecycle, userManager, null /* authContextPlugins */, lockPatternUtils, interactionJankMonitor, { promptSelectorInteractor }, Loading packages/SystemUI/multivalentTests/src/com/android/systemui/biometrics/AuthControllerTest.java +3 −1 Original line number Diff line number Diff line Loading @@ -117,6 +117,7 @@ import org.mockito.junit.MockitoRule; import java.util.ArrayList; import java.util.List; import java.util.Optional; import java.util.Random; @RunWith(AndroidJUnit4.class) Loading Loading @@ -1187,7 +1188,8 @@ public class AuthControllerTest extends SysuiTestCase { TestableAuthController(Context context) { super(context, null /* applicationCoroutineScope */, mExecution, mCommandQueue, mActivityTaskManager, mWindowManager, mFingerprintManager, mFaceManager, () -> mUdfpsController, mDisplayManager, mFingerprintManager, mFaceManager, Optional.empty(), () -> mUdfpsController, mDisplayManager, mWakefulnessLifecycle, mUserManager, mLockPatternUtils, () -> mUdfpsLogger, () -> mLogContextInteractor, () -> mPromptSelectionInteractor, () -> mCredentialViewModel, () -> mPromptViewModel, mInteractionJankMonitor, Loading packages/SystemUI/plugin/src/com/android/systemui/plugins/AuthContextPlugin.kt 0 → 100644 +85 −0 Original line number Diff line number Diff line /* * Copyright (C) 2024 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.systemui.plugins import android.os.IBinder import android.view.View import com.android.systemui.plugins.annotations.ProvidesInterface /** * Plugin for experimental "Contextual Auth" features. * * These plugins will get raw access to low-level events about the user's environment, such as * moving in/out of trusted locations, connection status of trusted devices, auth attempts, etc. * They will also receive callbacks related to system events & transitions to enable prototypes on * sensitive surfaces like lock screen and BiometricPrompt. * * Note to rebuild the plugin jar run: m PluginDummyLib */ @ProvidesInterface(action = AuthContextPlugin.ACTION, version = AuthContextPlugin.VERSION) interface AuthContextPlugin : Plugin { /** * Called in the background when the plugin is enabled. * * This is a good time to ask your friendly [saucier] to cook up something special. The * [Plugin.onCreate] can also be used for initialization. */ fun activated(saucier: Saucier) /** * Called when a [SensitiveSurface] is first shown. * * This may be called repeatedly if the state of the surface changes after it is shown. For * example, [SensitiveSurface.BiometricPrompt.isCredential] will change if the user falls back * to a credential-based auth method. */ fun onShowingSensitiveSurface(surface: SensitiveSurface) /** * Called when a [SensitiveSurface] sensitive surface is hidden. * * This method may still be called without [onShowingSensitiveSurface] in cases of rapid * dismissal and plugins implementations should typically be idempotent. */ fun onHidingSensitiveSurface(surface: SensitiveSurface) companion object { /** Plugin action. */ const val ACTION = "com.android.systemui.action.PLUGIN_AUTH_CONTEXT" /** Plugin version. */ const val VERSION = 1 } /** Information about a sensitive surface in the framework, which the Plugin may augment. */ sealed interface SensitiveSurface { /** Information about the BiometricPrompt that is being shown to the user. */ data class BiometricPrompt(val view: View? = null, val isCredential: Boolean = false) : SensitiveSurface /** Information about bouncer. */ data class LockscreenBouncer(val view: View? = null) : SensitiveSurface } /** Ask for the special. */ interface Saucier { /** What [flavor] would you like? */ fun getSauce(flavor: String): IBinder? } } packages/SystemUI/src/com/android/systemui/biometrics/AuthContainerView.java +5 −1 Original line number Diff line number Diff line Loading @@ -64,6 +64,7 @@ import com.android.internal.jank.InteractionJankMonitor; import com.android.internal.widget.LockPatternUtils; import com.android.systemui.biometrics.AuthController.ScaleFactorProvider; import com.android.systemui.biometrics.domain.interactor.PromptSelectorInteractor; import com.android.systemui.biometrics.plugins.AuthContextPlugins; import com.android.systemui.biometrics.shared.model.BiometricModalities; import com.android.systemui.biometrics.shared.model.PromptKind; import com.android.systemui.biometrics.ui.CredentialView; Loading Loading @@ -132,6 +133,7 @@ public class AuthContainerView extends LinearLayout private final int mEffectiveUserId; private final IBinder mWindowToken = new Binder(); private final ViewCaptureAwareWindowManager mWindowManager; @Nullable private final AuthContextPlugins mAuthContextPlugins; private final Interpolator mLinearOutSlowIn; private final LockPatternUtils mLockPatternUtils; private final WakefulnessLifecycle mWakefulnessLifecycle; Loading Loading @@ -289,6 +291,7 @@ public class AuthContainerView extends LinearLayout @Nullable List<FaceSensorPropertiesInternal> faceProps, @NonNull WakefulnessLifecycle wakefulnessLifecycle, @NonNull UserManager userManager, @Nullable AuthContextPlugins authContextPlugins, @NonNull LockPatternUtils lockPatternUtils, @NonNull InteractionJankMonitor jankMonitor, @NonNull Provider<PromptSelectorInteractor> promptSelectorInteractorProvider, Loading @@ -306,6 +309,7 @@ public class AuthContainerView extends LinearLayout WindowManager wm = getContext().getSystemService(WindowManager.class); mWindowManager = new ViewCaptureAwareWindowManager(wm, lazyViewCapture, enableViewCaptureTracing()); mAuthContextPlugins = authContextPlugins; mWakefulnessLifecycle = wakefulnessLifecycle; mApplicationCoroutineScope = applicationCoroutineScope; Loading Loading @@ -446,7 +450,7 @@ public class AuthContainerView extends LinearLayout final CredentialViewModel vm = mCredentialViewModelProvider.get(); vm.setAnimateContents(animateContents); ((CredentialView) mCredentialView).init(vm, this, mPanelController, animatePanel, mBiometricCallback); mBiometricCallback, mAuthContextPlugins); mLayout.addView(mCredentialView); } Loading Loading
packages/SystemUI/aconfig/biometrics_framework.aconfig +7 −0 Original line number Diff line number Diff line Loading @@ -12,3 +12,10 @@ flag { purpose: PURPOSE_BUGFIX } } flag { name: "cont_auth_plugin" namespace: "biometrics_framework" description: "Plugin and related API hooks for contextual auth plugins" bug: "373600589" }
packages/SystemUI/multivalentTests/src/com/android/systemui/biometrics/AuthContainerViewTest.kt +1 −0 Original line number Diff line number Diff line Loading @@ -667,6 +667,7 @@ open class AuthContainerViewTest : SysuiTestCase() { faceProps, wakefulnessLifecycle, userManager, null /* authContextPlugins */, lockPatternUtils, interactionJankMonitor, { promptSelectorInteractor }, Loading
packages/SystemUI/multivalentTests/src/com/android/systemui/biometrics/AuthControllerTest.java +3 −1 Original line number Diff line number Diff line Loading @@ -117,6 +117,7 @@ import org.mockito.junit.MockitoRule; import java.util.ArrayList; import java.util.List; import java.util.Optional; import java.util.Random; @RunWith(AndroidJUnit4.class) Loading Loading @@ -1187,7 +1188,8 @@ public class AuthControllerTest extends SysuiTestCase { TestableAuthController(Context context) { super(context, null /* applicationCoroutineScope */, mExecution, mCommandQueue, mActivityTaskManager, mWindowManager, mFingerprintManager, mFaceManager, () -> mUdfpsController, mDisplayManager, mFingerprintManager, mFaceManager, Optional.empty(), () -> mUdfpsController, mDisplayManager, mWakefulnessLifecycle, mUserManager, mLockPatternUtils, () -> mUdfpsLogger, () -> mLogContextInteractor, () -> mPromptSelectionInteractor, () -> mCredentialViewModel, () -> mPromptViewModel, mInteractionJankMonitor, Loading
packages/SystemUI/plugin/src/com/android/systemui/plugins/AuthContextPlugin.kt 0 → 100644 +85 −0 Original line number Diff line number Diff line /* * Copyright (C) 2024 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.systemui.plugins import android.os.IBinder import android.view.View import com.android.systemui.plugins.annotations.ProvidesInterface /** * Plugin for experimental "Contextual Auth" features. * * These plugins will get raw access to low-level events about the user's environment, such as * moving in/out of trusted locations, connection status of trusted devices, auth attempts, etc. * They will also receive callbacks related to system events & transitions to enable prototypes on * sensitive surfaces like lock screen and BiometricPrompt. * * Note to rebuild the plugin jar run: m PluginDummyLib */ @ProvidesInterface(action = AuthContextPlugin.ACTION, version = AuthContextPlugin.VERSION) interface AuthContextPlugin : Plugin { /** * Called in the background when the plugin is enabled. * * This is a good time to ask your friendly [saucier] to cook up something special. The * [Plugin.onCreate] can also be used for initialization. */ fun activated(saucier: Saucier) /** * Called when a [SensitiveSurface] is first shown. * * This may be called repeatedly if the state of the surface changes after it is shown. For * example, [SensitiveSurface.BiometricPrompt.isCredential] will change if the user falls back * to a credential-based auth method. */ fun onShowingSensitiveSurface(surface: SensitiveSurface) /** * Called when a [SensitiveSurface] sensitive surface is hidden. * * This method may still be called without [onShowingSensitiveSurface] in cases of rapid * dismissal and plugins implementations should typically be idempotent. */ fun onHidingSensitiveSurface(surface: SensitiveSurface) companion object { /** Plugin action. */ const val ACTION = "com.android.systemui.action.PLUGIN_AUTH_CONTEXT" /** Plugin version. */ const val VERSION = 1 } /** Information about a sensitive surface in the framework, which the Plugin may augment. */ sealed interface SensitiveSurface { /** Information about the BiometricPrompt that is being shown to the user. */ data class BiometricPrompt(val view: View? = null, val isCredential: Boolean = false) : SensitiveSurface /** Information about bouncer. */ data class LockscreenBouncer(val view: View? = null) : SensitiveSurface } /** Ask for the special. */ interface Saucier { /** What [flavor] would you like? */ fun getSauce(flavor: String): IBinder? } }
packages/SystemUI/src/com/android/systemui/biometrics/AuthContainerView.java +5 −1 Original line number Diff line number Diff line Loading @@ -64,6 +64,7 @@ import com.android.internal.jank.InteractionJankMonitor; import com.android.internal.widget.LockPatternUtils; import com.android.systemui.biometrics.AuthController.ScaleFactorProvider; import com.android.systemui.biometrics.domain.interactor.PromptSelectorInteractor; import com.android.systemui.biometrics.plugins.AuthContextPlugins; import com.android.systemui.biometrics.shared.model.BiometricModalities; import com.android.systemui.biometrics.shared.model.PromptKind; import com.android.systemui.biometrics.ui.CredentialView; Loading Loading @@ -132,6 +133,7 @@ public class AuthContainerView extends LinearLayout private final int mEffectiveUserId; private final IBinder mWindowToken = new Binder(); private final ViewCaptureAwareWindowManager mWindowManager; @Nullable private final AuthContextPlugins mAuthContextPlugins; private final Interpolator mLinearOutSlowIn; private final LockPatternUtils mLockPatternUtils; private final WakefulnessLifecycle mWakefulnessLifecycle; Loading Loading @@ -289,6 +291,7 @@ public class AuthContainerView extends LinearLayout @Nullable List<FaceSensorPropertiesInternal> faceProps, @NonNull WakefulnessLifecycle wakefulnessLifecycle, @NonNull UserManager userManager, @Nullable AuthContextPlugins authContextPlugins, @NonNull LockPatternUtils lockPatternUtils, @NonNull InteractionJankMonitor jankMonitor, @NonNull Provider<PromptSelectorInteractor> promptSelectorInteractorProvider, Loading @@ -306,6 +309,7 @@ public class AuthContainerView extends LinearLayout WindowManager wm = getContext().getSystemService(WindowManager.class); mWindowManager = new ViewCaptureAwareWindowManager(wm, lazyViewCapture, enableViewCaptureTracing()); mAuthContextPlugins = authContextPlugins; mWakefulnessLifecycle = wakefulnessLifecycle; mApplicationCoroutineScope = applicationCoroutineScope; Loading Loading @@ -446,7 +450,7 @@ public class AuthContainerView extends LinearLayout final CredentialViewModel vm = mCredentialViewModelProvider.get(); vm.setAnimateContents(animateContents); ((CredentialView) mCredentialView).init(vm, this, mPanelController, animatePanel, mBiometricCallback); mBiometricCallback, mAuthContextPlugins); mLayout.addView(mCredentialView); } Loading