用户拒绝后检测面容 ID 被禁用 LAPolicy.deviceOwnerAuthentication

Detect faceID disabled after user declining LAPolicy.deviceOwnerAuthentication

有没有办法检测用户在使用“LAContext().evaluatePolicy(.deviceOwnerAuthentication, localizedReason: someReason)”后是否拒绝了生物识别 (faceID)?

例如,

  1. 用户首次登录时系统会提示应用程序是否可以使用他们的生物识别技术
  2. 用户拒绝生物识别然后提示输入密码
  3. 用户拒绝密码

看来 canEvaluatePolicy returns 对 “LAContext().canEvaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, error: nil)”直到我关闭并重新打开应用程序。

我希望能够提醒用户他们可以在他们的应用程序设置中打开 faceID。

// Declare You're own Error type to handle possible errors
enum BiometryError: Swift.Error, LocalizedError {
    case unavailable, // Biometry unavailable
         failed,      // Can't verify
         cancel,      // User pressed cancel
         failback,    // User choose password
         locked,      // Biometry is locked
         enrolled,    // Biometry not setup
         succsess     // Success

    init(error: LAError) {
        switch error {
        case LAError.authenticationFailed:
            self = .failed
        case LAError.userCancel:
            self = .cancel
        case LAError.userFallback:
            self = .failback
        case LAError.biometryNotAvailable:
            self = .unavailable
        case LAError.biometryNotEnrolled:
            self = .enrolled
        case LAError.biometryLockout:
            self = .locked
        default:
            self = .unavailable
        }
    }
    
    public var errorDescription: String? {
        switch self {
        case .unavailable:
            return "Unavailable"
        case .failed:
            return "Failed"
        case .cancel:
            return "Cancel"
        case .failback:
            return "Failback"
        case .locked:
            return "Locked"
        case .enrolled:
            return "Enrolled"
        case .succsess:
            return "Succsess"

        }
    }
}



    // Authenticate method
    func authenticateBiometry(reply callback: @escaping (Bool, BiometryError?) -> Void) {
            
        LAContext().evaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, localizedReason: "reason") { success, error in
            if let error = error as? LAError, !success {
                // Here in this callback You can handle error and show alert if You want
                callback(false, BiometryError(error: error))
            } else  {
                // Success
                callback(true, nil)
            }
        }

    }

似乎没有办法确定您在问题中描述的情况。

我注意到 canEvaluatePolicy 的文档指出:

Don’t store the return value from this method because it might change as a result of changes in the system. For example, a user might disable Touch ID after you call this method. However, the reported value does remain consistent until your app enters the background.

然而,在测试中似乎即使将应用程序置于后台也不会改变 canEvaluatePolicy 返回的值。

正如您在问题中所指出的,返回的值在应用程序重新启动之前不会改变。您还会看到,如果您进入首选项并切换应用程序的生物识别设置,那么您的应用程序实际上会重新启动。其他与隐私相关的设置也会发生同样的过程。

如果您确定它已被拒绝,您可以在后续启动时提供生物识别身份验证,但您应该警惕在用户已经做出决定时窃听他们。

您可以使用的另一种方法是尝试 LAContext().evaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, localizedReason: "reason"),如果由于生物识别被拒绝而失败,请使用 LAContext().evaluatePolicy(.deviceOwnerAuthentication, localizedReason: "reason") 重试身份验证,这将立即提示输入密码。