package jnpf.dmsService.expiry; import jnpf.dmsEntity.storage.expiry.DmsFileExpiryResource; import jnpf.dmsMapper.DmsFileExpiryMapper; import jnpf.dmsMapper.DmsFileExpiryProjectionMapper; import jnpf.exception.DataException; import lombok.RequiredArgsConstructor; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Propagation; import org.springframework.transaction.annotation.Transactional; import java.util.Date; import java.util.List; import java.util.UUID; @Service @RequiredArgsConstructor public class DmsFileExpiryProjection { private final DmsFileExpiryProjectionMapper resources; private final DmsFileExpiryMapper expiry; /** The lifecycle caller owns the document lock and transaction, including this durable outbox. */ @Transactional(propagation = Propagation.MANDATORY) public void apply(String tenantId, UUID versionId, Date effectiveTo, String actor) { if (resources.hasPendingProjection(tenantId, versionId)) { throw new DataException("批准文件尚未完成业务回写,到期结算等待原任务补偿完成"); } List matches = resources.lockResources(tenantId, versionId); if (matches.size() > 1) throw new DataException("到期版本映射了多个当前业务资源,需人工核对"); if (!matches.isEmpty()) { DmsFileExpiryResource resource = matches.get(0); if (!versionId.toString().equals(resource.getCenterVersionId()) || !versionId.toString().equals(resource.getVersionCenterId())) { throw new DataException("到期版本与业务当前版本映射不一致,需人工核对"); } if (!("effective".equals(resource.getBizStatus()) || ("disabled".equals(resource.getBizStatus()) && "yidaoqi".equals(resource.getDisabledSource())))) { throw new DataException("业务资源已由其他原因停用或转历史,不覆盖原状态"); } if (resources.disable(tenantId, resource, effectiveTo, actor) != 1) { throw new DataException("到期业务资源已变化,请重试"); } if (resources.expireBusinessVersion(tenantId, resource, actor) != 1) { throw new DataException("到期业务版本状态或映射已变化,请重试"); } resources.closeRelations(tenantId, resource.getId(), effectiveTo, actor); } // Center-only uploads and historical versions still require index cleanup. expiry.enqueueCleanup(tenantId, versionId); } }