新增了身份证识别
This commit is contained in:
parent
7c09fd4172
commit
6cc5dc58de
@ -33,6 +33,11 @@
|
|||||||
<artifactId>weixin-java-miniapp</artifactId>
|
<artifactId>weixin-java-miniapp</artifactId>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.baidu.aip</groupId>
|
||||||
|
<artifactId>java-sdk</artifactId>
|
||||||
|
<version>4.16.22</version>
|
||||||
|
</dependency>
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
|
||||||
<build>
|
<build>
|
||||||
|
|||||||
@ -60,7 +60,7 @@ public class AdminSwaggerTagConst extends SwaggerTagConst {
|
|||||||
public static final String Expert = "前端-登录、注册、首页";
|
public static final String Expert = "前端-登录、注册、首页";
|
||||||
public static final String ExpertSign = "前端-医生签名";
|
public static final String ExpertSign = "前端-医生签名";
|
||||||
|
|
||||||
public static final String OSS = "前端-oss";
|
public static final String OSS = "前端-文件";
|
||||||
public static final String WX_MINI = "前端-微信小程序";
|
public static final String WX_MINI = "前端-微信小程序";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -0,0 +1,33 @@
|
|||||||
|
package net.lab1024.sa.admin.extend.baidubce;
|
||||||
|
|
||||||
|
import com.baidu.aip.ocr.AipOcr;
|
||||||
|
import lombok.Getter;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
|
import javax.annotation.PostConstruct;
|
||||||
|
|
||||||
|
@Slf4j
|
||||||
|
@Getter
|
||||||
|
@Component("baiducebase")
|
||||||
|
public class Base {
|
||||||
|
@Value("${baiduce.app-id}")
|
||||||
|
private String appId;
|
||||||
|
|
||||||
|
@Value("${baiduce.app-key}")
|
||||||
|
private String appkey;
|
||||||
|
|
||||||
|
@Value("${baiduce.app-secret}")
|
||||||
|
private String appSecret;
|
||||||
|
|
||||||
|
// AipOcr 实例
|
||||||
|
protected AipOcr ocrClient;
|
||||||
|
|
||||||
|
@PostConstruct
|
||||||
|
public void init() {
|
||||||
|
ocrClient = new AipOcr(appId, appkey, appSecret);
|
||||||
|
ocrClient.setConnectionTimeoutInMillis(2000);
|
||||||
|
ocrClient.setSocketTimeoutInMillis(60000);
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,30 @@
|
|||||||
|
package net.lab1024.sa.admin.extend.baidubce;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
|
||||||
|
import com.baidu.aip.ocr.AipOcr;
|
||||||
|
import net.lab1024.sa.common.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.common.common.exception.BusinessException;
|
||||||
|
import org.json.JSONObject;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
|
// 通用文字识别
|
||||||
|
@Component
|
||||||
|
public class Ocr extends Base {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 身份证识别
|
||||||
|
*/
|
||||||
|
public JSONObject idCard(byte[] imageBytes,String idCardSide) {
|
||||||
|
try {
|
||||||
|
HashMap<String, String> options = new HashMap<>();
|
||||||
|
options.put("detect_direction", "true");
|
||||||
|
options.put("detect_risk", "true");
|
||||||
|
|
||||||
|
return ocrClient.idcard(imageBytes, idCardSide, options);
|
||||||
|
|
||||||
|
} catch (Exception e) {
|
||||||
|
throw new BusinessException("OCR识别失败: " + e.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -18,7 +18,7 @@ import java.util.Map;
|
|||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
@Slf4j
|
@Slf4j
|
||||||
@Component
|
@Component("fangxinqianbase")
|
||||||
@Getter
|
@Getter
|
||||||
public class Base {
|
public class Base {
|
||||||
private static final ObjectMapper objectMapper = new ObjectMapper();
|
private static final ObjectMapper objectMapper = new ObjectMapper();
|
||||||
|
|||||||
@ -634,6 +634,4 @@ public class ExpertController {
|
|||||||
return ResponseDTO.error(ExpertBankVerifyFail);
|
return ResponseDTO.error(ExpertBankVerifyFail);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -77,6 +77,4 @@ public class ExpertService {
|
|||||||
addForm.setToken(token);
|
addForm.setToken(token);
|
||||||
return addForm;
|
return addForm;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -0,0 +1,51 @@
|
|||||||
|
package net.lab1024.sa.admin.module.app.file.controller;
|
||||||
|
|
||||||
|
import io.swagger.annotations.Api;
|
||||||
|
import io.swagger.annotations.ApiOperation;
|
||||||
|
import net.lab1024.sa.admin.constant.AdminSwaggerTagConst;
|
||||||
|
import net.lab1024.sa.admin.extend.baidubce.Ocr;
|
||||||
|
import net.lab1024.sa.admin.module.app.file.domain.vo.GetIdCardOcrVo;
|
||||||
|
import net.lab1024.sa.admin.module.app.file.service.OcrService;
|
||||||
|
import net.lab1024.sa.admin.module.business.bankcard.domain.form.CaseplatformBankAddForm;
|
||||||
|
import net.lab1024.sa.common.common.domain.ResponseDTO;
|
||||||
|
import org.springframework.web.bind.annotation.*;
|
||||||
|
import org.springframework.web.multipart.MultipartFile;
|
||||||
|
|
||||||
|
import javax.annotation.Resource;
|
||||||
|
import javax.validation.Valid;
|
||||||
|
|
||||||
|
@RestController
|
||||||
|
@Api(tags = {AdminSwaggerTagConst.App.OSS})
|
||||||
|
public class ImageController {
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private OcrService ocrService;
|
||||||
|
|
||||||
|
@ApiOperation(value = "身份证识别-ocr")
|
||||||
|
@PostMapping("/ocr/idCard")
|
||||||
|
public ResponseDTO<GetIdCardOcrVo> getIdCardOcr(
|
||||||
|
@RequestParam("frontFile") MultipartFile frontFile,
|
||||||
|
@RequestParam("backFile") MultipartFile backFile
|
||||||
|
){
|
||||||
|
if (frontFile == null || frontFile.isEmpty()) {
|
||||||
|
return ResponseDTO.userErrorParam("参数错误");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (backFile == null || backFile.isEmpty()) {
|
||||||
|
return ResponseDTO.userErrorParam("参数错误");
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
byte[] frontBytes = frontFile.getBytes();
|
||||||
|
byte[] backBytes = backFile.getBytes();
|
||||||
|
|
||||||
|
// 调用 Service
|
||||||
|
GetIdCardOcrVo result = ocrService.getIdCardOcr(frontBytes, backBytes);
|
||||||
|
return ResponseDTO.app_ok(result);
|
||||||
|
|
||||||
|
} catch (Exception e) {
|
||||||
|
return ResponseDTO.userErrorParam("识别失败:" + e.getMessage());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,16 @@
|
|||||||
|
package net.lab1024.sa.admin.module.app.file.domain.vo;
|
||||||
|
|
||||||
|
import io.swagger.annotations.ApiModelProperty;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class GetIdCardOcrVo {
|
||||||
|
@ApiModelProperty(value = "身份证姓名")
|
||||||
|
private String idCardName;
|
||||||
|
|
||||||
|
@ApiModelProperty(value = "身份证号")
|
||||||
|
private String idCardNo;
|
||||||
|
}
|
||||||
|
|
||||||
@ -0,0 +1,116 @@
|
|||||||
|
package net.lab1024.sa.admin.module.app.file.service;
|
||||||
|
|
||||||
|
import net.lab1024.sa.admin.extend.baidubce.Ocr;
|
||||||
|
import net.lab1024.sa.admin.extend.fangxinqian.company.Company;
|
||||||
|
import net.lab1024.sa.admin.module.app.expert.admin.ExpertSignVO;
|
||||||
|
import net.lab1024.sa.admin.module.app.expert.dao.ExpertSignDao;
|
||||||
|
import net.lab1024.sa.admin.module.app.file.domain.vo.GetIdCardOcrVo;
|
||||||
|
import net.lab1024.sa.common.common.exception.BusinessException;
|
||||||
|
import net.lab1024.sa.common.common.util.SmartRequestUtil;
|
||||||
|
import org.json.JSONObject;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import javax.annotation.Resource;
|
||||||
|
|
||||||
|
@Service
|
||||||
|
public class OcrService {
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private Ocr ocr;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 身份证识别
|
||||||
|
*/
|
||||||
|
public GetIdCardOcrVo getIdCardOcr(byte[] frontBytes,byte[] backBytes) {
|
||||||
|
try {
|
||||||
|
// 反面
|
||||||
|
JSONObject result = ocr.idCard(backBytes,"back");
|
||||||
|
|
||||||
|
String imageStatus = result.getString("image_status");
|
||||||
|
switch (imageStatus) {
|
||||||
|
case "normal":
|
||||||
|
// 识别正常,继续处理
|
||||||
|
break;
|
||||||
|
case "reversed_side":
|
||||||
|
throw new BusinessException("身份证未摆正,请重新上传");
|
||||||
|
case "non_idcard":
|
||||||
|
throw new BusinessException("上传的图片中不包含身份证,请上传正确图片");
|
||||||
|
case "blurred":
|
||||||
|
throw new BusinessException("身份证模糊,请重新上传清晰图片");
|
||||||
|
case "over_exposure":
|
||||||
|
throw new BusinessException("身份证关键字段反光或过曝,请重新拍摄");
|
||||||
|
case "unknown":
|
||||||
|
default:
|
||||||
|
throw new BusinessException("无法识别身份证,请重新上传");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (result.has("risk_type")) {
|
||||||
|
String riskType = result.getString("risk_type");
|
||||||
|
if (!"normal".equals(riskType)) {
|
||||||
|
switch (riskType) {
|
||||||
|
case "copy":
|
||||||
|
throw new BusinessException("检测到复印件身份证,请上传原件");
|
||||||
|
case "temporary":
|
||||||
|
throw new BusinessException("检测到临时身份证,请上传正式身份证");
|
||||||
|
case "screen":
|
||||||
|
throw new BusinessException("检测到翻拍身份证,请上传原件照片");
|
||||||
|
case "unknow":
|
||||||
|
default:
|
||||||
|
throw new BusinessException("身份证真实性存疑,请重新上传");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 正面
|
||||||
|
result = ocr.idCard(frontBytes,"front");
|
||||||
|
|
||||||
|
imageStatus = result.getString("image_status");
|
||||||
|
switch (imageStatus) {
|
||||||
|
case "normal":
|
||||||
|
// 识别正常,继续处理
|
||||||
|
break;
|
||||||
|
case "reversed_side":
|
||||||
|
throw new BusinessException("身份证未摆正,请重新上传");
|
||||||
|
case "non_idcard":
|
||||||
|
throw new BusinessException("上传的图片中不包含身份证,请上传正确图片");
|
||||||
|
case "blurred":
|
||||||
|
throw new BusinessException("身份证模糊,请重新上传清晰图片");
|
||||||
|
case "over_exposure":
|
||||||
|
throw new BusinessException("身份证关键字段反光或过曝,请重新拍摄");
|
||||||
|
case "unknown":
|
||||||
|
default:
|
||||||
|
throw new BusinessException("无法识别身份证,请重新上传");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (result.has("risk_type")) {
|
||||||
|
String riskType = result.getString("risk_type");
|
||||||
|
if (!"normal".equals(riskType)) {
|
||||||
|
switch (riskType) {
|
||||||
|
case "copy":
|
||||||
|
throw new BusinessException("检测到复印件身份证,请上传原件");
|
||||||
|
case "temporary":
|
||||||
|
throw new BusinessException("检测到临时身份证,请上传正式身份证");
|
||||||
|
case "screen":
|
||||||
|
throw new BusinessException("检测到翻拍身份证,请上传原件照片");
|
||||||
|
case "unknow":
|
||||||
|
default:
|
||||||
|
throw new BusinessException("身份证真实性存疑,请重新上传");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 解析识别结果
|
||||||
|
String name = result.getJSONObject("words_result").getJSONObject("姓名").getString("words");
|
||||||
|
String idNo = result.getJSONObject("words_result").getJSONObject("公民身份号码").getString("words");
|
||||||
|
|
||||||
|
// 构建返回对象
|
||||||
|
GetIdCardOcrVo vo = new GetIdCardOcrVo();
|
||||||
|
vo.setIdCardName(name);
|
||||||
|
vo.setIdCardNo(idNo);
|
||||||
|
return vo;
|
||||||
|
} catch (Exception e) {
|
||||||
|
throw new RuntimeException(e.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -54,14 +54,19 @@ fxq:
|
|||||||
client-secret: 97acf8ebb09641cbb90accf06e74ccf5
|
client-secret: 97acf8ebb09641cbb90accf06e74ccf5
|
||||||
client-url: https://saasapi.fangxinqian.cn/openapi/v2/
|
client-url: https://saasapi.fangxinqian.cn/openapi/v2/
|
||||||
|
|
||||||
# json序列化相关配置
|
baiduce:
|
||||||
jackson:
|
app-id: 119377580
|
||||||
serialization:
|
app-key: 2YFRnP3ryU8IP0IqbqybTu6u
|
||||||
write-enums-using-to-string: true
|
app-secret: Zw8pTeM1ovys7kOsNUlElOc6jBi6zsFU
|
||||||
write-dates-as-timestamps: false
|
|
||||||
deserialization:
|
# json序列化相关配置
|
||||||
read-enums-using-to-string: true
|
jackson:
|
||||||
fail-on-unknown-properties: false
|
serialization:
|
||||||
default-property-inclusion: always
|
write-enums-using-to-string: true
|
||||||
date-format: yyyy-MM-dd HH:mm:ss
|
write-dates-as-timestamps: false
|
||||||
time-zone: GMT+8
|
deserialization:
|
||||||
|
read-enums-using-to-string: true
|
||||||
|
fail-on-unknown-properties: false
|
||||||
|
default-property-inclusion: always
|
||||||
|
date-format: yyyy-MM-dd HH:mm:ss
|
||||||
|
time-zone: GMT+8
|
||||||
Loading…
x
Reference in New Issue
Block a user