|
@@ -0,0 +1,258 @@
|
|
|
+package com.yonge.cooleshow.biz.dal.service.impl;
|
|
|
+
|
|
|
+import com.yonge.cooleshow.auth.api.entity.SysUser;
|
|
|
+import com.yonge.cooleshow.auth.api.enums.CertificateTypeEnum;
|
|
|
+import com.yonge.cooleshow.biz.dal.entity.ContractTemplate;
|
|
|
+import com.yonge.cooleshow.biz.dal.entity.SysUserTsign;
|
|
|
+import com.yonge.cooleshow.biz.dal.service.*;
|
|
|
+import com.yonge.cooleshow.biz.dal.vo.StudentVo;
|
|
|
+import com.yonge.cooleshow.biz.dal.vo.TeacherVo;
|
|
|
+import com.yonge.cooleshow.common.constant.SysConfigConstant;
|
|
|
+import com.yonge.cooleshow.common.entity.HttpResponseResult;
|
|
|
+import com.yonge.cooleshow.common.enums.ContractTemplateTypeEnum;
|
|
|
+import com.yonge.cooleshow.common.enums.SysUserType;
|
|
|
+import com.yonge.toolset.base.exception.BizException;
|
|
|
+import com.yonge.toolset.thirdparty.eseal.ESealPlugin;
|
|
|
+import com.yonge.toolset.thirdparty.storage.StoragePluginContext;
|
|
|
+import com.yonge.toolset.thirdparty.storage.provider.KS3StoragePlugin;
|
|
|
+import com.yonge.toolset.thirdparty.user.realname.RealnameAuthenticationPluginContext;
|
|
|
+import com.yonge.toolset.thirdparty.user.realname.provider.LinkfaceRealnameAuthenticationPlugin;
|
|
|
+import com.yonge.toolset.utils.date.DateUtil;
|
|
|
+import com.yonge.toolset.utils.freemarker.FreemarkerTemplateEngine;
|
|
|
+import com.yonge.toolset.utils.pdf.PDFUtil;
|
|
|
+import org.apache.commons.io.FileUtils;
|
|
|
+import org.apache.commons.lang3.StringUtils;
|
|
|
+import org.slf4j.Logger;
|
|
|
+import org.slf4j.LoggerFactory;
|
|
|
+import org.springframework.beans.factory.InitializingBean;
|
|
|
+import org.springframework.beans.factory.annotation.Autowired;
|
|
|
+import org.springframework.beans.factory.annotation.Value;
|
|
|
+import org.springframework.scheduling.annotation.Async;
|
|
|
+import org.springframework.stereotype.Service;
|
|
|
+import org.springframework.transaction.annotation.Isolation;
|
|
|
+import org.springframework.transaction.annotation.Propagation;
|
|
|
+import org.springframework.transaction.annotation.Transactional;
|
|
|
+
|
|
|
+import java.io.File;
|
|
|
+import java.io.IOException;
|
|
|
+import java.text.DateFormat;
|
|
|
+import java.text.SimpleDateFormat;
|
|
|
+import java.time.LocalDateTime;
|
|
|
+import java.util.*;
|
|
|
+
|
|
|
+@Service
|
|
|
+public class ContractServiceImpl implements ContractService {
|
|
|
+ @Autowired
|
|
|
+ private SysUserService sysUserService;
|
|
|
+ @Autowired
|
|
|
+ private SysUserTsignService sysUserTsignService;
|
|
|
+ @Autowired
|
|
|
+ private ContractTemplateService contractTemplateService;
|
|
|
+ @Autowired
|
|
|
+ private SysUserContractRecordService contractRecordService;
|
|
|
+ @Autowired
|
|
|
+ private StudentService studentService;
|
|
|
+ @Autowired
|
|
|
+ private TeacherService teacherService;
|
|
|
+ @Autowired
|
|
|
+ private SysConfigService sysConfigService;
|
|
|
+ @Autowired
|
|
|
+ private RealnameAuthenticationPluginContext realnameAuthenticationPluginContext;
|
|
|
+ @Autowired
|
|
|
+ private StoragePluginContext storagePluginContext;
|
|
|
+ @Autowired
|
|
|
+ private ESealPlugin eSealPlugin;
|
|
|
+
|
|
|
+ @Value("${contract.baseDir:/var/pdf}")
|
|
|
+ private String contractBaseDir;
|
|
|
+
|
|
|
+ @Value("${message.debugMode}")
|
|
|
+ private boolean debugMode;
|
|
|
+
|
|
|
+ private DateFormat dateFormatOss = new SimpleDateFormat("yyyy/MM/dd");
|
|
|
+
|
|
|
+ private DateFormat dateFormat1 = new SimpleDateFormat("yyMMddHHmmSS");
|
|
|
+
|
|
|
+ private final Logger logger = LoggerFactory.getLogger(ContractService.class);
|
|
|
+
|
|
|
+ @Override
|
|
|
+ @Async
|
|
|
+ @Transactional(rollbackFor = Exception.class, isolation = Isolation.READ_COMMITTED, propagation = Propagation.REQUIRES_NEW)
|
|
|
+ public HttpResponseResult<String> transferProduceContract(Long userId, SysUserType userType, ContractTemplateTypeEnum contractType, Boolean isShowVisualSeal) {
|
|
|
+ SysUser user = sysUserService.findUserById(userId);
|
|
|
+ if (user == null) {
|
|
|
+ logger.error("用户不存在({})", userId);
|
|
|
+ return HttpResponseResult.failed("用户不存在");
|
|
|
+ }
|
|
|
+
|
|
|
+ if (StringUtils.isBlank(user.getRealName()) || StringUtils.isBlank(user.getIdCardNo())) {
|
|
|
+ logger.error("身份信息缺失({})", userId);
|
|
|
+ return HttpResponseResult.failed("身份信息缺失");
|
|
|
+ }
|
|
|
+
|
|
|
+ SysUserTsign sysUserTsign = sysUserTsignService.get(userId);
|
|
|
+ if (sysUserTsign == null) {
|
|
|
+ try {
|
|
|
+ sysUserTsign = register(userId, user.getRealName(), user.getIdCardNo(), user.getPhone());
|
|
|
+ } catch (Exception e) {
|
|
|
+ logger.error("用户电子签章注册失败", e);
|
|
|
+ return HttpResponseResult.failed("用户电子签章注册失败");
|
|
|
+ }
|
|
|
+ }
|
|
|
+ Date date = new Date();
|
|
|
+
|
|
|
+ // 合成freemarker
|
|
|
+ String srcPdfPath = contractBaseDir + "/product/" + dateFormat1.format(date) + "/" + userId + "_" + LocalDateTime.now().getSecond() + ".pdf";
|
|
|
+
|
|
|
+ File srcFile = new File(srcPdfPath);
|
|
|
+
|
|
|
+ File debtFile = new File(srcFile.getParent());
|
|
|
+ if (!debtFile.exists()) {
|
|
|
+ debtFile.mkdirs();
|
|
|
+ }
|
|
|
+
|
|
|
+ FreemarkerTemplateEngine templateEngine = FreemarkerTemplateEngine.getInstance();
|
|
|
+ templateEngine.setClassForTemplateLoading(ContractServiceImpl.class, "/config/contracts/");
|
|
|
+
|
|
|
+ Boolean signflag = contractRecordService.checkContractSign(userId,userType, contractType);
|
|
|
+ if (signflag) {
|
|
|
+ return HttpResponseResult.failed("用户已经签署协议");
|
|
|
+ }
|
|
|
+
|
|
|
+ // 查询最新协议模板
|
|
|
+ ContractTemplate tenantContractTemplate = contractTemplateService.queryLatestContractTemplate(contractType);
|
|
|
+ if(tenantContractTemplate == null){
|
|
|
+ logger.error("最新协议模板查询失败");
|
|
|
+ return HttpResponseResult.failed("最新协议模板查询失败");
|
|
|
+ }
|
|
|
+ String mainContent = tenantContractTemplate.getContractTemplateContent();
|
|
|
+
|
|
|
+ Map<String, Object> params = new HashMap<>();
|
|
|
+ String companyName = sysConfigService.findConfigValue(SysConfigConstant.COMPANY_NAME);
|
|
|
+ params.put("companyName",companyName);
|
|
|
+ params.put("companySealPicture",sysConfigService.findConfigValue(SysConfigConstant.COMPANY_SEAL_PICTURE));
|
|
|
+ params.put("contractMainContent",mainContent);
|
|
|
+ params.put("isShowVisualSeal", isShowVisualSeal);
|
|
|
+
|
|
|
+
|
|
|
+ Map<String,Object> userInfo = new HashMap<>();
|
|
|
+ userInfo.put("realName",user.getRealName());
|
|
|
+ userInfo.put("phone",user.getPhone());
|
|
|
+ userInfo.put("idCardNo",user.getIdCardNo());
|
|
|
+
|
|
|
+ if(SysUserType.STUDENT.equals(userType)){
|
|
|
+ StudentVo detail = studentService.detail(userId);
|
|
|
+ userInfo.put("subjectName",detail.getSubjectName());
|
|
|
+ }else if(SysUserType.TEACHER.equals(userType)){
|
|
|
+ TeacherVo detail = teacherService.detail(userId);
|
|
|
+ userInfo.put("subjectName",detail.getSubjectName());
|
|
|
+ }
|
|
|
+ params.put("userInfo", userInfo);
|
|
|
+
|
|
|
+ templateEngine.render(params, "latest_contract_template.ftl", srcFile);
|
|
|
+
|
|
|
+ // 生成借款协议PDF
|
|
|
+ try {
|
|
|
+ PDFUtil.renderToPDFByData(ContractServiceImpl.class.getResource("/").getFile(), FileUtils.readFileToString(srcFile), srcPdfPath, "simsun.ttc");
|
|
|
+ } catch (IOException e) {
|
|
|
+ logger.error("生成产品协议失败", e);
|
|
|
+ return HttpResponseResult.failed("生成产品协议失败");
|
|
|
+ }
|
|
|
+
|
|
|
+ String organCode = sysConfigService.findConfigValue(SysConfigConstant.COMPANY_ORGAN_CODE);
|
|
|
+ SysUserTsign organTsign = sysUserTsignService.queryByCardNo(organCode);
|
|
|
+ if (organTsign == null) {
|
|
|
+ //创建企业签章
|
|
|
+ addTsign(0L, organCode, companyName);
|
|
|
+ }
|
|
|
+
|
|
|
+ eSealPlugin.organSign(organTsign.getSealData(), srcPdfPath, srcPdfPath);
|
|
|
+ if (sysUserTsign != null && CertificateTypeEnum.IDENTITY.getCode().equals(user.getCertificateType())) {
|
|
|
+ eSealPlugin.userSign(sysUserTsign.getAccountId(), sysUserTsign.getSealData(), srcPdfPath, srcPdfPath);
|
|
|
+ }
|
|
|
+
|
|
|
+ // 上传到oss
|
|
|
+ String dateStrOss = dateFormatOss.format(date);
|
|
|
+ dateStrOss = "product/" + dateStrOss + "/" + DateUtil.getHour(date);
|
|
|
+ String pdfFilePath = storagePluginContext.uploadFile(KS3StoragePlugin.PLUGIN_NAME, dateStrOss, srcFile);
|
|
|
+ FileUtils.deleteQuietly(srcFile);
|
|
|
+ return HttpResponseResult.succeed(pdfFilePath);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ public SysUserTsign register(Long userId, String realName, String idCardNo, String mobileNo) {
|
|
|
+
|
|
|
+ if (StringUtils.isBlank(realName) || StringUtils.isBlank(idCardNo) || StringUtils.isBlank(mobileNo)) {
|
|
|
+ return null;
|
|
|
+ }
|
|
|
+
|
|
|
+ SysUserTsign sysUserTsign = sysUserTsignService.get(userId);
|
|
|
+ if (sysUserTsign == null) {
|
|
|
+
|
|
|
+ String accountId = "";
|
|
|
+ String sealData = "";
|
|
|
+
|
|
|
+ SysUser user = sysUserService.findUserById(userId);
|
|
|
+ if (user == null) {
|
|
|
+ throw new BizException("用户信息查询失败");
|
|
|
+ }
|
|
|
+
|
|
|
+ if (CertificateTypeEnum.IDENTITY.getCode().equals(user.getCertificateType())) {
|
|
|
+ if (!debugMode) {
|
|
|
+ realnameAuthenticationPluginContext.getRealnameAuthenticationPlugin(LinkfaceRealnameAuthenticationPlugin.getName()).verify(realName, idCardNo);
|
|
|
+ }
|
|
|
+
|
|
|
+ accountId = eSealPlugin.createUserAccount(realName, idCardNo, mobileNo);
|
|
|
+
|
|
|
+ if (StringUtils.isBlank(accountId)) {
|
|
|
+ throw new BizException("创建电子存证账户失败");
|
|
|
+ }
|
|
|
+
|
|
|
+ sealData = eSealPlugin.createUserSeal(accountId);
|
|
|
+
|
|
|
+ if (StringUtils.isBlank(sealData)) {
|
|
|
+ throw new BizException("创建电子存证印章失败");
|
|
|
+ }
|
|
|
+ }
|
|
|
+ sysUserTsign = new SysUserTsign(userId, accountId, sealData, realName, idCardNo);
|
|
|
+
|
|
|
+ sysUserTsignService.insert(sysUserTsign);
|
|
|
+ return sysUserTsign;
|
|
|
+ }
|
|
|
+ return null;
|
|
|
+ }
|
|
|
+
|
|
|
+ public void addTsign(Long userId, String organCode, String orgName) {
|
|
|
+ Optional.ofNullable(organCode).orElseThrow(() -> new BizException("营业执照编号不能为空!"));
|
|
|
+ Optional.ofNullable(orgName).orElseThrow(() -> new BizException("营业名称不能为空"));
|
|
|
+
|
|
|
+ SysUserTsign sysUserTsign = null;
|
|
|
+
|
|
|
+ SysUserTsign orignSysUserTsign = sysUserTsignService.queryByCardNo(organCode);
|
|
|
+
|
|
|
+ if (orignSysUserTsign == null) {
|
|
|
+
|
|
|
+ String accountId = eSealPlugin.createOrganAccount(orgName, organCode);
|
|
|
+ if (StringUtils.isBlank(accountId)) {
|
|
|
+ throw new BizException("创建企业电子存证账户失败");
|
|
|
+ }
|
|
|
+
|
|
|
+ String sealData = eSealPlugin.createOrganSeal(accountId, "", "");
|
|
|
+ if (StringUtils.isBlank(sealData)) {
|
|
|
+ throw new BizException("创建电子存证印章失败");
|
|
|
+ }
|
|
|
+
|
|
|
+ sysUserTsign = new SysUserTsign(-userId, accountId, sealData, orgName, organCode);
|
|
|
+ sysUserTsignService.insert(sysUserTsign);
|
|
|
+
|
|
|
+ } else if (!StringUtils.equals(orignSysUserTsign.getName(), orgName)) {
|
|
|
+ if (eSealPlugin.updateOrganAccount(orignSysUserTsign.getAccountId(), orgName, organCode)) {
|
|
|
+ orignSysUserTsign.setName(orgName);
|
|
|
+ sysUserTsignService.update(orignSysUserTsign);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+}
|