百度AI开放平台文字之身份证识别的实现

10 篇文章 0 订阅
9 篇文章 0 订阅

一、准备工作

一、获取百度的开发权鉴

百度AI开放平台地址:https://console.bce.baidu.com/?_=1532076508921&fromai=1#/aip/overview

和其他平台接口的使用一样,首先要获取相关的key值。登录百度账号之后进入控制台,依次点击:

 创建应用。保存相关的Key。

二、准备一张身份证照片

我的是在网上找的,保存在本地。

三、下载百度提供的工具类

FileUtil,Base64Util,HttpUtil,GsonUtils,这几个工具类都会用到,都需要下载。

  1. https://ai.baidu.com/file/658A35ABAB2D404FBF903F64D47C1F72
  2. https://ai.baidu.com/file/C8D81F3301E24D2892968F09AE1AD6E2
  3. https://ai.baidu.com/file/544D677F5D4E4F17B4122FBD60DB82B3
  4. https://ai.baidu.com/file/470B3ACCA3FE43788B5A963BF0B625F3

下载完成以后放在项目的util包下。

二、正式开发

一、获取AccessToken

 要正式的利用百度AI的身份证识别接口,必须要获取一个access_token,相当于百度的秘钥吧。获取Access Token

我写了一个工具类,专门用来获取AccessToken。使用的时候只需要把之前在控制台获取到的两个Key穿进去即可。其中API Key即clientId,Secret Key即clientSecret。我也不知道百度为什么要换参数的名字。

import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.SocketTimeoutException;
import java.net.URL;
import java.net.URLConnection;
import java.util.HashMap;
import java.util.Map;
import net.sf.json.JSONArray;
import net.sf.json.JSONObject;
import org.springframework.stereotype.Component;
/**
 * @Author: bian
 * @Date: 2018/7/16 15:47
 * @Todo:  百度API要求每个月换一次Token,因此专门写一个工具类用来更新token.
 */

public class AccessTokenUtil {

    public static Map getToken(String clientId,String clientSecret){

        Map token = new HashMap();
        String str = "https://aip.baidubce.com/oauth/2.0/token?grant_type=client_credentials&client_id="+clientId+"&client_secret="+clientSecret;
        try {
            URL url = new URL(str);
            URLConnection connectionData = url.openConnection();
            connectionData.setConnectTimeout(2000);
            BufferedReader br = new BufferedReader(new InputStreamReader(
                    connectionData.getInputStream(), "UTF-8"));
            StringBuilder sb = new StringBuilder();
            String line = null;
            while ((line = br.readLine()) != null){
                sb.append(line);
            }
            String datas = sb.toString();
            JSONObject jsonData = JSONObject.fromObject(datas);
            token.put("access_token", jsonData.getString("access_token").toString());
            token.put("session_key", jsonData.getString("session_key").toString());
            token.put("scope", jsonData.getString("scope").toString());
            token.put("refresh_token", jsonData.getString("refresh_token").toString());
            token.put("session_secret", jsonData.getString("session_secret").toString());
            token.put("expires_in", jsonData.getString("expires_in").toString());
        }catch (SocketTimeoutException e) {
            System.out.println("连接超时");
        } catch (FileNotFoundException e) {
            System.out.println("加载文件出错");
        }catch (IOException e) {
            System.out.println("IOException");
        }
        return token;
    }
}

二、封装实体类

为了操作简单,对身份证信息进行了封装,此处封装为IDCardBlack和IDCardFront两个类。其实后来发现使用Map结构更简单。

import org.springframework.stereotype.Component;

/**
 * @Description:    身份证背面的实体类
 * @author:ykbian
 * @date:2018/7/17 21:15
 */
@Component
public class IDCardBlack {

    private String issuingDate;//签发日期

    private String issuingAuthority;  //签发机关

    private String expiryDate;   //失效日期

    //省略set和get方法…………
}
import org.springframework.stereotype.Component;

/**
 * @Description:  身份证人像面实体类
 * @author:ykbian
 * @date:2018/7/17 21:24
 */
@Component
public class IDCardFront {

        private String IdNumber;

        private String gender;

        private  String nation;

        private  String name;


        private String address;

   //省略get和set方法……………………………………
}

三、测试代码

本来是写了一个服务接口和实现类。在controller里面调用。但是为了测试方便,直接在实现类里面测试。

import com.byk.characterrecognition.character_recognition.Service.IDCardRecognitionService;
import com.byk.characterrecognition.character_recognition.entity.IDCardBlack;
import com.byk.characterrecognition.character_recognition.entity.IDCardFront;
import com.byk.characterrecognition.character_recognition.util.AccessTokenUtil;
import com.byk.characterrecognition.character_recognition.util.Base64Util;
import com.byk.characterrecognition.character_recognition.util.FileUtil;
import com.byk.characterrecognition.character_recognition.util.HttpUtil;
import net.sf.json.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.net.URLEncoder;
import java.util.Map;

