下载实人认证Android SDK的ZIP压缩包后,您可参照本文内容将SDK集成到您的Android应用中。

背景信息

为了您的业务安全,实人认证Android SDK(以下简称 SDK)与应用的包名(AndroidManifest.xml中的package)和签名(build.gradle中的signingConfig)绑定,修改应用的包名或签名后都需要在实人认证管理控制台上重新下载 SDK。另外,debug包和release包在使用不同签名时不能混用同一张签名图片文件(yw_1222_*.jpg)。

注意 如果debug模式下未指定使用签名,IDE(以Android Studio为例)会默认使用debug.keystore进行签名(Linux/MacOS下一般是在~/.android/debug.keystore),该签名和之后您的release包的正式签名必然是不同的。
如果您不了解如何生成自己的签名文件并指定使用签名,请查阅官方文档Sign your app,其中,
说明 若您需要用到V2方式的签名,生成签名文件时请同时勾选V1、V2签名。如果只选择V2签名,apk将无法在Android 7.0以下安装。

如果您集成的SDK(rpsdk)还是旧版本(<= 3.0.x.x),建议升级到最新版本的SDK(>= 3.1.x.x)。如果您坚持使用旧版本,请参见老版本SDK接入文档说明。

关于开发环境IDE,Android Studio是Google官方推出并集成了诸多便捷的开发插件的Android开发平台,下面的介绍将基于Android Studio(以下简称AS)进行。

在工程中导入SDK

在控制台成功上传APK包后,您可以下载并获取到一个名为阿里云认证SDK-ANDROID.zip的ZIP压缩包。将其解压后,可以看到在一级目录下有yw_1222_0670.jpgclient.zip两个文件。

关于签名图片

yw_1222_0670.jpg是签名图片文件,该文件和您上传的APK的包名以及签名强绑定,用于SDK的使用授权。

将签名图片文件导入到工程应用模块的res/drawable目录下,如果没有这个目录,请先在工程中创建,否则将无法正常工作。

另外,如果工程在打包时启用了shrinkResources对资源进行压缩,还需要在keep.xmlres/raw/keep.xml)文件中添加以下内容:
<resources xmlns:tools="http://schemas.android.com/tools" tools:keep="@drawable/yw_1222_*" />

如果您想了解关于资源压缩的更多内容,请查阅官方文档Shrink your app,其中,压缩资源章节介绍了如何使用shrinkResources压缩资源,以及配置keep.xml,自定义要保留的资源。

关于SDK包

解压client.zip包,您将看到一系列SDK相关的依赖包,下表介绍了这些SDK包/文件的说明(其中 xxx表示版本号)。

名称 描述
releaseNotes.txt 升级日志和版本说明。
rpsdk-xxx.aar 认证SDK依赖包。
fastjson-xxx.jar fastjson扩展依赖包。若自身工程已集成该包,可忽略,但务必保证已集成的包的版本号不小于我们提供的包的版本号。
windvane-min-xxx.jar WebView依赖包。
oss-android-sdk-xxx.aar OSS 上传依赖包。
说明 若自身工程已集成该包,可忽略,但为兼容Android 9.0,务必保证版本号在2.9.0以上。公共Maven库中已有该包,在 dependencies下也可通过com.aliyun.dpa:oss-android-sdk:+定位。
okhttp-xxx.jar 网络请求依赖包。
说明 若自身工程已集成该包,可忽略,但务必保证使用3.0系列版本,且版本号不小于我们提供的包的版本号。公共Maven库中已有该包,在dependencies下也可通过com.squareup.okhttp3:okhttp:+定位。
okio-xxx.jar okhttp扩展依赖包。
说明 若自身工程已集成该包,可忽略,但务必保证已集成的包的版本号不小于我们提供的包的版本号。公共Maven库中已有该包,在dependencies下也可通过com.squareup.okio:okio:+定位。
logging-interceptor-xxx.jar okhttp日志拦截器依赖包。
说明 若自身工程已集成该包,可忽略,但建议版本号和okhttp包的版本号保持一致。公共Maven库中已有该包,在dependencies下也可通过com.squareup.okhttp3:logging-interceptor:+定位。
SecurityGuardSDK-external-release-xxx.aar 安全加固依赖包。若自身工程已集成阿里体系的其他产品(如阿里百川等)并含有该包,需判断哪个版本号较新,使用较新的版本。
SecurityBodySDK-external-release-xxx.aar 安全加固扩展依赖包。同上
jniLibs.zip 包含需要额外加入的so公共依赖库文件ibc++_shared.so

Google官方建议存在多个so时,在编译生成c++ so文件时选择stl类型为c++_shared,保证扩展性,具体请参见官方文档NDK编译—C++ 库支持。RPSDK包从3.2.0.0版本开始采用此种编译方式。

另外,您也可以在Android NDK(建议使用 ndk-18)包/目录(ndk-bundle)下的sources/cxx-stl/llvm-libc++/libs/路径下找到不同ABI类型的libc++_shared.so文件。

