diff --git a/sms4j-comm/src/main/java/org/dromara/sms4j/comm/constant/Constant.java b/sms4j-comm/src/main/java/org/dromara/sms4j/comm/constant/Constant.java index 5963fa69..00dbea90 100644 --- a/sms4j-comm/src/main/java/org/dromara/sms4j/comm/constant/Constant.java +++ b/sms4j-comm/src/main/java/org/dromara/sms4j/comm/constant/Constant.java @@ -8,7 +8,9 @@ package org.dromara.sms4j.comm.constant; * 2023/3/31 19:33 **/ public abstract class Constant { - /** 项目版本号*/ + /** + * 项目版本号 + */ public static final String VERSION = "V 3.0.1"; /** @@ -37,7 +39,9 @@ public abstract class Constant { */ public static final String HUAWEI_JAVA_DATE = "yyyy-MM-dd'T'HH:mm:ss'Z'"; - /** 云片短信国内短信请求地址*/ + /** + * 云片短信国内短信请求地址 + */ public static final String YUNPIAN_URL = "https://sms.yunpian.com/v2"; /** @@ -50,6 +54,11 @@ public abstract class Constant { */ public static final String SUPPLIER_KEY = "supplier"; + /** + * 自定义实现工厂路径 + */ + public static final String FACTORY_PATH = "factory"; + private Constant() { } } diff --git a/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunApplication.java b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunApplication.java new file mode 100644 index 00000000..b49f75a7 --- /dev/null +++ b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunApplication.java @@ -0,0 +1,20 @@ +package org.dromara.sms4j.example.zhangjun; + +import org.dromara.sms4j.core.factory.SmsFactory; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +/** + * 自定义广州掌骏短信实现 + * + * @author 4n + */ +@SpringBootApplication +public class ZhangJunApplication { + + public static void main(String[] args) { + SpringApplication.run(ZhangJunApplication.class, args); + SmsFactory.getBySupplier("zhangjun").sendMessage("17679318598", "154468"); + } + +} diff --git a/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunConfig.java b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunConfig.java new file mode 100644 index 00000000..18106009 --- /dev/null +++ b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunConfig.java @@ -0,0 +1,23 @@ +package org.dromara.sms4j.example.zhangjun; + +import lombok.Data; +import lombok.EqualsAndHashCode; +import org.dromara.sms4j.comm.constant.SupplierConstant; +import org.dromara.sms4j.provider.config.BaseConfig; + +/** + * @author 4n + */ +@EqualsAndHashCode(callSuper = true) +@Data +public class ZhangJunConfig extends BaseConfig { + private String appId; + private String sid; + private String url; + + @Override + public String getSupplier() { + return "zhangjun"; + } + +} diff --git a/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunFactory.java b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunFactory.java new file mode 100644 index 00000000..51c5ef13 --- /dev/null +++ b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunFactory.java @@ -0,0 +1,27 @@ +package org.dromara.sms4j.example.zhangjun; + +import lombok.AccessLevel; +import lombok.NoArgsConstructor; +import org.dromara.sms4j.provider.factory.AbstractProviderFactory; + +/** + * + *

掌骏短信 + * + * @author :4n + * 2023/10/31 14:54 + **/ +@NoArgsConstructor +public class ZhangJunFactory extends AbstractProviderFactory { + + @Override + public ZhangJunSmsImpl createSms(ZhangJunConfig ZhangJunConfig) { + return new ZhangJunSmsImpl(ZhangJunConfig); + } + + @Override + public String getSupplier() { + return "zhangjun"; + } + +} diff --git a/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunSmsImpl.java b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunSmsImpl.java new file mode 100644 index 00000000..f65eaff9 --- /dev/null +++ b/sms4j-spring-boot-example/src/main/java/org/dromara/sms4j/example/zhangjun/ZhangJunSmsImpl.java @@ -0,0 +1,111 @@ +package org.dromara.sms4j.example.zhangjun; + +import cn.hutool.json.JSONObject; +import cn.hutool.json.JSONUtil; +import lombok.extern.slf4j.Slf4j; +import org.dromara.sms4j.api.entity.SmsResponse; +import org.dromara.sms4j.comm.delayedTime.DelayedTime; +import org.dromara.sms4j.comm.exception.SmsBlendException; +import org.dromara.sms4j.comm.utils.SmsUtils; +import org.dromara.sms4j.provider.service.AbstractSmsBlend; + +import java.util.HashMap; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.Executor; + +/** + * @author :4n + **/ +@Slf4j +public class ZhangJunSmsImpl extends AbstractSmsBlend { + + private int retry = 0; + + /** + * ZhangJunSmsImpl + *

构造器,用于构造短信实现模块 + * + * @author :Wind + */ + public ZhangJunSmsImpl(ZhangJunConfig config, Executor pool, DelayedTime delayedTime) { + super(config, pool, delayedTime); + } + + /** + * ZhangJunSmsImpl + *

构造器,用于构造短信实现模块 + */ + public ZhangJunSmsImpl(ZhangJunConfig config) { + super(config); + } + + @Override + public String getSupplier() { + return "zhangjun"; + } + private LinkedHashMap buildBody(String phone, String message){ + LinkedHashMap map = new LinkedHashMap<>(); + map.put("appId", getConfig().getAppId()); + map.put("sid", getConfig().getSid()); + map.put("templateId", getConfig().getTemplateId()); + map.put("phone", phone); + Map data = new HashMap<>(); + data.put("code", message); + map.put("data", JSONUtil.toJsonStr(data)); + return map; + } + @Override + public SmsResponse sendMessage(String phone, String message) { + return sendMessage(phone, getConfig().getTemplateId(), buildBody(phone,message)); + } + + @Override + public SmsResponse sendMessage(String phone, String templateId, LinkedHashMap messages) { + String messageStr = JSONUtil.toJsonStr(messages); + return getSmsResponse(phone, messageStr, templateId); + } + + @Override + public SmsResponse massTexting(List phones, String message) { + LinkedHashMap map = new LinkedHashMap<>(); +// map.put(getConfig().getTemplateName(), message); + return massTexting(phones, getConfig().getTemplateId(), map); + } + + @Override + public SmsResponse massTexting(List phones, String templateId, LinkedHashMap messages) { + String messageStr = JSONUtil.toJsonStr(messages); + return getSmsResponse(SmsUtils.arrayToString(phones), messageStr, templateId); + } + + private SmsResponse getSmsResponse(String phone, String message, String templateId) { + try { + SmsResponse smsResponse = getResponse(http.postJson(getConfig().getUrl(), null, message)); + if(smsResponse.isSuccess() || retry == getConfig().getMaxRetries()){ + retry = 0; + return smsResponse; + } + return requestRetry(phone, message, templateId); + }catch (SmsBlendException e){ + return requestRetry(phone, message, templateId); + } + } + + private SmsResponse requestRetry(String phone, String message, String templateId) { + http.safeSleep(getConfig().getRetryInterval()); + retry++; + log.warn("短信第 {" + retry + "} 次重新发送"); + return getSmsResponse(phone, message, templateId); + } + + private SmsResponse getResponse(JSONObject resJson) { + SmsResponse smsResponse = new SmsResponse(); + smsResponse.setSuccess("OK".equals(resJson.getStr("Code"))); + smsResponse.setData(resJson); + smsResponse.setConfigId(getConfigId()); + return smsResponse; + } + +} \ No newline at end of file diff --git a/sms4j-spring-boot-example/src/main/resources/application.yml b/sms4j-spring-boot-example/src/main/resources/application.yml index fc1c106e..b9aecd22 100644 --- a/sms4j-spring-boot-example/src/main/resources/application.yml +++ b/sms4j-spring-boot-example/src/main/resources/application.yml @@ -73,4 +73,12 @@ sms: base-url: https://app.cloopen.com:8883/2013-12-26 access-key-id: 你的Access Key access-key-secret: 你的Access Key Secret - sdkAppId: 你的应用ID \ No newline at end of file + sdkAppId: 你的应用ID + #自定义广州掌骏短信,添加factory全路径。config,factory,SmsImpl复制其他默认实现即可,修改对应的supplier和发送核心逻辑即可 + zhangjun: + supplier: zhangjun + factory: org.dromara.sms4j.example.zhangjun.ZhangJunFactory + templateId: d2a****777 + appId: 64c52d2a****77775fe72e3 + sid: d2a****777 + url: https://sms.idowe.com/**/**/**/send \ No newline at end of file diff --git a/sms4j-spring-boot-starter/src/main/java/org/dromara/sms4j/starter/config/SupplierConfig.java b/sms4j-spring-boot-starter/src/main/java/org/dromara/sms4j/starter/config/SupplierConfig.java index a6a05886..567778d8 100644 --- a/sms4j-spring-boot-starter/src/main/java/org/dromara/sms4j/starter/config/SupplierConfig.java +++ b/sms4j-spring-boot-starter/src/main/java/org/dromara/sms4j/starter/config/SupplierConfig.java @@ -1,12 +1,18 @@ package org.dromara.sms4j.starter.config; +import cn.hutool.core.util.ObjectUtil; +import lombok.SneakyThrows; import org.dromara.sms4j.api.SmsBlend; +import org.dromara.sms4j.comm.constant.Constant; +import org.dromara.sms4j.comm.enumerate.ConfigType; import org.dromara.sms4j.provider.config.SmsConfig; import org.dromara.sms4j.provider.factory.BaseProviderFactory; +import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.context.annotation.Bean; +import java.util.ArrayList; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; @@ -23,6 +29,26 @@ public class SupplierConfig { return new LinkedHashMap<>(); } + @Bean + @ConditionalOnBean({SmsConfig.class}) + @SneakyThrows + protected List> factoryList(Map> blends, SmsConfig smsConfig) { + //注入自定义实现工厂 + List> factoryList = new ArrayList<>(); + if (ConfigType.YAML.equals(smsConfig.getConfigType())) { + for (String configId : blends.keySet()) { + Map configMap = blends.get(configId); + Object factoryPath = configMap.get(Constant.FACTORY_PATH); + if (ObjectUtil.isNotEmpty(factoryPath)) { + //反射创建实例 + Class> newClass = (Class>) Class.forName(factoryPath.toString()); + BaseProviderFactory factory = newClass.newInstance(); + factoryList.add(factory); + } + } + } + return factoryList; + } @Bean protected SmsBlendsInitializer smsBlendsInitializer(List> factoryList,