阿里云Ai训练营DayTwo

主题

今天的主题是使用springboot starter和阿里云的AI识别sdk构建一个身份证识别应用。

image-20200606123248413

主要依赖项

  • spring-boot-starter-web

  • 页面模板spring-boot-starter-thymeleaf

  • 阿里云识别组件与json组件

    • 1
      2
      3
      4
      5
      <dependency>
          <groupId>com.aliyun</groupId>
          <artifactId>ocr</artifactId>
          <version>1.0.3</version>
      </dependency>
    • 1
      2
      3
      4
      5
      <dependency>
      <groupId>com.alibaba</groupId>
      <artifactId>fastjson</artifactId>
      <version>1.2.67</version>
      </dependency>

主要逻辑

用户在web端上传身份证的正反面的照片,然后传递到springboot,然后由后端将图像传递到阿里云的识别服务,等待识别服务响应识别结果,最后将结果渲染到thymeleaf模板中返还给用户实现完整逻辑。

代码实现分析解读

Controller层上传文件部分

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
@PostMapping("/upload")
public String uploadFile(@RequestParam("face") MultipartFile face, @RequestParam("back") MultipartFile back,
RedirectAttributes attributes) {
// 判断是否上传了空文件
if (face.isEmpty() || back.isEmpty()) {
// 显示报错信息
attributes.addFlashAttribute("message", "Please select a file to upload.");
// 路由跳转
return "redirect:/";
}
// 初始化错误信息
String errorMessage = null;
try {
// 根据相对路径获取上传目录的绝对路径
Path dir = Paths.get(uploadDirectory);
// 检测路径的存在性,避免因为路径不存在而报错
if (!Files.exists(dir)) {
Files.createDirectories(dir);
}
// 个人感觉下面两部分的空检测是不必要的,上面已经检测过一遍了
if (!face.isEmpty()) {
// 将文本流保存到本地,并获取对应的文件名。文件名是随机ID
String filename = saveFile(face);
// 调用OCR服务,获取识别人脸面的识别信息
Map<String, String> res = ocrService.RecognizeIdCard(uploadDirectory + filename, "face");
// 在缓存中加入识别成功的文件
faceImages.add("/images/" + filename);
// 在缓存中加入识别结果
faceResults.add(res);
}
// 背部的识别同上
if (!back.isEmpty()) {
String filename = saveFile(back);
Map<String, String> res = ocrService.RecognizeIdCard(uploadDirectory + filename, "back");
backImages.add("/images/" + filename);
backResults.add(res);
}
} catch (TeaException e) {
// 错误捕捉
e.printStackTrace();
errorMessage = JSON.toJSONString(e.getData());
} catch (Exception e) {
e.printStackTrace();
errorMessage = e.getMessage();
}
// 判断是否有错误报出
if (StringUtils.isNotBlank(errorMessage)) {
attributes.addFlashAttribute("message", errorMessage);
}
// 路由跳转
return "redirect:/";
}

OCR服务

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
/**
* 身份证识别
* @param filePath 文件路径
* @param side 身份证的面
* @return 识别结果
* @throws Exception
*/
public Map<String, String> RecognizeIdCard(String filePath, String side) throws Exception {
// 实例化请求
RecognizeIdentityCardAdvanceRequest request = new RecognizeIdentityCardAdvanceRequest();
// 加载需要识别的图像流
request.imageURLObject = Files.newInputStream(Paths.get(filePath));
// 加载对应的面:人像面或者是国徽面
request.side = side;
// 发送请求并获取响应
RecognizeIdentityCardResponse response = ocrClient.recognizeIdentityCardAdvance(request, runtime);

if ("face".equals(side)) {
return JSON.parseObject(JSON.toJSONString(response.data.frontResult), new TypeReference<Map<String, String>>() {});
} else {
return JSON.parseObject(JSON.toJSONString(response.data.backResult), new TypeReference<Map<String, String>>() {});
}
}

下面是完整代码地址

源码地址: https://github.com/aliyun/alibabacloud-viapi-demo/tree/master

Author: TankNee
Link: https://www.tanknee.cn/2020/06/05/aliyunAiDayTwo/
Copyright Notice: All articles in this blog are licensed under CC BY-NC-SA 4.0 unless stating additionally.