jniLibs-armeabi.zip 为节省包体积,RPSDK包从3.2.0.2版本开始已不再默认打入兼容armeabi的so文件。

原因在于,ARM v5(对应ABI类型armeabi)在现在已经是相当老旧的Android系统的CPU架构版本,现在主流的是ARM v7(对应 ABI 类型 armeabi-v7a),并从Android 2.2开始支持。如果您不需要考虑比之更低的版本,可忽略该ZIP文件。如果您应用的其他依赖包尚未提供兼容armeabi-v7a的支持包,必须要求armeabi,可在工程src/main/jniLibs(默认)目录下加入该ZIP包下的相应文件。

解压出SDK依赖包后,建议在工程根目录下创建目录libs(已有则忽略),根据上述介绍酌情将SDK包拷入工程的libs目录下。例如:
同时,如果RPSDK包版本是 3.2.0.0 及以上,解压出jniLibs.zip包内容,将内容拷至src/main/jniLibs(默认JNI依赖so文件目录)下,例如:
说明 src/main/jniLibs并不是固定的,这和您定义的默认源集配置(sourceSets)有关,具体可参考Google官方文档 更改默认源集配置。默认情况下,jni的so库文件在src/main/jniLibs下。

如果您之前已集成过旧版本的SDK,请覆盖相应SDK依赖包文件(删除旧版本的包)。如果您之前rpsdk版本是3.0.x.x,新版本在3.1.x.x以上,请同时更新签名图片文件yw_1222_0670.jpg

在工程中集成SDK

添加SDK包依赖

以直接在应用下进行集成为例,在应用module下的build.gradle文件内,声明flatDir路径(若已有则忽略):

apply plugin: 'com.android.application'

repositories {
  flatDir {
    dirs '../libs'
  }
}

以gradle 版本 >= 3.0.0(注意非gradle tools版本,gradle版本可在gradle/wrapper/gradle-wrapper.properties下查看)为例,在应用module下的build.gradle文件内声明 SDK 包依赖:

dependencies {
    implementation fileTree(dir: '../libs', include: ['*.jar'])
    implementation (name:'rpsdk-3.2.0.0', ext:'aar')
    implementation (name:'oss-android-sdk-2.9.2', ext:'aar')
      implementation (name:'SecurityGuardSDK-external-release-5.4.9901', ext:'aar')
    implementation (name:'SecurityBodySDK-external-release-5.4.79', ext:'aar')
}
说明 关于aar包的引入方式建议尽量采用上面例子的写法,不要和jar包混在一起引入,防止某些gradle版本无法正确解出aar包内容。

关于ABI类型

SDK目前支持armeabi、armeabi-v7a、arm64-v8a三种ABI类型,其中RPSDK从3.2.0.0版本开始不再默认包含armeabi类型的so库文件,建议接入方在应用module下的build.gradle文件内,添加abiFilters配置,例如:
android {
      defaultConfig {
            ...
            ndk {
                abiFilters "armeabi-v7a", "arm64-v8a"
            }
    }
}

关于混淆配置

如果您的应用使用了ProGuard进行代码混淆,为了保证实人认证服务需要的一些类不被混淆,需要在ProGuard配置文件中添加相关指令。

