|
@@ -1,7 +1,29 @@
|
|
|
package cn.com.qmth.examcloud.core.oe.student.service.impl;
|
|
|
|
|
|
+import cn.com.qmth.examcloud.commons.exception.StatusException;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.entity.FaceBiopsyEntity;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.entity.FaceBiopsyItemEntity;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.entity.FaceBiopsyItemStepEntity;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.enums.FaceBiopsyAction;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.enums.FaceBiopsyType;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.repository.FaceBiopsyItemRepo;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.repository.FaceBiopsyItemStepRepo;
|
|
|
+import cn.com.qmth.examcloud.core.oe.common.repository.FaceBiopsyRepo;
|
|
|
+import cn.com.qmth.examcloud.core.oe.student.bean.FaceBiopsyInfo;
|
|
|
+import cn.com.qmth.examcloud.core.oe.student.bean.FaceBiopsyStepInfo;
|
|
|
import cn.com.qmth.examcloud.core.oe.student.service.FaceBiopsyService;
|
|
|
+import cn.com.qmth.examcloud.web.bootstrap.PropertyHolder;
|
|
|
+import cn.com.qmth.examcloud.web.helpers.GlobalHelper;
|
|
|
+import org.apache.commons.lang3.RandomUtils;
|
|
|
+import org.springframework.beans.factory.annotation.Autowired;
|
|
|
import org.springframework.stereotype.Service;
|
|
|
+import org.springframework.transaction.annotation.Transactional;
|
|
|
+
|
|
|
+import java.util.Date;
|
|
|
+import java.util.List;
|
|
|
+
|
|
|
+import java.util.ArrayList;
|
|
|
+import java.util.Random;
|
|
|
|
|
|
/**
|
|
|
* @Description 人脸活体检测接口实现类
|
|
@@ -12,4 +34,206 @@ import org.springframework.stereotype.Service;
|
|
|
@Service("faceBiopsyService")
|
|
|
public class FaceBiopsyServiceImpl implements FaceBiopsyService {
|
|
|
|
|
|
+ @Autowired
|
|
|
+ private FaceBiopsyRepo faceBiopsyRepo;
|
|
|
+ @Autowired
|
|
|
+ private FaceBiopsyItemRepo faceBiopsyItemRepo;
|
|
|
+ @Autowired
|
|
|
+ private FaceBiopsyItemStepRepo faceBiopsyItemStepRepo;
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public FaceBiopsyInfo getFaceBiopsyInfo(Long rootOrgId, Long examRecordDataId, FaceBiopsyType faceBiopsyType) {
|
|
|
+ //如果是第一次进行人脸活体检测,则初始化相关信息保存并返回
|
|
|
+ FaceBiopsyEntity faceBiopsyEntity = faceBiopsyRepo.findByExamRecordDataId(examRecordDataId);
|
|
|
+ if (faceBiopsyEntity == null) {
|
|
|
+ return addFirstFaceBiopsy(rootOrgId, examRecordDataId, faceBiopsyType);
|
|
|
+ }
|
|
|
+
|
|
|
+ //如果不是第一次人脸活体检测,判断是否有未检测完的记录,
|
|
|
+ FaceBiopsyInfo result = new FaceBiopsyInfo();
|
|
|
+ // 未完成的活体检测列表
|
|
|
+ List<FaceBiopsyItemEntity> unCompletedFaceBiopsyItemList =
|
|
|
+ faceBiopsyItemRepo.findByExamRecordDataIdAndCompleted(examRecordDataId, false);
|
|
|
+
|
|
|
+ //如果存在未完成的活体检测信息,则直接返回上次未完成的活检记录
|
|
|
+ if (unCompletedFaceBiopsyItemList != null && !unCompletedFaceBiopsyItemList.isEmpty()) {
|
|
|
+ FaceBiopsyItemEntity faceBiopsyItemEntity = unCompletedFaceBiopsyItemList.get(0);
|
|
|
+ result.setFaceBiopsyItemId(faceBiopsyItemEntity.getId());
|
|
|
+ result.setStartTime(calculateFaceBiopsyStartTime(examRecordDataId));
|
|
|
+
|
|
|
+ List<FaceBiopsyItemStepEntity> faceBiopsyItemStepEntityList =
|
|
|
+ faceBiopsyItemStepRepo.findByFaceBiopsyItemId(faceBiopsyItemEntity.getId());
|
|
|
+ result.setVerifySteps(copyFaceBiopsyStepDomainListFrom(faceBiopsyItemStepEntityList));
|
|
|
+ return result;
|
|
|
+ }
|
|
|
+
|
|
|
+ // 如果不存在未完成的活体检测信息,则判断活检次数是否超过最大活检次数
|
|
|
+ int verifiedTimes = faceBiopsyEntity.getVerifiedTimes();//已活检次数
|
|
|
+ //最大活体检测次数
|
|
|
+ int maxVerifyTimes = PropertyHolder.getInt("oe.faceBiopsy.maxVerifyTimes", 3);
|
|
|
+ //如果超过则提示超过最大活检次数,不允许活检
|
|
|
+ if (verifiedTimes >= maxVerifyTimes) {
|
|
|
+ throw new StatusException("201001", "本次考试已超过最大允许活检次数:" + maxVerifyTimes + ".不允许继续活检");
|
|
|
+ }
|
|
|
+
|
|
|
+ //没有超过,则追加活检次数
|
|
|
+ verifiedTimes++;
|
|
|
+ return appendFirstFaceBiopsy(faceBiopsyEntity.getId(), verifiedTimes, examRecordDataId, faceBiopsyType);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 第一次添加人脸活体检测结果
|
|
|
+ *
|
|
|
+ * @param rootOrgId
|
|
|
+ * @param examRecordDataId
|
|
|
+ * @param faceBiopsyType
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ @Transactional
|
|
|
+ public FaceBiopsyInfo addFirstFaceBiopsy(Long rootOrgId, Long examRecordDataId, FaceBiopsyType faceBiopsyType) {
|
|
|
+ //保存人脸活体检测相关信息
|
|
|
+ Long faceBiopsyId = addFaceBiopsyEntity(rootOrgId, examRecordDataId);
|
|
|
+ Long faceBiopsyItemId = addFaceBiopsyItemEntity(examRecordDataId, faceBiopsyType, faceBiopsyId);
|
|
|
+ List<FaceBiopsyItemStepEntity> faceBiopsyItemStepEntityList =
|
|
|
+ addFaceBiopsyItemStepList(examRecordDataId, faceBiopsyItemId);
|
|
|
+
|
|
|
+ //构建业务实体
|
|
|
+ return buildFaceBiopsyInfo(examRecordDataId, faceBiopsyItemId, faceBiopsyItemStepEntityList);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 追加人脸活体检测结果
|
|
|
+ *
|
|
|
+ * @param faceBiopsyId
|
|
|
+ * @param verifiedTimes
|
|
|
+ * @param examRecordDataId
|
|
|
+ * @param faceBiopsyType
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ @Transactional
|
|
|
+ public FaceBiopsyInfo appendFirstFaceBiopsy(Long faceBiopsyId, Integer verifiedTimes, Long examRecordDataId,
|
|
|
+ FaceBiopsyType faceBiopsyType) {
|
|
|
+ //更新人脸活体检测次数
|
|
|
+ FaceBiopsyEntity faceBiopsyEntity = GlobalHelper.getEntity(faceBiopsyRepo, faceBiopsyId, FaceBiopsyEntity.class);
|
|
|
+ faceBiopsyEntity.setVerifiedTimes(verifiedTimes);
|
|
|
+ faceBiopsyRepo.save(faceBiopsyEntity);
|
|
|
+ //添加人脸活体检测明细
|
|
|
+ Long faceBiopsyItemId = addFaceBiopsyItemEntity(examRecordDataId, faceBiopsyType, faceBiopsyId);
|
|
|
+ //添加人脸活体检测步骤
|
|
|
+ List<FaceBiopsyItemStepEntity> faceBiopsyItemStepEntityList =
|
|
|
+ addFaceBiopsyItemStepList(examRecordDataId, faceBiopsyItemId);
|
|
|
+
|
|
|
+ return buildFaceBiopsyInfo(examRecordDataId, faceBiopsyItemId, faceBiopsyItemStepEntityList);
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 构建人脸检测基本信息的业务实体对象
|
|
|
+ *
|
|
|
+ * @param examRecordDataId
|
|
|
+ * @param faceBiopsyItemId
|
|
|
+ * @param faceBiopsyItemStepEntityList
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ private FaceBiopsyInfo buildFaceBiopsyInfo(Long examRecordDataId, Long faceBiopsyItemId, List<FaceBiopsyItemStepEntity> faceBiopsyItemStepEntityList) {
|
|
|
+ //构建业务实体
|
|
|
+ FaceBiopsyInfo faceBiopsyInfo = new FaceBiopsyInfo();
|
|
|
+ faceBiopsyInfo.setFaceBiopsyItemId(faceBiopsyItemId);
|
|
|
+ faceBiopsyInfo.setStartTime(calculateFaceBiopsyStartTime(examRecordDataId));
|
|
|
+ faceBiopsyInfo.setVerifySteps(copyFaceBiopsyStepDomainListFrom(faceBiopsyItemStepEntityList));
|
|
|
+ return faceBiopsyInfo;
|
|
|
+ }
|
|
|
+
|
|
|
+ private List<FaceBiopsyStepInfo> copyFaceBiopsyStepDomainListFrom(List<FaceBiopsyItemStepEntity> faceBiopsyItemStepEntityList) {
|
|
|
+ List<FaceBiopsyStepInfo> resultList = new ArrayList<>();
|
|
|
+ for (FaceBiopsyItemStepEntity entity : faceBiopsyItemStepEntityList) {
|
|
|
+ FaceBiopsyStepInfo domain = new FaceBiopsyStepInfo();
|
|
|
+ domain.setAction(entity.getAction());
|
|
|
+ domain.setStay(entity.getActionStay());
|
|
|
+ domain.setStepId(entity.getId());
|
|
|
+ resultList.add(domain);
|
|
|
+ }
|
|
|
+ return resultList;
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 添加活体检测的具体步骤
|
|
|
+ *
|
|
|
+ * @param examRecordDataId 考试记录id
|
|
|
+ * @param faceBiopsyItemId 人脸活体检测明细id
|
|
|
+ */
|
|
|
+ private List<FaceBiopsyItemStepEntity> addFaceBiopsyItemStepList(Long examRecordDataId, Long faceBiopsyItemId) {
|
|
|
+ List<FaceBiopsyItemStepEntity> faceBiopsyItemStepEntityList = new ArrayList<FaceBiopsyItemStepEntity>();
|
|
|
+ FaceBiopsyItemStepEntity firstStep = new FaceBiopsyItemStepEntity();
|
|
|
+ firstStep.setExamRecordDataId(examRecordDataId);
|
|
|
+ firstStep.setFaceBiopsyItemId(faceBiopsyItemId);
|
|
|
+ firstStep.setAction(FaceBiopsyAction.FACE_COMPARE);
|
|
|
+ faceBiopsyItemStepEntityList.add(firstStep);
|
|
|
+
|
|
|
+ FaceBiopsyItemStepEntity secondStep = new FaceBiopsyItemStepEntity();
|
|
|
+ secondStep.setExamRecordDataId(examRecordDataId);
|
|
|
+ secondStep.setFaceBiopsyItemId(faceBiopsyItemId);
|
|
|
+ secondStep.setAction(FaceBiopsyAction.HAPPY);
|
|
|
+ secondStep.setActionStay(randomGenerateActionStay());//随机生成指令时长(3至6秒)
|
|
|
+ faceBiopsyItemStepEntityList.add(secondStep);
|
|
|
+
|
|
|
+ faceBiopsyItemStepRepo.saveAll(faceBiopsyItemStepEntityList);
|
|
|
+ return faceBiopsyItemStepEntityList;
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 随机生成指令持续的时长
|
|
|
+ *
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ private Integer randomGenerateActionStay() {
|
|
|
+ int minStay = PropertyHolder.getInt("oe.faceBiopsy.minActionStay", 3);
|
|
|
+ int maxStay = PropertyHolder.getInt("oe.faceBiopsy.maxActionStay", 6);
|
|
|
+ return RandomUtils.nextInt(minStay, maxStay);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 添加人脸活体检测明细
|
|
|
+ *
|
|
|
+ * @param examRecordDataId 考试记录id
|
|
|
+ * @param faceBiopsyType 人脸活体检测类型
|
|
|
+ * @param faceBiopsyId 人脸活体检测id
|
|
|
+ * @return Long 人脸活体检测明细id
|
|
|
+ */
|
|
|
+ private Long addFaceBiopsyItemEntity(Long examRecordDataId, FaceBiopsyType faceBiopsyType, Long faceBiopsyId) {
|
|
|
+ FaceBiopsyItemEntity faceBiopsyItemEntity = new FaceBiopsyItemEntity();
|
|
|
+ faceBiopsyItemEntity.setExamRecordDataId(examRecordDataId);
|
|
|
+ faceBiopsyItemEntity.setFaceBiopsyId(faceBiopsyId);
|
|
|
+ faceBiopsyItemEntity.setFaceBiopsyType(faceBiopsyType);
|
|
|
+ faceBiopsyItemRepo.save(faceBiopsyItemEntity);
|
|
|
+ return faceBiopsyItemEntity.getId();
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 添加人脸活体检测结果
|
|
|
+ *
|
|
|
+ * @param rootOrgId 学校id
|
|
|
+ * @param examRecordDataId 考试记录id
|
|
|
+ * @return Long 人脸活体检测结果id
|
|
|
+ */
|
|
|
+ private Long addFaceBiopsyEntity(Long rootOrgId, Long examRecordDataId) {
|
|
|
+ FaceBiopsyEntity faceBiopsyEntity = new FaceBiopsyEntity();
|
|
|
+ faceBiopsyEntity.setRootOrgId(rootOrgId);
|
|
|
+ faceBiopsyEntity.setExamRecordDataId(examRecordDataId);
|
|
|
+ faceBiopsyEntity.setVerifiedTimes(1);
|
|
|
+ faceBiopsyRepo.save(faceBiopsyEntity);
|
|
|
+ return faceBiopsyEntity.getId();
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 计算人脸活体检测开始时间
|
|
|
+ *
|
|
|
+ * @param examRecordDataId 考试记录id
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ private Date calculateFaceBiopsyStartTime(Long examRecordDataId) {
|
|
|
+ //TODO
|
|
|
+ return null;
|
|
|
+ }
|
|
|
}
|