原理介绍:
基于百度云的人脸资料库(用户上传),调用本地摄像头抓拍的图像,与百度云的用户图像做比对,实现人脸认证。
主要步骤如下:
1. 创建百度去账号
2. 在百度云控制台中创建人脸识别的应用,并记录app id ,api key, api sercet.
3. 创建用户组,创建用户并上传图像。
4. 创建spring boot创建 并使用themleaf模板,实现功能。
主要逻辑:
1. 在页面中调用摄像头
2. 点击登录后,会抓拍一张图片发送到服务端
3. 服务端收到图片后,对图片进行处理,并设置参数,发给百度云认证。
4. 收到服务端返回的结果,进行结果判断。
主要代码如下:
只有一个html页面:
<!DOCTYPE html> <html xmlns:th="http://www.w3.org/1999/xhtml"> <head> <meta charset="UTF-8"> <title>人脸认证</title> <script src="https://cdn.bootcss.com/jquery/3.3.1/jquery.min.js"></script> <script src="https://cdn.bootcss.com/twitter-bootstrap/4.2.1/js/bootstrap.min.js"></script> <link href="https://cdn.bootcss.com/twitter-bootstrap/4.2.1/css/bootstrap.min.css" rel="stylesheet"> </head> <body> <video width="400" height="300"></video> <!-- 图像画布 --> <canvas width="200" height="150"></canvas> <button id="" onclick="face_login()" class="btn btn-info"><i class="icon-play"></i> 登录</button> <script> function $(elem){ return document.querySelector(elem); } var canvas = $('canvas'), context = canvas.getContext('2d'), video = $('video'), snap = $('#snap'), upload = $('#upload'), uploaded = $('#uploaded'), mediaStreamTrack; //打开摄像头 if (navigator.mediaDevices && navigator.mediaDevices.getUserMedia) { navigator.mediaDevices.getUserMedia({ video: true, }).then(function(stream) { mediaStreamTrack = typeof stream.stop === 'function' ? stream : stream.getTracks()[1]; // 旧的浏览器可能没有srcObject if ("srcObject" in video) { video.srcObject = stream; } else { // 防止再新的浏览器里使用它,应为它已经不再支持了 video.src = window.URL.createObjectURL(stream); } video.play(); }); }else if (navigator.getMedia) { navigator.getMedia({ video: true }, function(stream) { mediaStreamTrack = stream.getTracks()[0]; video.src = (window.URL || window.webkitURL).createObjectURL(stream); video.play(); }); } //人脸识别参考文档:https://cloud.baidu.com/doc/FACE/ function face_login(){ context.drawImage(video, 0, 0, 200, 150); jQuery.post('faceLogin', { //指定发送图片到的servlet snapData: canvas.toDataURL('image/jpg') }).done(function(rs) { //对结果集进行解析,判断是否存在人脸 console.log(JSON.stringify(rs)); if(rs.error_code == "222202"){ alert("没有人脸信息或人脸数量非1,请重新拍照!"); }else if(rs.error_code == "222207"){ alert("人脸库中没有您的注册信息,请先注册。"); }else if(rs.error_code == "223120"){ alert("请正确登录,不得伪造!"); }else if(rs.error_msg == "SUCCESS"){ alert("登录成功!"); } }); } </script> </body> </html>
服务端代码也只有一个类:代码中百度云账号信息,已处理,不能直接用。
package com.cis.cloud; import com.alibaba.fastjson.JSON; import com.baidu.aip.face.AipFace; import org.json.JSONObject; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.*; import java.util.HashMap; import java.util.Map; @Controller @RequestMapping("/user") public class UserController { private static final String APP_ID_FACE ="155671420"; private static final String API_KEY_FACE ="6jnC1LDLEox5SsGfktlWhYZqx"; private static final String SECRET_KEY_FACE ="Q0C1Y2upbpxxVuPkTNwqkxOWYMDpCwwwI"; @GetMapping("face") public String face(){ return "user/face"; } //005.人脸识别登录 @ResponseBody @RequestMapping(value = "faceLogin",method = RequestMethod.POST) public Map faceLogin(@RequestParam("snapData") String str) throws Exception{ //使用Ajax提交base64字符串,需要经过去头转码 String img_data = str.substring(22, str.length()); AipFace client = new AipFace(APP_ID_FACE, API_KEY_FACE, SECRET_KEY_FACE); HashMap<String,String> options = new HashMap<String,String>(); //请求预置参数 options.put("quality_control", "NORMAL"); options.put("liveness_control", "LOW"); options.put("user_id", "hkk"); //与后台用户ID匹配 options.put("max_user_num", "3"); JSONObject res = client.search(img_data,"BASE64","family", options); //人脸库搜索 family为后台用户组名称 System.out.println(res.toString(2)); Map map = JSON.parseObject(res.toString()); return map; } }
附一段百度云返回的结果:
{ "result": { "face_token": "59b1966b9042068a95d69713e48e50bf", "user_list": [{ "score": 94.014793395996, "group_id": "family", "user_id": "hkk", "user_info": "" }] }, "log_id": 304569203895258121, "error_msg": "SUCCESS", "cached": 0, "error_code": 0, "timestamp": 1550389525 }