Android本地指纹认证后登录服务器开发流程及fido指纹登录简述

流程描述

1.app账户登录 --- 服务端返回token
2.app打开指纹登录选项,生成非对称密钥,弹出验证界面--服务端返回随机数相关数据
3.指纹验证成功后,对客户端生成的唯一标识+随机数签名 ,发送公钥和签名数据--- 服务端公钥验签,把账户与唯一标识、公钥绑定
4.退出账户---服务端返回token失效
5.点击指纹登录功能,弹出验证界面---服务端返回随机数
6.指纹验证成功后对唯一标识和随机数签名,发送签名数据---服务端验签成功后返回token

时序图
image.png
关键点说明
  • 步骤2的随机数和步骤5的需要返回随机数给第3步和第6步使用,目的是防止重放攻击(不加随机数的话,攻击者获取到即使加密的登录请求网络包也能获取token),增加安全性,避免本地相同请求读取缓存。
  • 唯一标识符可以参考Google Android开发者官方文档:唯一标识符最佳做法 | Android 开发者 | Android Developers (google.cn),我使用其中建议的一条UUID.randomUUID().toString()
  • 指纹和密钥:这里是Android 端重点
    1.首先使用Android 的keystore生成非对称密钥对,在构建秘密库初始化参数时候设置需要指纹验证才能使用私钥相关的操作
   val keyStore = KeyStore.getInstance("AndroidKeyStore")
            keyStore.load(null, null) //keystore的来源可空,打开keystore的密钥可空
            val keypairGenerator = KeyPairGenerator.getInstance(KeyProperties.KEY_ALGORITHM_EC, "AndroidKeyStore")
            val purpose = KeyProperties.PURPOSE_SIGN or KeyProperties.PURPOSE_VERIFY
            keypairGenerator.initialize(
                KeyGenParameterSpec.Builder("myKey", purpose)
                    .setDigests(KeyProperties.DIGEST_SHA256) //设置摘要算法
                    .setAlgorithmParameterSpec(ECGenParameterSpec("secp256r1"))//设置基于椭圆曲线计算的非对称密钥的算法
                    .setUserAuthenticationRequired(true) // 设置是否需要生物认证,此处与指纹关联上
                    .build()
            )
            keypairGenerator.genKeyPair()

2.根据密钥库对象初始化签名功能对象,构建指纹验证对象,开启认证操作传入签名功能对象,认证成功时候,方可使用我们传入的密码对象

//通过密钥库构建签名功能对象
 val signature1 = Signature.getInstance("SHA256withECDSA")  
        val privatekey = keyStore.getKey("myKey", null) as PrivateKey
        signature1.initSign(privatekey)
//构建指纹认证对话框对象
    mBiometricPrompt = BiometricPrompt.Builder(activity)  
            .setTitle(activity.resources.getString(R.string.fingerprint_verify))
            .setDescription(activity.resources.getString(R.string.description))
            .setNegativeButton(
                activity.resources.getString(R.string.cancel), activity.mainExecutor
            ) { _, i ->
                doCancel.invoke()
            }.build()
 //开启认证,传入具有签名功能的对象
   mBiometricPrompt.authenticate(  
            BiometricPrompt.CryptoObject(signature1),  
            mCancellationSignal,
            activity.mainExecutor,
            mAuthenticationCallback
        )
// 认证成功回调
 mAuthenticationCallback = object : BiometricPrompt.AuthenticationCallback() {
            override fun onAuthenticationError(errorCode: Int, errString: CharSequence) {
                super.onAuthenticationError(errorCode, errString)
                LogUtils.d("finger onAuthenticationError$errString")
            }

            override fun onAuthenticationSucceeded(result: BiometricPrompt.AuthenticationResult) {
                super.onAuthenticationSucceeded(result)
                LogUtils.d("finger onAuthenticationSucceeded${result}")
                val signature = result.cryptoObject.signature
                signature.update("Abcd12345".toByteArray())
                mSignData = signature.sign()  //签名值
           
                doAuth.invoke()
            }

            override fun onAuthenticationFailed() {
                super.onAuthenticationFailed()
                LogUtils.d("finger onAuthenticationFailed")
            }
        }

3.将签名数据和公钥和原数据发送给服务端

val publickKey = keyStore.getCertificate("myKey").publicKey 

服务端验签大概代码逻辑如下(非Android端代码):
Signature signature = Signature.getInstance("SHA256withECDSA");
signature.initVerify(publickKey);
signature.update("Abcd12345".toByteArray());
boolean = signature1.verify(mSignData);

另一种使用对称密钥的指纹登录方式

有很多文章描述的是在:打开指纹登陆选项时生成对称密钥,用对称密钥加密用来登录的信息(比如用户密码或其他什么口令),然后指纹登陆时,本地指纹验证成功后用对称密钥解密这些登录信息,然后拿账号密码或口令登录服务器,有点类似安全存储token,但是安全性要比非对称要低!

image.png

fido指纹登陆相关流程

根据fido对接官方中午文档描指纹登陆相关的UAF规范(旨在提供免密认证的规范协议。用户可通过指纹,虹膜,声音,脸部等生物识别技术来完成验证。UAF 也支持 PIN 码输入的验证方法),从两个方面简述指纹fido流程:

  • 根据 FIDO UAF 文档指引,FIDO UAF 在移动设备上的实现将分5层: app, client application,UAF Client,UAF ASM,UAF Authenticator。各层的简要功能如下:
    app :提供 UI 用于演示功能,显示 UAF Server 和 UAF Client 的信息交互,提供简单的 Server 设置。
    client application :封装与 UAF Server 交互的 API,以及与 UAF Client 交互的 API。app 调用 client application 的 API 与 UAF Server 及 UAF Client 交互。
    UAF Client :负责处理 Server 的 protocol message,并根据内容向 UAF ASM 发出请求。
    UAF ASM :用于处理 UAF Client 层的信息,并管理 UAF Authenticator。实际情况中 UAF ASM 通常与 UAF Authenticator 看做一个整体,对外打包为1个 apk。
    UAF Authenticator :用于认证用户,一个 UAF Authenticator 可能存在多个内部的 authenticator,它们拥有不同的特性,提供不同的认证方式。
    层级示意图:
    image.png
  • FIDO 指纹认证过程主要四个步骤: 提供了用户注册,登陆认证,交易认证,注销等功能。
    1.注册:会为注册的 username 生成一对非对称密钥对,FIDO UAF 要求密钥对存储在 UAF Authenticator 或 UAF ASM 的安全环境中。
    2.认证:在登陆认证和交易认证的时候使用生成的私钥进行签名,服务器再通过 authenticator 提供的公钥对签名报文进行验签,验签成功则认可这个用户,从而实现免密登陆的特性。
    3.交易:交易认证比登陆认多了一个交易信息,交易信息需要显示给用户(如果支持)并加入签名报文,其他和登陆认证是一样的。所以交易认证的操作类型也是 auth ,(认证登录不涉及这一步)。
    4.注销:已注册的用户可以通过注销删除用户记录。特殊的是注销操作不需要把 UAF Client 的结果发送给 UAF Server。UAF Server 在接收到注销操作后,就直接删除用户了。

参考链接:指纹登录是怎么跑起来的 - 知乎 (zhihu.com)

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,590评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 86,808评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,151评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,779评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,773评论 5 367
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,656评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,022评论 3 398
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,678评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 41,038评论 1 299
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,659评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,756评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,411评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,005评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,973评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,203评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,053评论 2 350
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,495评论 2 343

推荐阅读更多精彩内容