APP端集成开发
一、 准备工作
在正式集成前,需要做一些准备工作,完成一些账号、应用及配置,具体如下:
1.1 注册成为开发者
- STEP1:点击百度AI 开放平台导航右侧的控制台,页面跳转到百度云登录界面,登录完毕后,将会进入到百度云后台,点击「控制台」进入百度云控制台页面;您也可以在官网直接点击免费试用,登录完毕后将自动进入到百度云控制台。
- STEP2:使用百度账号完成登录,如您还未持有百度账户,可以点击此处注册百度账户。
- STEP3:进入百度云欢迎页面,填写企业和个人基本信息,注册完毕,至此成为开发者。(如您之前已经是百度云用户或百度开发者中心用户,STEP3 可略过。)
- STEP4:进入百度云控制台,找到人工智能相关服务面板。
- STEP5:点击进入「人脸识别」模块。
1.2 创建应用
创建好账号后,在正式调用AI 能力之前,需要您创建一下应用,这个是调用服务的基础能力单元。 选择「人脸识别」服务,首先见到此服务的控制台概览页,点击「创建应用」,即可进入应用创建界面,如下图所示:
如上图所示,点击「创建应用」,即可进入应用创建界面,如下图所示:
注意:您需要创建一个应用,分别做以下作用:
- 应用一:勾选身份证识别能力,绑定iOS OCR、Android OCR包名,用于使用OCR能力。
- 应用二:此应用默认会沟通人脸实名认证能力,用于使用身份验证判断;
1.3 获取秘钥
在您创建完毕应用后,平台将会分配给您此应用的相关凭证,主要为AppID、API Key、Secret Key,以上三个信息是您应用实际开发的主要凭证,每个应用之间各不相同,请您妥善保管。如上图所示。该AK/SK用于调用在线API 如:身份验证。注:开发中请注意区分多份AK/SK(API Key、Secret Key)
1.4 生成token
刚才所创建的应用在调用开放平台API 之前,首先需要获取Access Token(用户身份验证和授权的凭证)您需要使用创建应用所分配到的AppID、API Key 及Secret Key,进行Access Token 的生成,方法详见 Access Token 获取,我们为您准备了几种常见语言的请求示例代码。
注:Access Token 的有效期为30天(以秒为单位),请您集成时注意在程序中定期请求新的token,或每次请求都获取一次token。
1.5 示例代码下载
在人脸实名认证控制台创建完APP实名认证方案后,下载相应的IOS/安卓的示例工程。
APP实名认证方案创建请参考这里。
二、 集成逻辑
2.1 IOS集成
1、打开或者新建一个项目。
2、右键点击项目,会出现一个添加菜单,在菜单中选择『Add Files to“此处是你的项目名字”…… 』,如下图所示:
3、在添加文件弹出框里面选择申请到的license和SDK添加进来。如下图:
注意:license为百度官方提供,刚才在后台下载的文件(文件名称:idl-license.face-ios)
SDK包含下面几个文件:
- IDLFaceSDK.framework
- com.baidu.idl.face.faceSDK.bundle
- com.baidu.idl.face.model.bundle
- com.baidu.idl.face.live.action.image.bundle
- AipOcrSdk.framework
- AipBase.framework
- IdcardQuality.framework
4、确认下 Bundle Identifier
是否是申请license时填报的那一个.
5、注意:license 和 Bundle Identifier 为一一对应关系,填错了会导致SDK不可用.
6、 FACE_LICENSE_ID
这个参数填写百度官方给的LicenseID
在 FaceParameterConfig.h
文件中填写下面几项。
7、选择链接C++标准库。
8、如果没有使用pod管理第三方库的话,请在Build Setting Linking Other Linker Flags 上面加入 –ObjC选项。如果用了pod请忽略,因为pod会自动添加上。
以下为示例工程调用身份验证的代码片段:
2.2 OCR身份证识别集成
把下载下来的License文件(文件名:aip.license),添加到项目里面,无需更改文件名称,然后在AppDelegate
添加以下代码引用进去。
在FaceParameterConfig.h
里面设置下载下来的License文件的名字和后缀。
通过API调用ViewController
进行身份证扫描
详细调用文档,请参考 OCR-iOS-SDK文档
2.3.2 人脸SDK集成
2.3.2.1 、授权初始化
把下载下来的License文件(文件名:idl.license.face-ios),添加到项目里面,无需更改文件名称,然后在AppDelegate
添加以下代码引用进去。
在FaceParameterConfig.h
里面设置下载下来的License文件的名字和后缀。
2.3.2.2 、接口参数及调用说明
2.3.2.2.1 、动作采集
调用IDLFaceLivenessManager类的:
/*带黑边的方法-通过图片质量控制
- (void)livenessStratrgyWithImage:(UIImage *)image previewRect:(CGRect)previewRect detectRect:(CGRect)detectRect completionHandler:(LivenessStrategyCompletion)completion;
/*不带黑边*/
-(void) livenessNormalWithImage:(UIImage *)image previewRect:(CGRect)previewRect detectRect:(CGRect)detectRect completionHandler:(LivenessNormalCompletion)completion;
参数说明
- previewRect 人脸图片大小,类型:Rect
- detectRect 人脸检测区域大小,类型:Rect
- completion 完成后返回照片和状态结果
说明
检测图片中的人脸信息,完成人脸图像采集和人脸活体检测,返回检测状态和结果。
使用方法如下
图片 | key |
---|---|
抠图 | bestImage |
原图 | originalImage |
按要求数量的抠图 | crop%d(%d为第几张,从0开始) |
按要求数量的原图 | original%d(%d为第几张,从0开始) |
2.3.2.2.2 、人脸采集
调用IDLFaceDetectionManager类的:
/*带黑边的方法-通过图片质量控制*/
- (void)detectStratrgyWithQualityControlImage:(UIImage *)image previewRect:(CGRect)previewRect detectRect:(CGRect)detectRect completionHandler:(DetectStrategyCompletion)completion;
/*不带黑边*/
- (void)detectStratrgyWithNormalImage:(UIImage _)image previewRect:(CGRect)previewRect detectRect:(CGRect)detectRect completionHandler:(DetectStrategyCompletion)completion;
参数说明
previewRect
与detctRect
是为了做距离检测而定义的,为了在上层封装判断脸是否在框内/离太远/离太近。
- image:相机获取的图片
- previewRect:间接定义的最大距离的 maxRect 和最小距离的 minRect。
- detectRect:实际采集区域
- completion:回调
说明
检测图片中的人脸信息,完成人脸图像采集和人脸活体检测,返回检测状态和结果。
使用方法如下
| 图片 | key |
| ---- | ------------- |
| 原图 | originalImage |
| 抠图 | bestImage |
2.3.2.2.3 、设置人脸功能控制参数
具体方法详见如下:
// 设置鉴权
- (void)setLicenseID:(NSString *)licenseID andLocalLicenceFile:(NSString *)licensePath andRemoteAuthorize:(BOOL)remoteAuthorize;
// 最小检测人脸阈值,默认40
- (void)setMinFaceSize:(int)width;
// 截取人脸图片大小,默认400
- (void)setCropFaceSizeWidth:(CGFloat)width;
// 人脸检测精度阀值,默认0.5f
- (void)setNotFaceThreshold:(CGFloat)th;
// 人脸遮挡阀值,默认0.5
- (void)setOccluThreshold:(CGFloat)thr;
// 亮度阀值,默认90
- (void)setIllumThreshold:(CGFloat)thr;
// 图像模糊阀值,默认0.5
- (void)setBlurThreshold:(CGFloat)thr;
// 头部姿态角度,默认12,10,10
- (void)setEulurAngleThrPitch:(float)pitch yaw:(float)yaw roll:(float)roll;
//设置无黑边抠图的数量,默认1
- (void)setMaxCropImageNum:(int)imageNum;
//设置最大人脸检测数量,默认1
- (void)setMaxDetectNum:(int)detectNum;
//设置有黑边抠图方式的旋转角度,默认2.0f
- (void)setCropEnlargeRatio:(float)cropEnlargeRatio;
// 检测时间,默认10
- (void)setConditionTimeout:(CGFloat)timeout;
调用方法:
2.3.2.2.4 、检测功能初始化
- (int)initCollect;
调用方法:
2.3.2.2.5 、检测功能释放
- (int)uninitCollect
参数:
- 无
返回:
- 无
2.3.2.2.6 、活体动作设置
- (void)livenesswithList:(NSArray *)array order:(BOOL)ordernumberOfLiveness:(NSInteger)numberOfLiveness
参数:
- array: 活体动作列表
- order: 是否按顺序进行活体动作
- numberOfLiveness: 活体动作数目(array为nil是起作用)
返回:
- 无
说明:
- 活体动作设置
2.2 安卓集成
2.2.1 OCR身份证识别集成
- 把申请的license(aip.license)放到到项目中app module下的assets目录中
- 修改app的build.gradle包名为申请时填入的包名
- 拷贝ocr-ui到您的工程中
接下来调用具体请看示例工程
1、在首页面初始化OCR SDK(在HomeActivity.java中)
2、跳转至身份证扫描页面进行身份证扫描(在HomeActivity.java中)
3、调用身份证识别请求接口api进行身份证识别(在IdCardRecognizeActivity.java中) 其中请求参数如下:
请求参数 | 说明 |
---|---|
image | 身份证扫描的图像 |
id_card_side | 身份证的正反面类型 |
detect_risk | 是否开启旋转识别 |
4、获得身份证号码和姓名后进入人脸活体验证步骤
详细调用文档,请参考 OCR-Android-SDK文档
2.2.2 人脸SDK集成
1、授权参数
(1)把申请的license(idl-license.face-android")放到到项目中app module下的assets目录中
(2)修改 Config.java
类中的参数
在人脸实名认证控制台创建完APP方案后,会自动生成LicenseID和LicenseFileName信息,这里您只需要填写apiKey和secretkey信息即可。
public class Config {
// 为了apiKey,secretKey为您调用百度人脸在线接口的,如注册,比对等。
// 为了的安全,建议放在您的服务端,端把人脸传给服务器,在服务端端
// license为调用sdk的人脸检测功能使用,人脸识别 = 人脸检测(SDK功能)+ 人脸比对(服务端API)
public static String apiKey = "替换为你的apiKey(ak)";
public static String secretKey = "替换为你的secretKey(sk)";
public static String licenseID = "替换为你的licenseID,后台SDK管理界面中,已经生成的licenseID,如:test-face-android";
public static String licenseFileName = "替换为你的license文件";
}
(3)配置签名(申请license时的md5为打包签名的文件,所以必须用申请license的签名文件)
app->build.gradle->android->signingConfigs
signingConfigs {
def password = "替换为签名密码"
def alias = "替换为签名别名"
def filePath = "替换为签名文件路径" //如 ../facesharp.jks//签名文件路径
debug {
keyAlias alias
keyPassword password
storeFile file(filePath)
storePassword(password)
}
release {
keyAlias alias
keyPassword password
storeFile file(filePath)
storePassword(password)
}
}
(4)修改包名 app->build.gradle->android->defaultConfig ->applicationId您申请license时填的包名
2、初始化人脸相关SDK(在HomeActivity.java**中)
private void initLicense() {
setFaceConfig();
// 为了android和ios 区分授权,appId=appname_face_android ,其中appname为申请sdk时的应用名
// 应用上下文
// 申请License取得的APPID
// assets目录下License文件名
FaceSDKManager.getInstance().initialize(mContext,
Config.licenseID, Config.licenseFileName, new IInitCallback() {
@Override
public void initSuccess() {
// 初始化OCR SDK 使用的license是aip.license,名字不能修改
initOCRSDK();
}
@Override
public void initFailure(final int errCode,
final String errMsg) {
runOnUiThread(new Runnable() {
@Override
public void run() {
Log.e(TAG, "初始化失败 = " + errCode + " " + errMsg);
showToast("初始化失败 = " + errCode + ", " + errMsg);
mIsInitSuccess = false;
}
});
}
});
}
3、设置配置参数,如不设置,将使用默认值(在HomeActivity.java中)
private void setFaceConfig() {
FaceConfig config = FaceSDKManager.getInstance().getFaceConfig();
mConsoleConfig = ConsoleConfigManager.getInstance(mContext).getConfig();
// -----TODO:以下为通过console平台获取到的配置信息-----
// 设置模糊度阈值
config.setBlurnessValue(mConsoleConfig.getBlur());
// 设置光照阈值(范围0-255)
config.setBrightnessValue(mConsoleConfig.getIllumination());
// 设置遮挡阈值
config.setOcclusionValue(mConsoleConfig.getOcclusion());
// 设置活体动作,通过设置list,LivenessTypeEunm.Eye, LivenessTypeEunm.Mouth,
// LivenessTypeEunm.HeadUp, LivenessTypeEunm.HeadDown, LivenessTypeEunm.HeadLeft,
// LivenessTypeEunm.HeadRight, LivenessTypeEunm.HeadLeftOrRight
config.setLivenessTypeList(mConsoleConfig.getActions());
// 设置动作活体是否随机
config.setLivenessRandom(mConsoleConfig.isFaceVerifyRandom());
// 风控加密类型,0:普通版;1:加密版
config.setSecType(mConsoleConfig.getSecType());
// -----TODO:以下不需要通过console平台配置,需要手动修改-----
// 设置可检测的最小人脸阈值
config.setMinFaceSize(FaceEnvironment.VALUE_MIN_FACE_SIZE);
// 设置可检测到人脸的阈值
config.setNotFaceValue(FaceEnvironment.VALUE_NOT_FACE_THRESHOLD);
// 设置人脸姿态角阈值
config.setHeadPitchValue(FaceEnvironment.VALUE_HEAD_PITCH);
config.setHeadYawValue(FaceEnvironment.VALUE_HEAD_YAW);
// 设置闭眼阈值
config.setEyeClosedValue(FaceEnvironment.VALUE_CLOSE_EYES);
// 设置图片缓存数量(非动作活体使用)
config.setCacheImageNum(FaceEnvironment.VALUE_CACHE_IMAGE_NUM);
// 设置口罩判断开关以及口罩阈值
config.setOpenMask(FaceEnvironment.VALUE_OPEN_MASK);
config.setMaskValue(FaceEnvironment.VALUE_MASK_THRESHOLD);
// 设置开启提示音
config.setSound(ExampleApplication.isOpenSound);
// 原图缩放系数
config.setScale(FaceEnvironment.VALUE_SCALE);
// 抠图高的设定,为了保证好的抠图效果,我们要求高宽比是4:3,所以会在内部进行计算,只需要传入高即可
config.setCropHeight(FaceEnvironment.VALUE_CROP_HEIGHT);
// 抠图人脸框与背景比例
config.setEnlargeRatio(FaceEnvironment.VALUE_CROP_ENLARGERATIO);
// 选择针对人脸采集输出图片的类型进行加密,0:原图,1:抠图
config.setOutputImageType(FaceEnvironment.VALUE_OUTPUT_IMAGE_TYPE);
FaceSDKManager.getInstance().setFaceConfig(config);
}
4、开始进行人脸采集 非动作活体版:(在FaceDetectActivity.java中) (1)在摄像头的回调方法onPreviewFrame(byte[] data, Camera camera)中调用FaceSDKManager.getInstance().getDetectStrategyModule()获得IDetectStrategy对象。(该方法每次调用都会返回一个新对象,建议只调用一次)。
(2)调用IDetectStrategy.setPreviewDegree(int degree);设置预览图片的旋转角度。 调用IDetectStrategy.setDetectStrategySoundEnable(boolean flag);设置是否开启语音。 调用IDetectStrategy.setDetectStrategyConfig(Rect previewRect, Rect detectRect, IDetectStrategyCallback callback);设置预览框的大小,人脸检测框的坐标和回调。
(3)多次调用detectStrategy(byte[] imageData);进行人脸图片采集。
(4)实现IDetectStrategyCallback.onDetectCompletion(FaceStatusNewEnum status, String message, HashMap<String, ImageInfo> base64ImageCropMap, HashMap<String, ImageInfo> base64ImageSrcMap);回调方法并处理结果。其中base64ImageCropMap为采集到的指定数量的抠图,base64ImageSrcMap为采集到的指定数量的原图。
(5)获取采集到的最优抠图和原图,即在上述第(4)步的IDetectStrategyCallback.onDetectCompletion();回调方法中调用getBestImage(HashMap<String, ImageInfo> imageCropMap, HashMap<String, ImageInfo> imageSrcMap);,其实现如下:
动作活体版:(在FaceLivenessActivity.java中) (1)在摄像头的回调方法onPreviewFrame(byte[] data, Camera camera)中调用FaceSDKManager.getInstance().getLivenessStrategyModule(ILivenessViewCallback)获得ILivenessStrategy对象。(该方法每次调用都会返回一个新对象,建议只调用一次)。
(2)调用ILivenessStrategy.setPreviewDegree(int degree);设置预览图片的旋转角度。 调用ILivenessStrategy.setLivenessStrategySoundEnable(boolean flag);设置是否开启语音。 调用ILivenessStrategy.setLivenessStrategyConfig(List<LivenessTypeEnum> livenessList, Rect previewRect, Rect detectRect, ILivenessStrategyCallback callback);设置动作活体类型、预览框的大小,人脸检测框的坐标和回调。
(3)多次调用livenessStrategy(byte[] imageData);进行人脸图片采集。
(4)实现ILivenessStrategyCallback.onDetectCompletion(FaceStatusNewEnum status, String message, HashMap<String, ImageInfo> base64ImageCropMap, HashMap<String, ImageInfo> base64ImageSrcMap, int currentLivenessCount);回调方法并处理结果。其中base64ImageCropMap为采集到的指定数量的抠图,base64ImageSrcMap为采集到的指定数量的原图。
(5)获取采集到的最优抠图和原图,即在上述第(4)步的ILivenessStrategyCallback.onDetectCompletion();回调方法中调用getBestImage(HashMap<String, ImageInfo> imageCropMap, HashMap<String, ImageInfo> imageSrcMap);,其实现如下:
5、跳转至身份核验接口调用页面,需要传入:图片的base64、图片加密类型(加密、不加密)、姓名、身份证号 (在FaceDetectExpActivity.java和FaceLivenessExpActivity.java中)
6、获取accessToken,用于调用接口(在CollectVerifyActivity.java中)
注意:为了防止ak、sk泄露,建议把ak、sk放在服务端,移动端通过服务端去拉取token(目前是在工程中的Config.java中)
7、根据离线采集得到的人脸图片(抠图或原图),进行人脸实名认证(包含加密或非加密两种)(在CollectVerifyActivity.java中)
提示:为了安全及维护成本考虑,我们建议您将SDK获取的人脸图像,推送到服务器端,由服务器端进行API调用,并将结果返回给客户端APP
其中请求参数如下:
非加密版
| 请求参数 | 含义 | 说明 |
| --------------- | ----------------|--------|
| image_type | 图片类型 |BASE64:图片的base64值,base64编码后的图片数据,编码后的图片大小不超过2M;图片尺寸不超过1920*1080|
| image | 图片信息 |--------|
| name | 姓名 |需要是UTF-8编码的中文|
| id_card_number | 身份证号 | |
| quality_control | 图片质量控制 | NONE: 不进行控制
LOW:较低的质量要求
NORMAL: 一般的质量要求
HIGH: 较高的质量要求
默认 NONE|
| liveness_control| 活体检测控制 | NONE: 不进行控制
LOW:较低的活体要求(高通过率 低攻击拒绝率)
NORMAL: 一般的活体要求(平衡的攻击拒绝率, 通过率)
HIGH: 较高的活体要求(高攻击拒绝率 低通过率)
默认 NONE |
| spoofing_control| 合成图控制 | 默认NONE |
加密版
| 请求参数 | 含义 | 说明 |
| --------------- | ----------------|--------|
| image_type | 图片类型 |BASE64:图片的base64值,base64编码后的图片数据,编码后的图片大小不超过2M;图片尺寸不超过1920*1080|
| image | 图片信息 |--------|
| name | 姓名 |需要是UTF-8编码的中文|
| id_card_number | 身份证号 | |
| quality_control | 图片质量控制 | NONE: 不进行控制
LOW:较低的质量要求
NORMAL: 一般的质量要求
HIGH: 较高的质量要求
默认 NONE|
| liveness_control| 活体检测控制 | NONE: 不进行控制
LOW:较低的活体要求(高通过率 低攻击拒绝率)
NORMAL: 一般的活体要求(平衡的攻击拒绝率, 通过率)
HIGH: 较高的活体要求(高攻击拒绝率 低通过率)
默认 NONE |
| spoofing_control| 合成图控制 | 默认NONE |
| image_sec | 是否图像加密 |True:打开图像加密。(接受SDK端传入的加密图片信息,服务端进行解密)
False:关闭图像加密。
默认为False |
| risk_identify | 是否进行风险识别 | |
| IP | 需要风控判别的ip地址| 当risk_identify为true时传入 |
| iphone | 需要风控判别的手机号| 当risk_identify为true时传入 |