package com.ruoyi.message.sms.provider.ls; import com.alibaba.fastjson2.JSON; import com.google.gson.Gson; import com.ruoyi.common.utils.OkHttpExample; import com.ruoyi.common.utils.uuid.IdUtils; import com.ruoyi.message.MessageChannel; import com.ruoyi.message.SendResult; import com.ruoyi.message.sms.AbstractSmsSender; import com.ruoyi.message.sms.SmsSendRequest; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; import org.springframework.beans.factory.ObjectProvider; import org.springframework.stereotype.Component; import java.text.SimpleDateFormat; import java.util.Date; import java.util.LinkedHashMap; import java.util.Map; /** * 丽水短信发送方({@code ls} 通道,丽水 13 家医院)。 *

* 对接特征(与其他通道差异最大的一个): *

* 代码来源:{@code RyTask.ls 分支} + {@code RyTask.getDXCode}(行为保持不变)。 */ @Slf4j @Component public class LishuiSmsSender extends AbstractSmsSender { /** * 渠道 key,与 {@code spring.profiles.active=ls} 对应 */ public static final String KEY = "ls"; private final ObjectProvider configProvider; public LishuiSmsSender(ObjectProvider configProvider) { this.configProvider = configProvider; } @Override public String key() { return KEY; } @Override public String description() { return "丽水短信(13家医院,token + 机构级配置)"; } @Override protected SendResult doSend(SmsSendRequest request) throws Exception { LishuiMessageConfig config = resolveConfig(request.getOrgid()); if (config == null || StringUtils.isEmpty(config.getAddress())) { //与线上行为一致:该机构没有配置短信地址,视为发送失败 return SendResult.fail(KEY, MessageChannel.SMS, "短信发送失败,该机构没有配置短信地址", null); } String token = resolveToken(request.getOrgid(), config); Map body = buildBody(request, config); log.info("【{}】丽水短信发送,地址:{},参数:{},机构ID:{}", KEY, config.getAddress(), request, request.getOrgid()); String result = OkHttpExample.sendPostRequest(config.getAddress(), new Gson().toJson(body), token); log.info("【{}】丽水短信发送结果:{}", KEY, result); if (StringUtils.isEmpty(result)) { return SendResult.fail(KEY, MessageChannel.SMS, "短信发送失败", result); } Map textParam = JSON.parseObject(result, Map.class); Object codeObj = textParam == null ? null : textParam.get("Code"); String code = codeObj == null ? null : codeObj.toString(); if ("0".equals(code)) { return SendResult.success(KEY, MessageChannel.SMS, result).withCode(code); } return SendResult.fail(KEY, MessageChannel.SMS, "短信发送失败", result).withCode(code); } /** * 优先使用业务模块注册的 {@link LishuiMessageConfigProvider}(查 sys_config), * 否则退化为代码内静态配置。 */ private LishuiMessageConfig resolveConfig(String orgid) { LishuiMessageConfigProvider provider = configProvider.getIfAvailable(); if (provider != null) { LishuiMessageConfig config = provider.getConfig(orgid); if (config != null) { if (StringUtils.isEmpty(config.getOrgid())) { config.setOrgid(orgid); } return config; } } LishuiMessageConfig fallback = LishuiStaticConfig.fallback(orgid); return fallback; } private String resolveToken(String orgid, LishuiMessageConfig config) { if (StringUtils.isEmpty(config.getTokenUrl())) { return null; } LishuiMessageConfigProvider provider = configProvider.getIfAvailable(); if (provider == null) { log.warn("【{}】未找到 LishuiMessageConfigProvider 实现,无法换取 token,将以空 token 调用", KEY); return null; } return provider.getToken(orgid, config.getTokenUrl()); } /** * 组装丽水报文:{@code XiaoXiTou + YeWuXX.DuanXinXX}(与 {@code RyTask.getDXCode} 完全一致) */ private Map buildBody(SmsSendRequest request, LishuiMessageConfig config) { Map headerMap = new LinkedHashMap<>(); SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); headerMap.put("XiaoXiID", IdUtils.simpleUUID()); headerMap.put("FaSongSJ", sdf.format(new Date())); headerMap.put("ZuHuID", config.getZuHuId()); headerMap.put("ZuHuMC", config.getZuHuMc()); headerMap.put("FaSongJGID", config.getOrgid()); headerMap.put("FaSongJGMC", config.getZuHuMc()); headerMap.put("FaSongXTJC", "SUIFANGXT"); headerMap.put("FaSongXTMC", "随访系统"); headerMap.put("FaSongFCSJC", "ZJHES"); headerMap.put("XiaoXiLX", "FZ_PT_DuanXinFS"); headerMap.put("XiaoXiMC", "短信发送"); Map duanXinXX = new LinkedHashMap<>(); duanXinXX.put("ShouJiHM", request.getPhone()); duanXinXX.put("FaSongNR", request.getContent()); duanXinXX.put("FaSongRID", config.getSendPersonId()); duanXinXX.put("FaSongRXM", config.getSendPersonName()); Map yeWuXX = new LinkedHashMap<>(); yeWuXX.put("DuanXinXX", duanXinXX); Map body = new LinkedHashMap<>(); body.put("XiaoXiTou", headerMap); body.put("YeWuXX", yeWuXX); return body; } }