以AS为例,在应用module下的build.gradle文件内,如果配置了proguardFiles,并且启用了minifyEnabled,则表明已使用指定的配置文件(一般为proguard-rules.pro)进行了代码混淆,例如:
android {
    ...
    buildTypes {
        release {
            minifyEnabled true
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}
那么在相应的ProGuard配置文件(一般为proguard-rules.pro)中添加以下配置信息,保证实人认证服务需要的类不被混淆:
-keep class com.taobao.securityjni.**{*;}
-keep class com.taobao.wireless.security.**{*;}
-keep class com.ut.secbody.**{*;}
-keep class com.taobao.dp.**{*;}
-keep class com.alibaba.wireless.security.**{*;}
-keep class com.alibaba.security.rp.**{*;}
-keep class com.alibaba.sdk.android.**{*;}
-keep class com.alibaba.security.biometrics.**{*;}
-keep class android.taobao.windvane.**{*;}

关于权限配置

使用SDK需要在AndroidManifest.xml中添加如下权限声明(已有则忽略):
<uses-permission android:name="android.permission.CAMERA"/>
如果您使用的rpsdk版本在3.0.0.4(不含)以下,还需要添加以下权限声明(已有则忽略):
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>

使用SDK

具体在使用SDK时,只需关注rpsdk内的RPSDK相关接口。

初始化

一般在应用启动时,调用RPSDK的初始化接口,例如:
import android.app.Application;
import android.content.Context;

import com.alibaba.security.rp.RPSDK;

public class DemoApplication extends Application {
    private Context appContext;

    @Override
    public void onCreate() {
        super.onCreate();
        appContext = this.getApplicationContext();
        // 初始化实人认证 SDK
        RPSDK.initialize(appContext);
    }
}

上述写法并不是必须的,您可以在任意调用RPSDK其他接口前的位置调用初始化,但为了方便维护和管理,建议您这么做。

进入实人认证

调用开始实人认证的接口,需要您提前获取verifyTokenverifyToken由您的服务端调用发起认证请求接口DescribeVerifyToken获取),将其传入接口:
RPSDK.start(verifyToken, DemoActivity.this, new RPSDK.RPCompletedListener() {
      @Override
      public void onAuditResult(RPSDK.AUDIT audit, String code) {
          Toast.makeText(ParametersActivity.this, audit + "", Toast.LENGTH_SHORT).show();

        if (audit == RPSDK.AUDIT.AUDIT_PASS) {
              // 认证通过。建议接入方调用实人认证服务端接口DescribeVerifyResult来获取最终的认证状态,并以此为准进行业务上的判断和处理
                // do something
        } else if(audit == RPSDK.AUDIT.AUDIT_FAIL) {
            // 认证不通过。建议接入方调用实人认证服务端接口DescribeVerifyResult来获取最终的认证状态,并以此为准进行业务上的判断和处理
                // do something
          } else if(audit == RPSDK.AUDIT.AUDIT_NOT) {
            // 未认证,具体原因可通过code来区分(code取值参见下方表格),通常是用户主动退出或者姓名身份证号实名校验不匹配等原因,导致未完成认证流程
              // do something
          }
    }
});

RPSDK.start接口支持除RPH5BioOnly、RPMin外的所有认证方案,该接口会以加载H5的方式显示页面,如果您选择的认证方案只包含活体检测步骤(参见认证方案),并对调起实人认证的速度有较高的要求,可以考虑使用RPSDK.startVerifyByNative接口。

RPSDK.startVerifyByNative(verifyToken, DemoActivity.this, new RPSDK.RPCompletedListener() {
      @Override
      public void onAuditResult(RPSDK.AUDIT audit, String code) {
          Toast.makeText(ParametersActivity.this, audit + "", Toast.LENGTH_SHORT).show();

        if (audit == RPSDK.AUDIT.AUDIT_PASS) {
              // 认证通过。建议接入方调用实人认证服务端接口DescribeVerifyResult来获取最终的认证状态,并以此为准进行业务上的判断和处理
                // do something
        } else if(audit == RPSDK.AUDIT.AUDIT_FAIL) {
            // 认证不通过。建议接入方调用实人认证服务端接口DescribeVerifyResult来获取最终的认证状态,并以此为准进行业务上的判断和处理
                // do something
          } else if(audit == RPSDK.AUDIT.AUDIT_NOT) {
            // 未认证,具体原因可通过code来区分(code取值参见下方表格),通常是用户主动退出或者姓名身份证号实名校验不匹配等原因,导致未完成认证流程
              // do something
          }
    }
});
注意 RPSDK.startVerifyByNative接口支持除RPH5BioOnly之外的仅活体检测认证方案(如RPBioOnly、FDBioOnly、FVBioOnly),包含身份证件拍摄等其他步骤的认证方案需要使用RPSDK.start接口。另外,RPSDK.startVerifyByNative接口不支持在控制台配置引导页、授权页、结果页等,需接入方自行处理。

在开始实人认证的接口中,verifyToken参数由接入方的服务端调用实人认证服务的DescribeVerifyToken接口获得。

RPSDK.RPCompletedListener#onAuditResult中可获取到认证状态和认证失败时错误码,具体见下表说明。
audit code code释义
RPSDK.AUDIT.AUDIT_PASS 1 认证通过。
RPSDK.AUDIT.AUDIT_FAIL 2~12 表示认证不通过,具体的不通过原因可以查看服务端的查询认证结果(DescribeVerifyResult)接口文档中认证状态的表格说明。
RPSDK.AUDIT.AUDIT_NOT -1 未完成认证,原因:用户在认证过程中,主动退出。
RPSDK.AUDIT.AUDIT_NOT 3001 未完成认证,原因:认证token无效或已过期。
RPSDK.AUDIT.AUDIT_NOT 3101 未完成认证,原因:用户姓名身份证实名校验不匹配。
RPSDK.AUDIT.AUDIT_NOT 3102 未完成认证,原因:实名校验身份证号不存在。
RPSDK.AUDIT.AUDIT_NOT 3103 未完成认证,原因:实名校验身份证号不合法。
RPSDK.AUDIT.AUDIT_NOT 3104 未完成认证,原因:认证已通过,重复提交。
RPSDK.AUDIT.AUDIT_NOT 3204 未完成认证,原因:非本人操作。
RPSDK.AUDIT.AUDIT_NOT 3206 未完成认证,原因:非本人操作。
RPSDK.AUDIT.AUDIT_NOT 3208 未完成认证,原因是:公安网无底照。

常见问题

请参见Android集成常见问题