package com.product.saas.service;
|
|
import java.io.File;
|
import java.util.Date;
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.stereotype.Component;
|
|
import com.product.admin.config.CmnConst;
|
import com.product.admin.service.CodeService;
|
import com.product.admin.service.LoginAuthService;
|
import com.product.core.config.Global;
|
import com.product.core.dao.BaseDao;
|
import com.product.core.entity.FieldSetEntity;
|
import com.product.core.exception.BaseException;
|
import com.product.core.service.support.AbstractBaseService;
|
import com.product.core.transfer.Transactional;
|
import com.product.file.service.FileManagerService;
|
import com.product.module.sys.service.UserService;
|
import com.product.saas.config.SaasCode;
|
import com.product.saas.config.SaasConst;
|
import com.product.saas.service.idel.ITenantApplyService;
|
import com.product.tool.flow.service.FlowService;
|
import com.product.util.BaseUtil;
|
|
import cn.hutool.core.io.FileUtil;
|
|
/**
|
* 租户申请
|
*
|
*/
|
@Component
|
public class TenantApplyService extends AbstractBaseService implements ITenantApplyService{
|
|
@Autowired
|
BaseDao baseDao;
|
|
@Autowired
|
CodeService codeService;
|
|
@Autowired
|
UserService userService;
|
|
@Autowired
|
FlowService flowService;
|
|
@Autowired
|
LoginAuthService loginAuthService;
|
|
@Autowired
|
FileManagerService fileManagerService;
|
|
|
|
/**
|
* 租户信息读取和验证
|
* @param fse
|
* @return
|
*/
|
public boolean validTenantInfo(FieldSetEntity fse) {
|
// 获取手机号和验证码
|
String phone = fse.getString("phone");
|
String code = fse.getString("code");
|
// 验证验证码是否正确
|
loginAuthService.verifyPhoneCaptcha(phone, code);
|
String unitName = fse.getString("unitName");
|
// 验证信息是否匹配
|
FieldSetEntity fseTenantByPhone = baseDao.getFieldSetEntityByFilter(SaasConst.PRODUCT_SYS_TENANT_APPLY, "applicant_phone = ?", new Object[] {phone}, false);
|
FieldSetEntity fseTenantByName = baseDao.getFieldSetEntityByFilter(SaasConst.PRODUCT_SYS_TENANT_APPLY, "unit_name = ?", new Object[] {unitName}, false);
|
// 情况1:手机号和单位名都不存在 -> 通过
|
if (fseTenantByPhone == null && fseTenantByName == null) {
|
return true;
|
}
|
// 情况2:只存在手机号 -> 手机号已申请
|
if (fseTenantByPhone != null && fseTenantByName == null) {
|
throw new BaseException(SaasCode.TENANT_APPLY_VALID_PHONE_HAS_APPLY.getValue(), SaasCode.TENANT_APPLY_VALID_PHONE_HAS_APPLY.getText());
|
}
|
// 情况3:只存在单位名 -> 单位已申请
|
if (fseTenantByPhone == null && fseTenantByName != null) {
|
throw new BaseException(SaasCode.TENANT_APPLY_VALID_UNIT_HAS_APPLY.getValue(), SaasCode.TENANT_APPLY_VALID_UNIT_HAS_APPLY.getText());
|
}
|
// 情况4:都存在 -> 检查是否是同一条记录
|
if (fseTenantByPhone.getUUID().equals(fseTenantByName.getUUID())) {
|
return true;
|
}
|
// 情况5:都存在但不是同一条记录 -> 手机号和单位名都已申请
|
throw new BaseException(SaasCode.TENANT_APPLY_VALID_UNIT_AND_PHONE_HAS_APPLY.getValue(), SaasCode.TENANT_APPLY_VALID_UNIT_AND_PHONE_HAS_APPLY.getText());
|
}
|
|
/**
|
* 获取指定租户申请,根据申请人手机号
|
* @param applicantPhone 申请人手机号
|
* @return
|
*/
|
public FieldSetEntity getTenantApplyByPhone(String applicantPhone) {
|
StringBuilder sql = new StringBuilder();
|
sql.append("SELECT A.*, B.file_name AS business_license_name, B.attachment_size AS business_license_size, C.dict_label AS apply_status_label \n");
|
sql.append("FROM product_sys_tenant_apply A \n");
|
sql.append("LEFT JOIN product_sys_attachments B ON B.uuid = A.business_license \n");
|
sql.append("LEFT JOIN product_sys_dict C ON C.dict_value = A.apply_status AND C.dict_name = 'SYSTEM_TENANT_APPLY_STATUS' \n");
|
sql.append("WHERE A.applicant_phone = ?");
|
return baseDao.getFieldSetEntityBySQL(sql.toString(), new Object[] {applicantPhone}, false);
|
}
|
|
/**
|
* 保存租户申请
|
* approval_sign:送审标识(0:保存;1:送审或激活)
|
* @param fse
|
* @return
|
*/
|
@Override
|
@Transactional
|
public boolean saveTenantApply(FieldSetEntity fse) {
|
// 获取送审标志
|
String flowSign = fse.getString("approval_sign");
|
if (!BaseUtil.strIsNull(flowSign) || "1".equals(flowSign)) {
|
// 保存租户信息
|
fse.setValue("apply_status", 2);
|
fse.setValue("is_passed", 0);
|
baseDao.saveFieldSetEntity(fse);
|
|
// 查询送审记录
|
FieldSetEntity fseTask = baseDao.getFieldSetEntityByFilter("product_sys_flow_task", "table_name = 'product_sys_tenant_apply' AND record_uuid = ?", new Object[] {fse.getUUID()}, false);
|
if (fseTask == null) {
|
// 获取送审开始的后一个节点信息
|
StringBuilder sql = new StringBuilder();
|
sql.append("SELECT * FROM product_sys_flow_node \n");
|
sql.append("WHERE uuid IN ( \n");
|
sql.append(" SELECT target_uuid FROM product_sys_flow_link \n");
|
sql.append(" WHERE source_uuid IN ( \n");
|
sql.append(" SELECT uuid FROM product_sys_flow_node \n");
|
sql.append(" WHERE module_type = 1 AND flow_uuid IN ( \n");
|
sql.append(" SELECT uuid FROM product_sys_flow_model \n");
|
sql.append(" WHERE type_code = ? \n");
|
sql.append(" ) \n");
|
sql.append(" ) \n");
|
sql.append(") \n");
|
FieldSetEntity fseFlowNode = baseDao.getFieldSetEntityBySQL(sql.toString(), new Object[] {SaasConst.FLOW_TENANT_APPLY}, false);
|
if (fseFlowNode == null || BaseUtil.strIsNull(fseFlowNode.getString("default_users"))) {
|
throw new BaseException("租户申请流程有误", "租户申请流程有误");
|
}
|
// 封装送审参数
|
FieldSetEntity fseFlowTask = new FieldSetEntity(SaasConst.PRODUCT_SYS_TENANT_APPLY);
|
fseFlowTask.setValue("uuid", fse.getUUID());
|
fseFlowTask.setValue("type_code", SaasConst.FLOW_TENANT_APPLY);
|
fseFlowTask.setValue("accepters", fseFlowNode.getString("default_users"));
|
fseFlowTask.setValue("flow_title", "租户申请-" + fse.getString("unit_name"));
|
// 执行送审
|
flowService.autoSendFlow(fseFlowTask);
|
} else {
|
// 激活送审任务
|
FieldSetEntity fseTaskDetail = new FieldSetEntity("product_sys_flow_detail");
|
fseTaskDetail.setValue("task_uuid", fseTask.getUUID());
|
fseTaskDetail.setValue("is_sub_flow", "0");
|
fseTaskDetail.setValue("opinion", "租户撤回后重新提交");
|
flowService.activate(fseTaskDetail);
|
}
|
return true;
|
} else {
|
fse.setValue("apply_status", 1);
|
fse.setValue("is_passed", 0);
|
// 保存租户信息
|
return baseDao.saveFieldSetEntity(fse);
|
}
|
}
|
|
/**
|
* 撤销租户申请
|
* @param fse
|
* @return
|
*/
|
@Override
|
@Transactional
|
public boolean cancelTenantApply(FieldSetEntity fse){
|
// 获取对应流程任务
|
FieldSetEntity fseTask = baseDao.getFieldSetEntityByFilter("product_sys_flow_task", "table_name = 'product_sys_tenant_apply' AND record_uuid = ?", new Object[] {fse.getUUID()}, false);
|
if (fseTask == null) {
|
throw new BaseException(SaasCode.TENANT_AAPLY_INFO_FLOW_TASK_ERROR.getValue(), SaasCode.TENANT_AAPLY_INFO_FLOW_TASK_ERROR.getText());
|
}
|
// 终止流程
|
flowService.stop(fseTask);
|
// 标记申请数据为未送审
|
return baseDao.executeUpdate("UPDATE product_sys_tenant_apply SET apply_status = 1 WHERE applicant_phone = ? AND unit_name = ? ",
|
new Object[] {fse.getString("applicant_phone"), fse.getString("unit_name")});
|
}
|
|
/**
|
* 刷新申请单状态(流程处理器调用)
|
* @param fseApply
|
*/
|
public void refreshApplyStatus(FieldSetEntity fseApply) {
|
if ("1".equals(fseApply.getString("is_passed"))) {
|
// 审核通过
|
baseDao.executeUpdate("UPDATE product_sys_tenant_apply SET apply_status = 3 WHERE uuid = ?", new Object[] {fseApply.getUUID()});
|
} else {
|
// 审核失败
|
baseDao.executeUpdate("UPDATE product_sys_tenant_apply SET apply_status = 4 WHERE uuid = ?", new Object[] {fseApply.getUUID()});
|
}
|
}
|
|
/**
|
* 申请完成
|
* @param fseApply
|
*/
|
@Transactional
|
public void applyFinish(FieldSetEntity fseApply) {
|
// 创建客户信息
|
FieldSetEntity fseClient = new FieldSetEntity(SaasConst.PRODUCT_SYS_CLIENTS);
|
fseClient.setValue("client_name", fseApply.getString("unit_name"));
|
fseClient.setValue("client_tel", fseApply.getString("applicant_phone"));
|
fseClient.setValue("client_code", codeService.createCode(SaasConst.PRODUCT_SYS_CLIENTS, "client_code", ""));
|
fseClient.setValue("attachment_capacity", "2130000000");
|
fseClient.setValue("platform_admin", fseApply.getString("platform_admin"));
|
fseClient.setValue("expiration_date", fseApply.getString("expiration_date"));
|
fseClient.setValue("client_unit_type", fseApply.getString("unit_type"));
|
fseClient.setValue("client_address_province_id", fseApply.getString("area_province"));
|
fseClient.setValue("client_address_city_id", fseApply.getString("area_city"));
|
fseClient.setValue("client_address_county_id", fseApply.getString("area_county"));
|
fseClient.setValue("client_address_line_one", fseApply.getString("address"));
|
fseClient.setValue(CmnConst.CREATED_BY, 1);
|
fseClient.setValue(CmnConst.CREATED_UTC_DATETIME, new Date());
|
baseDao.add(fseClient);
|
// 复制license到web模块
|
copyLicense(fseApply.getString("license"), fseClient.getString("client_code"));
|
|
// 创建组织机构单位
|
FieldSetEntity fseOrgUnit = new FieldSetEntity(CmnConst.PRODUCT_SYS_ORG_LEVELS);
|
fseOrgUnit.setValue("client_uuid", fseClient.getUUID());
|
fseOrgUnit.setValue("org_level_name", fseApply.getString("unit_name"));
|
fseOrgUnit.setValue("org_level_all", "成都XXXX软件有限公司>" + fseApply.getString("unit_name"));
|
fseOrgUnit.setValue("org_level_code", codeService.createCode("product_sys_org_levels", "org_level_code", "001"));
|
fseOrgUnit.setValue("org_level_code_parent", "001");
|
fseOrgUnit.setValue("org_level_type", 0);
|
fseOrgUnit.setValue("org_level_status", 0);
|
fseOrgUnit.setValue("sequence", 1);
|
fseOrgUnit.setValue(CmnConst.CREATED_BY, 1);
|
fseOrgUnit.setValue(CmnConst.CREATED_UTC_DATETIME, new Date());
|
baseDao.add(fseOrgUnit);
|
// 创建租户管理员用户信息
|
FieldSetEntity fseUser = new FieldSetEntity(CmnConst.PRODUCT_SYS_USERS);
|
fseUser.setValue(CmnConst.USER_NAME, fseApply.getString("applicant_name"));
|
fseUser.setValue(CmnConst.USER_ACCOUNT, fseApply.getString("applicant_phone"));
|
fseUser.setValue(CmnConst.USER_PRIMARY_EMAIL, fseApply.getString("applicant_email"));
|
fseUser.setValue(CmnConst.USER_MOBILE_NUMBER, fseApply.getString("applicant_phone"));
|
fseUser.setValue(CmnConst.USER_PWD, userService.createPassWord(fseApply.getString("applicant_phone"), fseApply.getString("applicant_pwd")));
|
fseUser.setValue(CmnConst.IS_MANAGER, 1);
|
fseUser.setValue(CmnConst.STATUS, 1);
|
fseUser.setValue(CmnConst.CREATED_BY, 1);
|
fseUser.setValue(CmnConst.CREATED_UTC_DATETIME, new Date());
|
baseDao.add(fseUser);
|
FieldSetEntity fseUserInfo = baseDao.getFieldSetEntity(CmnConst.PRODUCT_SYS_USERS, fseUser.getUUID(), false);
|
// 创建租户管理员信息
|
FieldSetEntity fseManager = new FieldSetEntity(CmnConst.PRODUCT_SYS_ORG_MANAGER);
|
fseManager.setValue(CmnConst.USER_ID, fseUserInfo.getString(CmnConst.USER_ID));
|
fseManager.setValue(CmnConst.ORG_LEVEL_UUID, fseOrgUnit.getUUID());
|
fseManager.setValue(CmnConst.MANAGER_TYPE, 2);
|
fseManager.setValue(CmnConst.ROLE_UUIDS, "eabb00f3-2118-4165-967b-a7d88f472f67-notchange");
|
fseManager.setValue(CmnConst.IS_USED, 1);
|
fseManager.setValue(CmnConst.CLIENT_UUID, fseClient.getUUID());
|
fseManager.setValue(CmnConst.CREATED_BY, 1);
|
fseManager.setValue(CmnConst.CREATED_UTC_DATETIME, new Date());
|
baseDao.add(fseManager);
|
baseDao.executeUpdate("UPDATE product_sys_tenant_apply SET client_uuid = ? WHERE uuid = ?", new Object[] {fseClient.getUUID(), fseApply.getUUID()});
|
|
// 发送信息给租户管理员
|
FieldSetEntity fse = new FieldSetEntity("temp");
|
fse.setValue("applicant_phone", fseApply.getString("applicant_phone"));
|
loginAuthService.sendMessage(fse, "租户注册成功", "temp");
|
}
|
|
/**
|
* 复制license到指定目录
|
* @param fileUUID 附件UUID
|
* @param clientCode 客户编码
|
*/
|
public void copyLicense(String fileUUID, String clientCode) {
|
|
// 获取文件信息
|
FieldSetEntity fse = baseDao.getFieldSetEntity(SaasConst.PRODUCT_SYS_ATTACHMENTS, fileUUID, false);
|
if (fse == null) {
|
throw new BaseException(SaasCode.TENANT_APPLY_LICENSE_DATA_NO_EXIST.getValue(), SaasCode.TENANT_APPLY_LICENSE_DATA_NO_EXIST.getText());
|
}
|
|
// 构建源文件路径
|
String baseDir = System.getProperty("user.dir");
|
String localDir = Global.getSystemConfig("local.dir", "");
|
String attachmentUrl = fse.getString("attachment_url");
|
String attachmentTitle = fse.getString("attachment_title");
|
|
String filePath = baseDir + File.separator + localDir + File.separator + attachmentUrl + File.separator + attachmentTitle;
|
|
// 检查源文件是否存在
|
if (!FileUtil.exist(filePath)) {
|
throw new BaseException(SaasCode.TENANT_APPLY_LICENSE_FILE_NO_EXIST.getValue(), SaasCode.TENANT_APPLY_LICENSE_FILE_NO_EXIST.getText());
|
}
|
|
// 构建目标目录
|
String targetDir = baseDir + File.separator + "resources" + File.separator;
|
FileUtil.mkdir(targetDir);
|
|
// 构建目标文件名:license + clientCode + .dat
|
// 无论原文件是否有扩展名,都使用.dat扩展名
|
String targetFileName = "license" + clientCode + ".dat";
|
String targetPath = targetDir + targetFileName;
|
|
// 复制文件
|
try {
|
// 使用Hutool复制,第三个参数true表示覆盖已存在的文件
|
FileUtil.copy(filePath, targetPath, true);
|
// 验证复制结果
|
if (FileUtil.exist(targetPath)) {
|
long sourceSize = FileUtil.size(new File(filePath));
|
long targetSize = FileUtil.size(new File(targetPath));
|
if (sourceSize != targetSize) {
|
throw new BaseException(SaasCode.TENANT_APPLY_LICENSE_FILE_COPY_FAIL.getValue(), SaasCode.TENANT_APPLY_LICENSE_FILE_COPY_FAIL.getValue() + "目标文件不完整");
|
}
|
} else {
|
throw new BaseException(SaasCode.TENANT_APPLY_LICENSE_FILE_COPY_FAIL.getValue(), SaasCode.TENANT_APPLY_LICENSE_FILE_COPY_FAIL.getValue() + "目标文件不存在");
|
}
|
} catch (Exception e) {
|
throw new BaseException(SaasCode.TENANT_APPLY_LICENSE_FILE_COPY_FAIL.getValue(), SaasCode.TENANT_APPLY_LICENSE_FILE_COPY_FAIL.getValue() + e.getMessage());
|
}
|
}
|
}
|