Biometric Unlock

Biometric Unlock with expo-local-authentication

A saved sign-in lets anyone holding the unlocked phone order books as its owner, so shopping apps ask for a fingerprint or the screen lock before reusing it. expo-local-authentication shows Android's BiometricPrompt (Face ID or Touch ID on iOS, with the faceIDPermission text its config plugin writes):

src/auth/unlock.ts: asking for biometrics or the screen lock (excerpt)TypeScript
export async function unlock() {
  const level = await LocalAuthentication.getEnrolledLevelAsync();
  console.log('hardware:', await LocalAuthentication.hasHardwareAsync(),
    'enrolled level:', SecurityLevel[level]);
  if (level === SecurityLevel.NONE) return true;        // no screen lock: nothing to ask
  const result = await LocalAuthentication.authenticateAsync({
    promptMessage: 'Unlock BookNest',
    promptSubtitle: 'Your saved sign-in is locked',
  });
  console.log('unlock:', result.success ? 'success' : result.error);
  return result.success;
}

The emulator can do this for real: adb shell locksettings set-pin 1111 set a PIN, the fingerprint setup screen enrolled a finger, and adb -s emulator-5554 emu finger touch 1 touched the sensor. On the next cold start, uiautomator read the prompt as Unlock BookNest, Your saved sign-in is locked, Fingerprint sensor and Use PIN (screenshots of this secure window come out black). After one more touch, logcat showed enrolled level: BIOMETRIC_STRONG and unlock: success.

The prompt offers the PIN as a fallback unless you pass disableDeviceFallback: true. The check runs in JavaScript, so it stops a curious borrower, not an attacker with a debugger; for that, save the tokens with SecureStore's requireAuthentication: true, and the Keystore itself refuses to decrypt them without one.