package com.ruoyi.other.service.impl; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.ruoyi.other.api.domain.TCompanyBalanceWarning; import com.ruoyi.other.api.domain.TGroupCompany; import com.ruoyi.other.api.dto.BalanceWarningDTO; import com.ruoyi.other.mapper.TCompanyBalanceWarningMapper; import com.ruoyi.other.mapper.TGroupCompanyMapper; import com.ruoyi.other.service.TCompanyBalanceWarningService; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import javax.annotation.Resource; import java.math.BigDecimal; import java.math.RoundingMode; /** *

* 公司余额预警配置 服务实现类 *

* * @author mxcd * @since 2026-09-26 */ @Service public class TCompanyBalanceWarningServiceImpl extends ServiceImpl implements TCompanyBalanceWarningService { /** 通知对象:集团联系人 */ private static final int NOTIFY_OBJECT_GROUP_CONTACT = 1; /** 通知对象:公司联系人 */ private static final int NOTIFY_OBJECT_COMPANY_CONTACT = 2; /** 通知方式:短信 */ private static final int NOTIFY_TYPE_SMS = 1; /** 预警线金额上限(与前端 InputNumber 上限保持一致) */ private static final BigDecimal MAX_WARN_AMOUNT = new BigDecimal("99999999.99"); /** 账户模式:共享模式(公司下无子账户,子账户预警线不适用) */ private static final int ACCOUNT_MODE_SHARED = 1; /** 公司 Mapper(校验配置所属公司是否存在、详情返回账户模式) */ @Resource private TGroupCompanyMapper groupCompanyMapper; @Override public BalanceWarningDTO getBalanceWarning(Integer companyId) { if (companyId == null) { return null; } BalanceWarningDTO dto = new BalanceWarningDTO(); dto.setCompanyId(companyId); // 未配置时仅返回公司账户模式,预警字段保持为空,由前端置默认值 TCompanyBalanceWarning entity = getByCompanyId(companyId); if (entity != null) { dto.setCompanyWarnAmount(entity.getCompanyWarnAmount()); dto.setSubWarnAmount(entity.getSubWarnAmount()); dto.setNotifyObject(defaultIfNull(entity.getNotifyObject(), NOTIFY_OBJECT_GROUP_CONTACT)); dto.setNotifyType(defaultIfNull(entity.getNotifyType(), NOTIFY_TYPE_SMS)); } TGroupCompany company = groupCompanyMapper.selectById(companyId); Integer accountMode = company == null ? null : company.getAccountMode(); dto.setAccountMode(accountMode); // 共享模式下公司无子账户,子账户预警线不适用,不回显历史值 if (isSharedMode(accountMode)) { dto.setSubWarnAmount(null); } return dto; } @Override @Transactional(rollbackFor = Exception.class) public Integer saveBalanceWarning(BalanceWarningDTO dto) { if (dto == null || dto.getCompanyId() == null) { throw new IllegalArgumentException("配置所属公司不能为空"); } TGroupCompany company = groupCompanyMapper.selectById(dto.getCompanyId()); if (company == null) { throw new IllegalArgumentException("公司不存在"); } // 校验并规范化各配置项(不合法直接抛出业务提示) BigDecimal companyWarnAmount = normalizeWarnAmount(dto.getCompanyWarnAmount(), "公司预警线"); // 共享模式无子账户:忽略传入值并落库为空;分配模式(及其他模式)子账户预警线仍必填 BigDecimal subWarnAmount = isSharedMode(company.getAccountMode()) ? null : normalizeWarnAmount(dto.getSubWarnAmount(), "子账户预警线"); Integer notifyObject = normalizeNotifyObject(dto.getNotifyObject()); Integer notifyType = normalizeNotifyType(dto.getNotifyType()); // 一个公司一条配置:存在则覆盖,不存在则新增 TCompanyBalanceWarning entity = getByCompanyId(dto.getCompanyId()); if (entity == null) { entity = new TCompanyBalanceWarning(); entity.setCompanyId(dto.getCompanyId()); entity.setDelFlag(false); } entity.setCompanyWarnAmount(companyWarnAmount); entity.setSubWarnAmount(subWarnAmount); entity.setNotifyObject(notifyObject); entity.setNotifyType(notifyType); saveOrUpdate(entity); return entity.getId(); } /** * 按公司查询配置(唯一索引保障最多一条,多余数据取首条不抛异常) */ private TCompanyBalanceWarning getByCompanyId(Integer companyId) { return getOne(Wrappers.lambdaQuery() .eq(TCompanyBalanceWarning::getCompanyId, companyId), false); } /** * 是否为共享模式(账户模式为 1;为空或未知模式按非共享处理,子账户预警线仍必填) */ private boolean isSharedMode(Integer accountMode) { return accountMode != null && accountMode == ACCOUNT_MODE_SHARED; } /** * 校验并规范化预警线金额(必填,0~99999999.99,统一保留2位小数) */ private BigDecimal normalizeWarnAmount(BigDecimal amount, String label) { if (amount == null) { throw new IllegalArgumentException("请输入" + label); } if (amount.compareTo(BigDecimal.ZERO) < 0 || amount.compareTo(MAX_WARN_AMOUNT) > 0) { throw new IllegalArgumentException(label + "需在0~" + MAX_WARN_AMOUNT + "之间"); } return amount.setScale(2, RoundingMode.HALF_UP); } /** * 校验通知对象(必填,1=集团联系人,2=公司联系人) */ private Integer normalizeNotifyObject(Integer notifyObject) { if (notifyObject == null) { throw new IllegalArgumentException("请选择通知对象"); } if (notifyObject != NOTIFY_OBJECT_GROUP_CONTACT && notifyObject != NOTIFY_OBJECT_COMPANY_CONTACT) { throw new IllegalArgumentException("通知对象不合法"); } return notifyObject; } /** * 校验通知方式(当前仅支持短信,为空时默认短信) */ private Integer normalizeNotifyType(Integer notifyType) { if (notifyType == null) { return NOTIFY_TYPE_SMS; } if (notifyType != NOTIFY_TYPE_SMS) { throw new IllegalArgumentException("通知方式不合法"); } return notifyType; } /** * 空值兜底(历史数据未写入通知项时按默认值返回) */ private Integer defaultIfNull(Integer value, int defaultValue) { return value == null ? defaultValue : value; } }