touchIDLockout在iOS 11.0中已弃用 [英] touchIDLockout deprecated in iOS 11.0

查看:448
本文介绍了touchIDLockout在iOS 11.0中已弃用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

使用Xcode 9为IOS11编译我的应用程序时,我收到以下警告:

When compiling my Application with Xcode 9 for IOS11 I get the following warnings:

warning: 'touchIDLockout' was deprecated in iOS 11.0: use LAErrorBiometryLockout

warning: 'touchIDNotEnrolled' was deprecated in iOS 11.0: use LAErrorBiometryNotEnrolled

warning: 'touchIDNotAvailable' was deprecated in iOS 11.0: use LAErrorBiometryNotAvailable

我正在使用touchID但我没有使用touchIdLockout ... cste且touchID工作正常。

I'm using touchID but I'm not using touchIdLockout...cste and the touchID is working correctly.

如何删除这些警告?

我将此追踪到一个原因。从我的代码中的LocalAuthentication框架引用 LAError 就足以显示这些警告。

I tracked this down to a single cause. It's enough to reference LAError from the LocalAuthentication framework in my code to make these warnings appear.

重现的步骤(试过Xcode 9.2):

Steps to reproduce (tried in Xcode 9.2):


  1. 创建一个新的iOS应用程序(单视图模板)。请注意,iOS部署目标设置为iOS 11.2。

  2. 将这些行添加到 AppDelegate.swift

import LocalAuthentication

中的一行appDidFinishLaunching

