AutoFill

Password, Name, Phone, Address, Email, 2FACode ...

Posted by poos on December 6, 2019

相关链接

Apple document:

password_autofill/about_the_password_autofill_workflow

Video:

wwdc2017/206

大类区分为用户名密码(Password)和其他类型(Name, Phone, Address, Email, 2FACode…)的 AutoFill。

总体来说,基础版本的 auto-fill 是被 iOS system 自动发现的,也就是说你可以无需适配使用这个功能。

但是,为了让用户能够自动填入与当前 app 相匹配的用户密码,你可以将 app bundle id 绑定。

Password

img

默认提供的

如果有两个以上输入框(和一个确定按钮),在某一个输入框为 Secure 的时候,它和上边的那个输入框即可被自动填入用户密码。

Demo 比较简单,可以想象一下拖 Storyboard,几个 Textfield 即可验证。

基于 Associated Domain

App

像添加 Universal link 一样,可以通过添加 webcredentials 来给应用指定 domain。

Project -> Capabilities -> Associated Domains

1
2
links::example.com
webcredentials:example.com
Server

配置 apple-app-site-association

1
2
3
4
5
6
{
   "webcredentials": {
       "apps": [    "AppPrefix.com.example.DemoApp",
                    "AppPrefix.com.example.DemoAdminApp" ]
    }
}

Keychain Sharing

这个是当一个 Apple 账号发布了多个应用程序, 那么创建一个组,可以让这多个应用共享用户信息。在设置中填入要共享的应用的 Bundle Identifier 即可。

Project -> Capabilities -> Keychain Sharing

1
2
com.example.DemoApp
com.example.DemoAdminApp

其他类型的输入框

当一个输入框被设置了 content type,那么就知道了这个输入框的类型,iOS 就可以提供相应的快速键入选项。

API:

1
2
3
// The textContentType property is to provide the keyboard with extra information about the semantic intent of the text document.
@available(iOS 10.0, *)
optional var textContentType: UITextContentType! { get set } // default is nil

Content:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
extension UITextContentType {


    @available(iOS 10.0, *)
    public static let name: UITextContentType

    @available(iOS 10.0, *)
    public static let namePrefix: UITextContentType

    @available(iOS 10.0, *)
    public static let givenName: UITextContentType

    @available(iOS 10.0, *)
    public static let middleName: UITextContentType

    @available(iOS 10.0, *)
    public static let familyName: UITextContentType

    @available(iOS 10.0, *)
    public static let nameSuffix: UITextContentType

    @available(iOS 10.0, *)
    public static let nickname: UITextContentType

    @available(iOS 10.0, *)
    public static let jobTitle: UITextContentType

    @available(iOS 10.0, *)
    public static let organizationName: UITextContentType

    @available(iOS 10.0, *)
    public static let location: UITextContentType

    @available(iOS 10.0, *)
    public static let fullStreetAddress: UITextContentType

    @available(iOS 10.0, *)
    public static let streetAddressLine1: UITextContentType

    @available(iOS 10.0, *)
    public static let streetAddressLine2: UITextContentType

    @available(iOS 10.0, *)
    public static let addressCity: UITextContentType

    @available(iOS 10.0, *)
    public static let addressState: UITextContentType

    @available(iOS 10.0, *)
    public static let addressCityAndState: UITextContentType

    @available(iOS 10.0, *)
    public static let sublocality: UITextContentType

    @available(iOS 10.0, *)
    public static let countryName: UITextContentType

    @available(iOS 10.0, *)
    public static let postalCode: UITextContentType

    @available(iOS 10.0, *)
    public static let telephoneNumber: UITextContentType

    @available(iOS 10.0, *)
    public static let emailAddress: UITextContentType

    @available(iOS 10.0, *)
    public static let URL: UITextContentType

    @available(iOS 10.0, *)
    public static let creditCardNumber: UITextContentType

    @available(iOS 11.0, *)
    public static let username: UITextContentType

    @available(iOS 11.0, *)
    public static let password: UITextContentType

    @available(iOS 12.0, *)
    public static let newPassword: UITextContentType

    @available(iOS 12.0, *)
    public static let oneTimeCode: UITextContentType
}

FYI: TWO-FACTOR AUTHENTICATION (2FA)

原理(工作流程)

应用生命周期

当用户点击了 QuickType Bar 之后,系统会验证 Face ID(或者其他),applicationWillResignActive(_:), 然后验证完成applicationDidBecomeActive(_:)

在应用离开响应的时候,不要做 dismiss, pop 或者 TF removeFromSuperView,这些都会导致自己填入失败。 所以要注意一下应用蒙板,自动退出等特殊情况。

Textfield 生命周期

系统会发送 textDidChangeNotification 当被更新。对应到不同的输入框稍微有点差别:

  • UITextField: UITextFieldDelegate textField(_:shouldChangeCharactersIn:replacementString:)

  • UITextView: UITextViewDelegate textView(_:shouldChangeTextIn:replacementText:)

  • 自定义的继承于 UITextInput protocol 的: insertText(_:) 或者 replace(_:withText:)

总结

基于这一套,可以在不修改代码,或者少量修改代码的时候,给用户提供更多的便利。

在 Password 方面,还有一些三方的,例如 1-Password 等,虽然供应商不同,但是到 App 内部代码处理上,已经被协议化了,可以方便的使用而不作修改~