Fixed
Status Update
Comments
cs...@google.com <cs...@google.com> #2
Thank you for reporting this issue. For us to further investigate this issue, please provide the following additional information:
Please provide sample project or apk to reproduce the issue. Also mention the steps to be followed for reproducing the issue with the given sample project or apk.
Expected output
What do you expect to occur?
Current output
What do you see instead?
Android bug report
After reproducing the issue, press the volume up, volume down, and power button simultaneously. This will capture a bug report on your device in the “bug reports” directory. Attach the bug report file to this issue.
Alternate method:
After reproducing the issue, navigate to developer settings, ensure ‘USB debugging’ is enabled, then enable ‘Bug report shortcut’. To take bug report, hold the power button and select the ‘Take bug report’ option.
NOTE: Please upload the files to Google Drive and share the folder to android-bugreport@google.com, then share the link here.
Please provide sample project or apk to reproduce the issue. Also mention the steps to be followed for reproducing the issue with the given sample project or apk.
Expected output
What do you expect to occur?
Current output
What do you see instead?
Android bug report
After reproducing the issue, press the volume up, volume down, and power button simultaneously. This will capture a bug report on your device in the “bug reports” directory. Attach the bug report file to this issue.
Alternate method:
After reproducing the issue, navigate to developer settings, ensure ‘USB debugging’ is enabled, then enable ‘Bug report shortcut’. To take bug report, hold the power button and select the ‘Take bug report’ option.
NOTE: Please upload the files to Google Drive and share the folder to android-bugreport@google.com, then share the link here.
ap...@google.com <ap...@google.com> #3
ok, I did some more research, turns out that callback notification goes to the if we press "cancel" button but goes wrong when authentication succeeds
as you can see in the attached project
if you open the bio-prompt in the 1st Fragment and authenticate
and after that you go to the 2nd Fragment and authenticate in the bio-prompt
callback notifies the Fragment1 instead of the Fragment2 as you can see in the logs
expected result is that Fragment2 is notified instead of Fragment1
also if you first go to Fragment2 and after that you go to Fragment1 always opening the prompt and doing the authentication
Fragment2 is notified instead of Fragment1
funny thing is that doing cancel instead of authentication notification works ok
https://drive.google.com/open?id=1ZVhp9sFBJ6pa1bKzHg1AM5tF5XnmyFMM
as you can see in the attached project
if you open the bio-prompt in the 1st Fragment and authenticate
and after that you go to the 2nd Fragment and authenticate in the bio-prompt
callback notifies the Fragment1 instead of the Fragment2 as you can see in the logs
expected result is that Fragment2 is notified instead of Fragment1
also if you first go to Fragment2 and after that you go to Fragment1 always opening the prompt and doing the authentication
Fragment2 is notified instead of Fragment1
funny thing is that doing cancel instead of authentication notification works ok
ch...@google.com <ch...@google.com>
ap...@google.com <ap...@google.com> #4
manually closing the FingerprintHelperFragment works as a workaround
```
override fun onPause() {
// WORKAROUND forhttps://issuetracker.google.com/issues/123857949
activity?.let { activity ->
activity.supportFragmentManager.findFragmentByTag("FingerprintHelperFragment")?.let {
activity.supportFragmentManager.beginTransaction().remove(it).commitAllowingStateLoss()
}
super.onPause()
}
}
```
```
override fun onPause() {
// WORKAROUND for
activity?.let { activity ->
activity.supportFragmentManager.findFragmentByTag("FingerprintHelperFragment")?.let {
activity.supportFragmentManager.beginTransaction().remove(it).commitAllowingStateLoss()
}
super.onPause()
}
}
```
ae...@google.com <ae...@google.com> #6
There's might be something slightly different in the way lifecycle is being managed between O and lower, and P+
Looking at how mAuthenticationCallback is being passed around here should give us some ideas
https://cs.corp.google.com/aosp-androidx/biometric/src/main/java/androidx/biometric/BiometricPrompt.java?q=biometricprompt.java&dr
Josh can you take a look when convenient? I think the callback isn't getting to the FingerprintHelperFragment for some reason. We can also chat offline when you get to this.
Looking at how mAuthenticationCallback is being passed around here should give us some ideas
Josh can you take a look when convenient? I think the callback isn't getting to the FingerprintHelperFragment for some reason. We can also chat offline when you get to this.
ap...@google.com <ap...@google.com> #7
This bug is actually a duplicate of https://issuetracker.google.com/issues/121117380 . This issue happens because the new AuthenticationCallback is not being supplied to the biometric prompt fragments if they already exist in the FragmentManager.
Until this is fixed, users of this library MUST manually check for and remove any biometric prompt fragments from the FragmentManager before attempting to call BiometricPrompt#authenticate().
Until this is fixed, users of this library MUST manually check for and remove any biometric prompt fragments from the FragmentManager before attempting to call BiometricPrompt#authenticate().
na...@google.com <na...@google.com> #8
#7
I think that:
1. BiometricPrompt#authenticateInternal should call mFingerprintHelperFragment.setCallback method even if mFingerprintHelperFragment was existed before.
2. FingerprintHelperFragment#cleanup has to set mClientAuthenticationCallback and mExecutor to null to prevent leaking.
I think that:
1. BiometricPrompt#authenticateInternal should call mFingerprintHelperFragment.setCallback method even if mFingerprintHelperFragment was existed before.
2. FingerprintHelperFragment#cleanup has to set mClientAuthenticationCallback and mExecutor to null to prevent leaking.
Description
Summary
The current API for providing composition locals is very allocation heavy and requires several groups. This can be improved in several ways,
The current API will allocated an array to store the providers and a mall object to for each "provides" parameter. It will then create a persistent map of the provided values and then union of the existing map and this map as the persistent scope.
Some composable function just provide one provides which makes these allocation particularly heavey weight. Also, constructing the union persisent map can be expensive.
Proposals
1. Special case single provider
The single provider can be special cased to avoid the creating of the array, the
ProvidesValue
instance and the persistent map.This would require new API that takes the composition local definition and the value (as well as a corresponding lint with a quick-fix to migrate code to the new API).
2. Allow building the map directly outside composition.
Instead of building the map in composition, the local map (for large maps) can be constructed as helper or outside composition entirely. This is specifically helpful when the map is conditionally built the current API requires paying the local provider overhead multiple times for shared or conditional providers.
This will require a new API that allows providing a composition local map directly.
3. Faster persistent maps
The persistent map is a general map that handles many cases well but it doesn't handle small changes well (such as adding a single value). We could provide a wrapper around the persistent map that will handles the special cases found in the Compose library better such as a singleton wrapper for cases, such when a single value is provided.
This doesn't require any API changes.