func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
    let _: LAError? = nil
    return true
}


  • 构建应用程序。

  • Build the app.

    让_:LAError? = nil 行足以使三个警告出现。但是,警告与任何特定代码行都没有关联。它们出现在构建日志中,没有任何文件/行引用:

    The let _: LAError? = nil line is enough to make the three warnings appear. The warnings are not associated with any particular line of code, though. They appear in the build log without any file/line reference:

    <unknown>:0: warning: 'touchIDLockout' was deprecated in iOS 11.0: use LAErrorBiometryLockout
    <unknown>:0: warning: 'touchIDNotEnrolled' was deprecated in iOS 11.0: use LAErrorBiometryNotEnrolled
    <unknown>:0: warning: 'touchIDNotAvailable' was deprecated in iOS 11.0: use LAErrorBiometryNotAvailable
    

    以下是截图: Xcode中警告的屏幕截图

    示例项目: 下载示例项目(Xcode 9.2)

    作为参考,我向Apple报告了此情况。雷达#36028653。

    For reference, I reported this to Apple. Radar #36028653.

    推荐答案

    简答:这对我来说看起来像编译器错误,导致
    导入一个C枚举,它定义了多个常量
    ,具有相同的值。

    Short answer: It looks like a compiler bug to me, caused by the import of a C enumeration which defines multiple constants with the same value.

    长答案:不幸的是我没有解决方法如何避免弃用
    警告,只有可能的解释是什么导致它。

    Long answer: Unfortunately I do not have a solution how to avoid the deprecation warning, only a possible explanation what causes it.

    LAError 代码定义为
    中的C枚举< LocalAuthentication框架中的LAError.h> 。以下是该定义的
    摘录:

    The LAError codes are defined as a C enumeration in <LAError.h> in the LocalAuthentication framework. Here is an extract of that definition:

    // Error codes
    #define kLAErrorAuthenticationFailed                       -1
    #define kLAErrorUserCancel                                 -2
    // ...
    #define kLAErrorTouchIDNotAvailable                        -6
    #define kLAErrorTouchIDNotEnrolled                         -7
    #define kLAErrorTouchIDLockout                             -8
    // ...
    #define kLAErrorBiometryNotAvailable                        kLAErrorTouchIDNotAvailable
    #define kLAErrorBiometryNotEnrolled                         kLAErrorTouchIDNotEnrolled
    #define kLAErrorBiometryLockout                             kLAErrorTouchIDLockout
    
    typedef NS_ENUM(NSInteger, LAError)
    {
        LAErrorAuthenticationFailed = kLAErrorAuthenticationFailed,
        LAErrorUserCancel = kLAErrorUserCancel,
        // ...
        LAErrorTouchIDNotAvailable NS_ENUM_DEPRECATED(10_10, 10_13, 8_0, 11_0, "use LAErrorBiometryNotAvailable") = kLAErrorTouchIDNotAvailable,
        LAErrorTouchIDNotEnrolled NS_ENUM_DEPRECATED(10_10, 10_13, 8_0, 11_0, "use LAErrorBiometryNotEnrolled") = kLAErrorTouchIDNotEnrolled,
        LAErrorTouchIDLockout NS_ENUM_DEPRECATED(10_11, 10_13, 9_0, 11_0, "use LAErrorBiometryLockout")
        __WATCHOS_DEPRECATED(3.0, 4.0, "use LAErrorBiometryLockout") __TVOS_DEPRECATED(10.0, 11.0, "use LAErrorBiometryLockout") = kLAErrorTouchIDLockout,
        // ...
        LAErrorBiometryNotAvailable NS_ENUM_AVAILABLE(10_13, 11_0) __WATCHOS_AVAILABLE(4.0) __TVOS_AVAILABLE(11.0) = kLAErrorBiometryNotAvailable,
        LAErrorBiometryNotEnrolled NS_ENUM_AVAILABLE(10_13, 11_0) __WATCHOS_AVAILABLE(4.0) __TVOS_AVAILABLE(11.0) = kLAErrorBiometryNotEnrolled,
        LAErrorBiometryLockout NS_ENUM_AVAILABLE(10_13, 11_0) __WATCHOS_AVAILABLE(4.0) __TVOS_AVAILABLE(11.0) = kLAErrorBiometryLockout,
        // ...
    } NS_ENUM_AVAILABLE(10_10, 8_0) __WATCHOS_AVAILABLE(3.0) __TVOS_AVAILABLE(10.0);
    

    可以看到旧(已弃用)和新错误代码使用
    相同的值。例如, LAErrorTouchIDNotAvailable LAErrorBiometryNotAvailable 都定义为 -6

    One can see that "old" (deprecated) and the "new" error codes use the same values. For example, both LAErrorTouchIDNotAvailable and LAErrorBiometryNotAvailable are defined as -6.

    这在C中完全有效,但Swift enum 的原始值必须为
    相互独立。显然,Swift导入器通过
    解决了将新/重复的情况映射到静态变量的问题。

    That is perfectly valid in C, but the raw values of a Swift enum must be mutually distinct. Apparently the Swift importer solves that by mapping the new/duplicate cases to static variables.

    这是Swift映射的摘录:

    Here is an extract of the Swift mapping:

    public struct LAError {
    
        public init(_nsError: NSError)
        public static var _nsErrorDomain: String { get }
    
    
        public enum Code : Int {
            case authenticationFailed
            case userCancel
            // ...
            @available(iOS, introduced: 8.0, deprecated: 11.0, message: "use LAErrorBiometryNotAvailable")
            case touchIDNotAvailable
            @available(iOS, introduced: 8.0, deprecated: 11.0, message: "use LAErrorBiometryNotEnrolled")
            case touchIDNotEnrolled
            @available(iOS, introduced: 9.0, deprecated: 11.0, message: "use LAErrorBiometryLockout")
            case touchIDLockout
            // ...
            @available(iOS 11.0, *)
            public static var biometryNotAvailable: LAError.Code { get }
            @available(iOS 11.0, *)
            public static var biometryNotEnrolled: LAError.Code { get }
            @available(iOS 11.0, *)
            public static var biometryLockout: LAError.Code { get }
            // ...
        }
    
        // ...
    }
    

    这似乎是弃用警告的原因,而且对于swift-users邮件列表中报告的问题也是

    And this seems to be the cause for the deprecation warnings, and also for the problem reported on the swift-users mailing list

    • [swift-users] Handle deprecated enum cases from a library

    它是无法为 LAError 写一个详尽且无警告的
    开关语句。

    that it is impossible to write an exhaustive and warning-free switch statement for LAError.

    为了证明我的推测,我用自定义的
    枚举重现了这个问题:将以下定义添加到macOS 10.13或iOS 11 pro的桥接头
    文件中ject:

    To prove my conjecture, I have reproduced the problem with a custom enumeration: Add the following definition to the bridging header file of an macOS 10.13 or iOS 11 project:

    #import <Foundation/Foundation.h>
    
    typedef NS_ENUM(NSInteger, MyEnum)
    {
        MyEnumA = 1,
        MyEnumB = 2,
        MyEnumC NS_ENUM_DEPRECATED(10_10, 10_13, 8_0, 11_0, "use MyEnumNewC") = 3,
    
        MyEnumNewC NS_ENUM_AVAILABLE(10_13, 11_0) = 3,
    };
    

    这是导入到Swift的

    This is imported to Swift as

     public enum MyEnum : Int {
        case A
        case B
        @available(OSX, introduced: 10_10, deprecated: 10_13, message: "use MyEnumNewC")
        case C
    
        @available(OSX 10_13, *)
        public static var newC: MyEnum { get }
     }
    

    第一个(不同的)枚举值有3个案例,重复值有静态
    属性。

    with 3 cases for the first (distinct) enum values, and a static property for the duplicate value.

    事实上,任何使用 MyEnum 都会触发弃用警告:

    And indeed, any use of MyEnum triggers a deprecation warning:

    // main.swift:
    print(MyEnum.A) // Or: let _: MyEnum? = nil
    
    // Build log:
    // <unknown>:0: warning: 'C' was deprecated in OS X 10.13: use MyEnumNewC
    

    此外,无法在
    开关语句中使用新的枚举值:

    In addition, it is not possible to use the new enum value in a switch statement:

    func foo(err: MyEnum) {
        switch err {
        case .A:
            print("A")
        case .B:
            print("B")
        case .newC:
            print("C")
        }
    }
    
    // Build log:
    // main.swift:12:9: error: switch must be exhaustive
    // <unknown>:0: warning: 'C' was deprecated in OS X 10.13: use MyEnumNewC
    

    即使编译器(显然)知道这些情况是详尽无遗的:

    even if the compiler (apparently) knows that these cases are exhaustive:

    func foo(err: MyEnum) {
        switch err { // Switch must be exhaustive
        case .A:
            print("A")
        case .B:
            print("B")
        case .newC:
            print("C")
        default:
            print("default")
        }
    }
    
    // Build log:
    // <unknown>:0: warning: 'C' was deprecated in OS X 10.13: use MyEnumNewC
    // main.swift:19:9: warning: default will never be executed
    

    这看起来像是一个编译器错误。

    This looks like a compiler bug to me.

    这篇关于touchIDLockout在iOS 11.0中已弃用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

  • 查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