package jnpf.dmsService;
|
|
import jnpf.base.UserInfo;
|
import jnpf.dmsEntity.DmsWenjianXinzengShenheEntity;
|
import jnpf.dmsEntity.DmsWenjianXiudingShenheEntity;
|
import jnpf.dmsEntity.permission.entity.DmsFileVersionEntity;
|
import jnpf.dmsEntity.permission.enums.DmsPermissionAction;
|
import jnpf.dmsEntity.permission.enums.DmsResourceType;
|
import jnpf.dmsEntity.storage.form.DmsWorkflowFilePrepareForm;
|
import jnpf.dmsEntity.storage.DmsWorkflowSourceKey;
|
import jnpf.dmsEntity.storage.enums.DmsWorkflowFileType;
|
import jnpf.dmsEntity.storage.vo.DmsFileUploadVO;
|
import jnpf.dmsEntity.storage.vo.DmsWorkflowFilePrepareVO;
|
import jnpf.dmsMapper.DmsFileObjectMapper;
|
import jnpf.dmsMapper.DmsFileVersionMapper;
|
import jnpf.dmsMapper.DmsWenjianXinzengShenheMapper;
|
import jnpf.dmsMapper.DmsWenjianXiudingShenheMapper;
|
import jnpf.dmsPermission.DmsCurrentIdentity;
|
import jnpf.dmsPermission.DmsPermissionError;
|
import jnpf.dmsPermission.DmsPermissionException;
|
import jnpf.exception.DataException;
|
import lombok.RequiredArgsConstructor;
|
import org.springframework.stereotype.Service;
|
import org.springframework.transaction.annotation.Transactional;
|
|
import java.util.List;
|
import java.util.Locale;
|
import java.util.Objects;
|
import java.util.UUID;
|
|
@Service
|
@RequiredArgsConstructor
|
public class DmsWorkflowFilePrepareService {
|
private static final int TO_BE_SUBMIT = 0;
|
private static final int RUNNING = 1;
|
|
private final DmsCurrentIdentity currentIdentity;
|
private final DmsPermissionDecisionService decisionService;
|
private final DmsWenjianXinzengShenheMapper newAuditMapper;
|
private final DmsWenjianXiudingShenheMapper revisionAuditMapper;
|
private final DmsFileVersionMapper fileVersionMapper;
|
private final DmsFileObjectMapper fileObjectMapper;
|
private final DmsWorkflowApprovalValidator approvalValidator;
|
|
@Transactional
|
public DmsWorkflowFilePrepareVO prepare(DmsWorkflowFilePrepareForm form, String serviceId) {
|
UserInfo user = currentIdentity.requireUser();
|
String tenantId = currentIdentity.tenantId(user);
|
String sourceId = form.getSourceId().trim();
|
String taskId = form.getTaskId().trim();
|
String sourceKey = DmsWorkflowSourceKey.of(sourceId, taskId, form.getFileType());
|
|
if (form.getFileType() == DmsWorkflowFileType.CREATE) {
|
DmsWenjianXinzengShenheEntity audit = requireStageableNewAudit(tenantId, sourceId, taskId);
|
requireNoLegacyRegistration(tenantId, serviceId, sourceId);
|
DmsWorkflowFilePrepareVO result = new DmsWorkflowFilePrepareVO();
|
result.setSourceKey(sourceKey);
|
result.setApprovedFileJson(approvalValidator.validateNew(audit, form));
|
result.setVersionLabel("D(00)");
|
return result;
|
}
|
|
DmsWenjianXiudingShenheEntity audit = requireStageableRevisionAudit(tenantId, sourceId, taskId);
|
UUID baseVersionId = form.getVersionId();
|
if (baseVersionId == null) {
|
throw new DataException("修订文件时versionId不能为空");
|
}
|
String approvedFile = approvalValidator.validateRevision(tenantId, audit, form);
|
requireNoLegacyRegistration(tenantId, serviceId, sourceId);
|
DmsFileUploadVO existing = fileObjectMapper.selectUploadBySource(
|
tenantId, serviceId, sourceKey);
|
if (existing != null) {
|
if (!Objects.equals(existing.getBaseFileVersionId(), baseVersionId)) {
|
throw DmsPermissionException.of(DmsPermissionError.IDEMPOTENCY_CONFLICT,
|
"source_id已用于另一个文件版本的修订");
|
}
|
decisionService.requireAllowed(DmsResourceType.DOCUMENT, existing.getDocumentId(),
|
DmsPermissionAction.UPDATE);
|
DmsWorkflowFilePrepareVO result = new DmsWorkflowFilePrepareVO();
|
result.setSourceKey(sourceKey);
|
result.setApprovedFileJson(approvedFile);
|
result.setDocumentId(existing.getDocumentId());
|
result.setVersionLabel(existing.getVersionLabel());
|
result.setRevisionReason(existing.getRevisionReason());
|
return result;
|
}
|
DmsFileVersionEntity baseVersion = fileVersionMapper.selectByTenantAndId(
|
tenantId, baseVersionId);
|
if (baseVersion == null) {
|
throw DmsPermissionException.of(DmsPermissionError.RESOURCE_NOT_FOUND,
|
"待修订文件版本不存在");
|
}
|
UUID documentId = baseVersion.getDocumentId();
|
decisionService.requireAllowed(DmsResourceType.DOCUMENT, documentId,
|
DmsPermissionAction.UPDATE);
|
DmsFileVersionEntity current = fileVersionMapper.selectCurrentEffective(
|
tenantId, documentId);
|
if (current == null || !Objects.equals(current.getId(), baseVersionId)) {
|
throw DmsPermissionException.of(DmsPermissionError.REVISION_CONFLICT,
|
"待修订版本已不是现行有效版本,请刷新后重试");
|
}
|
|
long nextVersionNo = fileVersionMapper.selectNextVersionNo(tenantId, documentId);
|
DmsWorkflowFilePrepareVO result = new DmsWorkflowFilePrepareVO();
|
result.setSourceKey(sourceKey);
|
result.setApprovedFileJson(approvedFile);
|
result.setDocumentId(documentId);
|
result.setVersionLabel(String.format(Locale.ROOT, "D(%02d)", nextVersionNo - 1));
|
result.setRevisionReason("工作流审核通过");
|
return result;
|
}
|
|
private DmsWenjianXinzengShenheEntity requireStageableNewAudit(String tenantId, String sourceId, String taskId) {
|
List<DmsWenjianXinzengShenheEntity> rows =
|
newAuditMapper.selectByFlowForUpdate(tenantId, sourceId, taskId);
|
DmsWenjianXinzengShenheEntity audit = requireUnique(rows, "文件新增审核单");
|
requireStageable(audit.getFlowState(), sourceId, taskId);
|
return audit;
|
}
|
|
private DmsWenjianXiudingShenheEntity requireStageableRevisionAudit(String tenantId, String sourceId, String taskId) {
|
List<DmsWenjianXiudingShenheEntity> rows =
|
revisionAuditMapper.selectByFlowForUpdate(tenantId, sourceId, taskId);
|
DmsWenjianXiudingShenheEntity audit = requireUnique(rows, "文件修订审核单");
|
requireStageable(audit.getFlowState(), sourceId, taskId);
|
return audit;
|
}
|
|
private <T> T requireUnique(List<T> rows, String label) {
|
if (rows == null || rows.isEmpty()) {
|
throw new DataException("未找到与sourceId、taskId匹配的" + label);
|
}
|
if (rows.size() != 1) {
|
throw new DataException("sourceId、taskId匹配到多条" + label);
|
}
|
return rows.get(0);
|
}
|
|
private void requireStageable(Integer state, String sourceId, String taskId) {
|
if (!Integer.valueOf(TO_BE_SUBMIT).equals(state)
|
&& !Integer.valueOf(RUNNING).equals(state)) {
|
throw new DataException("文件流程不处于待提交或审批中,不能登记待生效文件:"
|
+ sourceId + "/" + taskId);
|
}
|
}
|
|
private void requireNoLegacyRegistration(String tenantId, String serviceId, String flowId) {
|
if (fileObjectMapper.selectUploadBySource(tenantId, serviceId, flowId) != null) {
|
throw new DataException("该flowID存在旧版登记记录,缺少任务归属,请核对迁移后重试");
|
}
|
}
|
}
|