Android 15下OTP自动填充结合User Consent API无法正常工作
Android 15 OTP自动填充失效的解决方法
核心原因
Android 15(API 35)对短信读取权限及SMS用户授权API的触发逻辑做了严格限制,旧版实现因权限模型和API调用方式不符合新规范导致失效。以下是针对性解决步骤:
适配权限与API调用逻辑
Android 15移除了READ_SMS权限的直接授予,同时要求必须通过短信验证意图触发用户授权,不能依赖后台监听。需:- 在Manifest中保留
SEND_SMS、RECEIVE_SMS权限声明; - 动态请求
POST_NOTIFICATIONS权限(授权弹窗依赖通知权限); - 使用新版API调用方式:
SmsRetriever.getClient(context).startSmsUserConsent(null)(无需指定电话号码),配合ActivityResultContracts处理回调。
- 在Manifest中保留
严格遵循短信格式规范
验证短信必须严格符合Google一键短信验证的格式要求:开头包含
<#>标记,结尾附加应用包名(用大括号包裹),示例:<#> 你的验证码是123456 XYZ{com.your.app.package}
Android 15对格式校验更严格,不符合规范的短信无法被API识别。替换为推荐的回调实现
放弃旧版广播接收逻辑,改用ActivityResultContracts处理授权结果,示例代码:// 注册短信授权回调 val smsConsentLauncher = registerForActivityResult(ActivityResultContracts.StartActivityForResult()) { result -> if (result.resultCode == Activity.RESULT_OK && result.data != null) { val smsMessage = result.data?.getStringExtra(SmsRetriever.EXTRA_SMS_MESSAGE) smsMessage?.let { // 从短信内容提取OTP val otp = it.replace(Regex("[^0-9]"), "") // 填充到输入框 otpInput.setText(otp) } } } // 启动短信授权请求 fun initiateSmsConsent() { val client = SmsRetriever.getClient(this) client.startSmsUserConsent(null) .addOnSuccessListener { intentSender -> smsConsentLauncher.launch(IntentSenderRequest.Builder(intentSender).build()) } .addOnFailureListener { // 处理请求失败,引导用户手动输入 } }版本兼容性处理
针对Android 15及以上版本做分支处理,保留旧版本的原有逻辑:if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.VANILLA_ICE_CREAM) { initiateSmsConsent() } else { // 旧版SMS Retriever逻辑 startLegacySmsRetriever() }
内容的提问来源于stack exchange,提问作者Aditya Nandardhane
相关产品推荐
相关产品推荐

