• IOS 8 关于 Touch ID


    一、什么是Touch ID?

    Touch ID是在iPhone 5s后的设备上出现的指纹识别。Apple在IOS 8中开放给第三方APP使用。 可以使用 Touch ID 来验证用户的身份,用户经验证后才能访问你 app 中的部分或全部内容。指纹数据将受到保护,不会被 iOS 或其他 app 存取。另外即将推出的Apple pay也是与Touch ID紧密相关的。

    二、比较适合哪些应用场景?

    涉及到个⼈私密性信息较强的应⽤(银⾏账号密码等)

    优点:相对于以往的密码验证更安全,方便;

    缺点:当前每台设备最多设置5个Touch ID,重启手机需要重新输入密码。

    三、如何使用?

    1.验证Touch ID是否可用,即当前设备是否支持Touch ID,且用户是否在设置中设置了一个Touch ID

    - (void)canEvaluatePolicy
    {
        LAContext *context = [[LAContext alloc] init];
        __block  NSString *msg;
        NSError *error;
        BOOL success;
        
        // test if we can evaluate the policy, this test will tell us if Touch ID is available and enrolled
        success = [context canEvaluatePolicy: LAPolicyDeviceOwnerAuthenticationWithBiometrics error:&error];
        if (success) {
            msg =[NSString stringWithFormat:NSLocalizedString(@"TOUCH_ID_IS_AVAILABLE", nil)];
        } else {
            msg =[NSString stringWithFormat:NSLocalizedString(@"TOUCH_ID_IS_NOT_AVAILABLE", nil)];
        }
        [super printResult:self.textView message:msg];
        
    }
    

      

    2.验证

    - (void)evaluatePolicy
    {
        LAContext *context = [[LAContext alloc] init];
        __block  NSString *msg;
        
        // show the authentication UI with our reason string
        [context evaluatePolicy:LAPolicyDeviceOwnerAuthenticationWithBiometrics localizedReason:NSLocalizedString(@"UNLOCK_ACCESS_TO_LOCKED_FATURE", nil) reply:
         ^(BOOL success, NSError *authenticationError) {
             if (success) {
                 msg =[NSString stringWithFormat:NSLocalizedString(@"EVALUATE_POLICY_SUCCESS", nil)];
             } else {
                 msg = [NSString stringWithFormat:NSLocalizedString(@"EVALUATE_POLICY_WITH_ERROR", nil), authenticationError.localizedDescription];
             }
             [self printResult:self.textView message:msg];
         }];
        
    }
    

      支持自定义密码验证:

    - (void)evaluatePolicy2
    {
        LAContext *context = [[LAContext alloc] init];
        __block  NSString *msg;
        
        // set text for the localized fallback button
        context.localizedFallbackTitle = NSLocalizedString(@"TOUCH_ID_FALLBACK",nil);
        
        // show the authentication UI with our reason string
        [context evaluatePolicy:LAPolicyDeviceOwnerAuthenticationWithBiometrics localizedReason:NSLocalizedString(@"UNLOCK_ACCESS_TO_LOCKED_FATURE", nil) reply:
         ^(BOOL success, NSError *authenticationError) {
             if (success) {
                 msg =[NSString stringWithFormat:NSLocalizedString(@"EVALUATE_POLICY_SUCCESS", nil)];
             } else {
                 msg = [NSString stringWithFormat:NSLocalizedString(@"EVALUATE_POLICY_WITH_ERROR", nil), authenticationError.localizedDescription];
             }
             [self printResult:self.textView message:msg];
         }];
        
    }
    

     

    四、KeyChain 验证

    说到Touch ID就必须提Keychain,系统提供给APP存放密码的”数据库“。一般我们将密码存在APP 的独立存储中,当用户删除APP后其密码也就一并删除了,用Keychain可以将用户的密码长久保存。以前获取keychain中的密码需要输入设备的密码,有了Touch ID后就可以更安全快捷的获取密码。另外,⾃⼰的程序只能访问⾃⼰的keychain,相同bundle的程序通过设置group可以互相共享同组的keychain,从⽽实现程序间可以共同访问⼀些数

    据。

    旧的未使用Touch ID的方式添加密码到Keychain:

        NSDictionary *attributes = @{
            (__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
            (__bridge id)kSecAttrService: @"SampleService",
            (__bridge id)kSecValueData: [@"SECRET_PASSWORD_TEXT" dataUsingEncoding:NSUTF8StringEncoding],
            (__bridge id)kSecUseNoAuthenticationUI: @YES,
    //        (__bridge id)kSecAttrAccessControl: (__bridge_transfer id)sacObject
            };
        
        dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
            OSStatus status =  SecItemAdd((__bridge CFDictionaryRef)attributes, nil);
            
            NSString *msg = [NSString stringWithFormat:NSLocalizedString(@"SEC_ITEM_ADD_STATUS", nil), [self keychainErrorToString:status]];
            [self printResult:self.textView message:msg];
        });
    

      使用Touch ID的 方式:

        NSDictionary *attributes = @{
            (__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
            (__bridge id)kSecAttrService: @"SampleService",
            (__bridge id)kSecValueData: [@"SECRET_PASSWORD_TEXT" dataUsingEncoding:NSUTF8StringEncoding],
            (__bridge id)kSecUseNoAuthenticationUI: @YES,
            (__bridge id)kSecAttrAccessControl: (__bridge_transfer id)sacObject
            };
        
        dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
            OSStatus status =  SecItemAdd((__bridge CFDictionaryRef)attributes, nil);
            
            NSString *msg = [NSString stringWithFormat:NSLocalizedString(@"SEC_ITEM_ADD_STATUS", nil), [self keychainErrorToString:status]];
            [self printResult:self.textView message:msg];
        });
    

      

    删除keychain中的密码:

    - (void)deleteItemAsync
    {
        NSDictionary *query = @{
            (__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
            (__bridge id)kSecAttrService: @"SampleService"
            };
        
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
            OSStatus status = SecItemDelete((__bridge CFDictionaryRef)(query));
            
            NSString *msg = [NSString stringWithFormat:NSLocalizedString(@"SEC_ITEM_DELETE_STATUS", nil), [self keychainErrorToString:status]];
            [super printResult:self.textView message:msg];
        });
    }
    

      

    更新KeyChain中的密码:

    - (void)updateItemAsync
    {
        NSDictionary *query = @{
            (__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
            (__bridge id)kSecAttrService: @"SampleService",
            (__bridge id)kSecUseOperationPrompt: @"Authenticate to update your password"
            };
        
        NSDictionary *changes = @{
            (__bridge id)kSecValueData: [@"UPDATED_SECRET_PASSWORD_TEXT" dataUsingEncoding:NSUTF8StringEncoding]
            };
        
        dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
            OSStatus status = SecItemUpdate((__bridge CFDictionaryRef)query, (__bridge CFDictionaryRef)changes);
            NSString *msg = [NSString stringWithFormat:NSLocalizedString(@"SEC_ITEM_UPDATE_STATUS", nil), [self keychainErrorToString:status]];
            [super printResult:self.textView message:msg];
        });
    }
    

      

    获取Keychain中的密码:

    - (void)copyMatchingAsync
    {
        NSDictionary *query = @{
            (__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
            (__bridge id)kSecAttrService: @"SampleService",
            (__bridge id)kSecReturnData: @YES,
            (__bridge id)kSecUseOperationPrompt: NSLocalizedString(@"AUTHENTICATE_TO_ACCESS_SERVICE_PASSWORD", nil)
            };
        
        dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
            CFTypeRef dataTypeRef = NULL;
            NSString *msg;
            
            OSStatus status = SecItemCopyMatching((__bridge CFDictionaryRef)(query), &dataTypeRef);
            if (status == errSecSuccess)
            {
                NSData *resultData = ( __bridge_transfer NSData *)dataTypeRef;
                NSString * result = [[NSString alloc] initWithData:resultData encoding:NSUTF8StringEncoding];
            
                msg = [NSString stringWithFormat:NSLocalizedString(@"RESULT", nil), result];
            } else {
                msg = [NSString stringWithFormat:NSLocalizedString(@"SEC_ITEM_COPY_MATCHING_STATUS", nil), [self keychainErrorToString:status]];
            }
            [self printResult:self.textView message:msg];
        });
    }
    

      

    Demo地址:https://developer.apple.com/library/ios/samplecode/KeychainTouchID/Introduction/Intro.html#//apple_ref/doc/uid/TP40014530-Intro-DontLinkElementID_2

  • 相关阅读:
    如何让DataGridView根据数据“0”或“1”等值显示为“是”或“否”
    GridView控件RowDataBound事件中获取列字段的几种方法
    DataGridView 显示和隐藏DataGridViewButtonCell按钮的办法
    ASP.NET会话(Session)保存模式
    Update 两个表之间数据更新
    两表相连去除重复数据
    BS网站与Winform窗体的数据交互(WebService实现)
    winform 下实现消息传递机制
    SQL常用字符串函数
    HDU 威威猫系列故事——篮球梦
  • 原文地址:https://www.cnblogs.com/dokaygang128/p/4112837.html
Copyright © 2020-2023  润新知