/**
 * @Author: bian
 * @Date: 2018/7/16 15:42
 * @Todo:  身份证识别服务接口的实现类
 */
@Service
public class IDCardRecognitionServiceImpl{

//    @Autowired
//    private static IDCardFront idCardFront;
//
//    @Autowired
//    private static IDCardBlack idCardBlack;

    public   static IDCardFront IDCardRecognitionFront(String imageUrl, String clientId, String clientSecret) {
        //为了测试方便使用new的方式,正式环境里面要用@Autowired标签注入
        IDCardFront idCardFront =  new IDCardFront();
        // 身份证识别url========百度提供
        String idcardIdentificate = "https://aip.baidubce.com/rest/2.0/ocr/v1/idcard";
        //图片路径=========这里本来要写图片的路径,我改为从服务接口传参
        try {
            byte[] imgData = FileUtil.readFileByBytes(imageUrl);
            String imgStr = Base64Util.encode(imgData);
            // 识别身份证正面id_card_side=front;识别身份证背面id_card_side=back;
            String params = "id_card_side=front&" + URLEncoder.encode("image", "UTF-8") + "="
                    + URLEncoder.encode(imgStr, "UTF-8");
            /**
             * 线上环境access_token有过期时间, 客户端可自行缓存,过期后重新获取。
             */
            Map map = AccessTokenUtil.getToken(clientId,clientSecret);
            String accessToken = map.get("access_token").toString();
            JSONObject wordsResult = HttpUtil.post(idcardIdentificate, accessToken, params);
            String IdNumber = wordsResult.getJSONObject("公民身份号码").getString("words");
            String gender = wordsResult.getJSONObject("性别").getString("words");
            String nation = wordsResult.getJSONObject("民族").getString("words");
            String name = wordsResult.getJSONObject("姓名").getString("words");
            String address = wordsResult.getJSONObject("住址").getString("words");
            idCardFront.setAddress(address);
            idCardFront.setGender(gender);
            idCardFront.setIdNumber(IdNumber);
            idCardFront.setName(name);
            idCardFront.setNation(nation);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return idCardFront;
    }

    public static IDCardBlack IDCardRecognitionBlack(String imageUrl, String clientId, String clientSecret) {
        // 身份证识别url
        String idcardIdentificate = "https://aip.baidubce.com/rest/2.0/ocr/v1/idcard";
        //为了测试方便使用new的方式,正式环境里面要用@Autowired标签注入
        IDCardBlack idCardBlack = new IDCardBlack();
        try {
            byte[] imgData = FileUtil.readFileByBytes(imageUrl);
            String imgStr = Base64Util.encode(imgData);
            // 识别身份证正面id_card_side=front;识别身份证背面id_card_side=back;
            String params = "id_card_side=back&" + URLEncoder.encode("image", "UTF-8") + "="
                    + URLEncoder.encode(imgStr, "UTF-8");
            /**
             * 线上环境access_token有过期时间, 客户端可自行缓存,过期后重新获取。
             */
            Map map = AccessTokenUtil.getToken(clientId,clientSecret);
            String accessToken = map.get("access_token").toString();
            JSONObject wordsResult = HttpUtil.post(idcardIdentificate, accessToken, params);
            String issuingAuthority = wordsResult.getJSONObject("签发机关").getString("words");
            String issuingDate = wordsResult.getJSONObject("签发日期").getString("words");
            String expiryDate = wordsResult.getJSONObject("失效日期").getString("words");
            idCardBlack.setExpiryDate(expiryDate);
            idCardBlack.setIssuingAuthority(issuingAuthority);
            idCardBlack.setIssuingDate(issuingDate);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return idCardBlack;
    }


    public static void main(String[] arg){
        String image01 = "E:/test/front.png";
        String image02 = "E:/test/black.png";
        String clientId = "你的clientId";
        String clientSecret = "你的clientSecret";
        IDCardFront idCardFront = IDCardRecognitionServiceImpl.IDCardRecognitionFront(image01,clientId,clientSecret);
        IDCardBlack idCardBlack = IDCardRecognitionServiceImpl.IDCardRecognitionBlack(image02,clientId,clientSecret);
        System.out.println(idCardFront);
        System.out.println(idCardBlack);
    }
}

执行main方法,效果如下:

 

三、源码获取

点击此处获取源码https://github.com/bian1234/studyNote/tree/master/APILearn/character_recognition

四、其他

网络图片文字识别和表格文字识别已经完善。其他的文字识别操作都差不多,有时间再补充。

另外,表格文字识别的效果实在不敢恭维。谁用谁知道。

 

  • 0
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值