如何发送邮箱、手机短信以及设置

1.邮件发送

1.1 邮件服务设置

1.1.1 方法一:通过yaml文件配置

pamirs:
  email:
    smtp:
      smtpHost: smtp.exmail.qq.com
      smtpUser: xxx@xxx.com
      smtpPassword: xxxxxx
      smtpPort: 465
      smtpSecurity: SSL
      #邮件模块可后续后台自行添加
      templates:
        - name: 邮箱注册邮件
          title: '${code}是你此次注册的验证码'
          body: '<div>Hi ${realname},</div><div>你正在使用验证码注册。</div>'

1.1.2 方法二:工程启动加入初始化设置方法

/**
     * 初始化邮件模板
     */
    private void initEmailTemplate(){
        EmailSenderSource emailSenderSource = new EmailSenderSource();
        emailSenderSource.setName("邮件发送服务");
        emailSenderSource.setType(MessageEngineTypeEnum.EMAIL_SEND);
        //优先级
        emailSenderSource.setSequence(10);
        //发送账号
        emailSenderSource.setSmtpUser("xxx@xxx.com");
        //发送密码
        emailSenderSource.setSmtpPassword("xxxxxx");
        //发送服务器地址和端口
        emailSenderSource.setSmtpHost("smtp.exmail.qq.com");
        emailSenderSource.setSmtpPort(465);
        //" None: SMTP 对话用明文完成。" +
        //" TLS (STARTTLS): SMTP对话的开始时要求TLS 加密 (建议)" +
        //" SSL/TLS: SMTP对话通过专用端口用 SSL/TLS 加密 (默认是: 465)")
        emailSenderSource.setSmtpSecurity(EmailSendSecurityEnum.SSL);
        emailSenderSource.setActive(true);
        emailSenderSource.createOrUpdate();

        List<EmailTemplate> templates = new ArrayList<>();
        templates.add(new EmailTemplate().setName("重置密码邮件模板").setTitle("请确认你的密码修改请求").setBody("<div>Hi ${realname},</div><div>你正在使用验证码注册。</div>").setModel(PamirsUser.MODEL_MODEL).setEmailSenderSource(emailSenderSource));
        new EmailTemplate().createOrUpdateBatch(templates);
    }

1.2 调用邮件发送组件发送邮件

/**
     * 代码中使用消息组件发送Email
     */
    public void sendEmailByTemplate(){
        try {
            EmailSender emailSender = (EmailSender) MessageEngine.get(MessageEngineTypeEnum.EMAIL_SEND).get(null);;
            EmailTemplate template = new EmailTemplate().setName("邮件模版名称").queryOne();
            //标题:${name}
            //内容:${fieldInt}次数
            String sendTo = "xxx@xxx.com";
            String copyTo = "yyy@yyy.com";

            Map<String, Object> objectData = new HashMap<>();
            objectData.put("name","张三");
            objectData.put("fieldInt",999);
            Boolean aBoolean = emailSender.send(template, objectData, sendTo, copyTo);
            if (null == aBoolean || !aBoolean) {
                log.error("发送邮件失败");
            }
        } catch (Exception e) {
            log.error("发送确认邮件失败:,异常:{}", e);
        }
    }

2.发送短信

2.1 短信通道设置

2.1.1 方法一:通过yaml文件配置

pamirs:
  sms:
    aliyun:
      signatureMethod: HMAC-SHA1
      endpoint: https://dysmsapi.aliyuncs.com
      version: '2017-05-25'
      accessKeyId: xxxxxxxxxxxxx
      signatureVersion: '1.0'
      accessKeySecret: xxxxxxxxxxxx
      regionId: cn-hangzhou
      timeZone: GMT
      signName: xxxxxx

2.1.2 方法二:工程启动加入初始化设置方法

private void initSmsConfig() {
        SmsChannelConfig smsChannelConfig = new SmsChannelConfig();
        SmsChannelConfig smsChannelConfigs = smsChannelConfig.setChannel(SMSChannelEnum.ALIYUN)
                .setAccessKeyId("xxxxxx")
                .setSignName("xxxxxx")
                .queryOne();
        if (null == smsChannelConfigs) {
            smsChannelConfig.setChannel(SMSChannelEnum.ALIYUN);
            smsChannelConfig.setType(MessageEngineTypeEnum.SMS_SEND);
            smsChannelConfig.setSignatureMethod("HMAC-SHA1");
            smsChannelConfig.setEndpoint("https://dysmsapi.aliyuncs.com");
            smsChannelConfig.setVersion("2017-05-25");
            smsChannelConfig.setAccessKeyId("xxxxxx");
            smsChannelConfig.setAccessKeySecret("xxxxxx");
            smsChannelConfig.setSignatureVersion("1.0");
            smsChannelConfig.setRegionId("cn-hangzhou");
            smsChannelConfig.setTimeZone("GMT");
            smsChannelConfig.setSignName("xxxxxx");
            smsChannelConfig.setActive(Boolean.TRUE);
            smsChannelConfig.create();
        } else {
            smsChannelConfigs.updateById();
        }

        //初始化短信模版,需要先到阿里云申请短信模版
        SmsTemplate smsTemplate = new SmsTemplate();
        smsTemplate.setChannel(SMSChannelEnum.ALIYUN);
        smsTemplate.setTemplateType(SMSTemplateTypeEnum.SIGN_IN);
        smsTemplate.setTemplateCode("SMS_252710149");//阿里云短信模版的Code
        smsTemplate.setTemplateContent("验证码: ${code},您正在登录。10分钟内有效,请注意保密,请勿向他人泄露您的验证码。");//阿里云短信模版

        List<SmsTemplate> smsTemplates = new ArrayList<>();
        smsTemplates.add(smsTemplate);
        new SmsTemplate().createOrUpdateBatch(smsTemplates);
    }

2.2 调用邮件发送组件发送邮件

public void sendSms(){
        try {

            List<String> receivePhoneNumbers = new ArrayList<>();
            receivePhoneNumbers.add("13800000000");
            // 占位符处理
            Map<String, String> vars = new HashMap<>();
            vars.put("code", "123456");

            SmsTemplate smsTemplate = new SmsTemplate().setChannel(SMSChannelEnum.ALIYUN);
            smsTemplate.setTemplateType(SMSTemplateTypeEnum.SIGN_IN);
            smsTemplate.setTemplateCode("SMS_252710149").queryOne();
            SMSSender smsSender = (SMSSender) MessageEngine.get(MessageEngineTypeEnum.SMS_SEND).get(null);
            receivePhoneNumbers.stream().distinct().forEach(it -> {
                try {
                    if (!smsSender.smsSend(smsTemplate, it, vars)) {
                        //todo 错误处理
                    }
                } catch (Exception e) {
                    //todo 错误处理
                }
            });
        } catch (Exception e) {
            //todo 错误处理
        }
    }

Oinone社区 作者:数式-海波原创文章,如若转载,请注明出处:https://doc.oinone.top/backend/4346.html

访问Oinone官网:https://www.oinone.top获取数式Oinone低代码应用平台体验

(0)
数式-海波的头像数式-海波数式管理员
上一篇 2023年11月6日 pm4:48
下一篇 2023年11月7日 am11:35

相关推荐

  • 平台配置日志输出和推送到APM与LogStash

    场景描述 目前设计器镜像启动后日志文件为out.log,是启动脚本中定向输出了(>>)out.log文件。实际项目可能: 日志输出到特定目录的特定文件名中 指定以日志保留策略(单个文件大小和文件保留个数) 日志输出到APM工具中(如skywalking) 日志推送到LogStash 日志自定义输出 不定向输出,采用自己配置的方式,与标准的SpringBoot工程配置日志一样。两种方式(都是Spring提供的方式): 方式一 bootstrap.yml 里面可以按profiles指定logback的配置文件,具体文件名和文件输入在logback里面进行配置,跟通用的logback配置一致. 例如: logging: config: classpath:logback-pre.xml 方式二 resources的根目录,直接配置 logback-spring.xml, 启动会自动加载。 日志自定义场景 配置日志推送到LogStash <!–配置日志推送到LogStash–> <contextListener class="pro.shushi.pamirs.demo.core.config.DemoLogbackFiledConfig"/> <appender name="LogStash" class="net.logstash.logback.appender.LogstashTcpSocketAppender"> <destination>127.0.0.1:4560</destination> <!– encoder必须配置,有多种可选 –> <encoder charset="UTF-8" class="net.logstash.logback.encoder.LogstashEncoder"> <!– SkyWalking插件, log加tid–> <provider class="org.apache.skywalking.apm.toolkit.log.logback.v1.x.logstash.TraceIdJsonProvider" /> <!–在生成的json中会加这些字段–> <customFields> {"app.name":"pamirs-demo", "app.type":"Microservice", "platform":"pamirs", "env":"dev"} </customFields> <timeZone>Asia/Shanghai</timeZone> <writeVersionAsInteger>true</writeVersionAsInteger> <providers> <pattern> <pattern> <!–动态的变量–> { "ip": "%{ip}", "server.name": "%{server.name}", "logger_name": "%logger" } </pattern> </pattern> </providers> </encoder> </appender> skywalking的日志rpc上传 <!– skywalking的日志rpc上传 –> <appender name="SkyWalkingLogs" class="org.apache.skywalking.apm.toolkit.log.logback.v1.x.log.GRPCLogClientAppender"> <encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder"> <layout class="org.apache.skywalking.apm.toolkit.log.logback.v1.x.mdc.TraceIdMDCPatternLogbackLayout"> <Pattern>${CONSOLE_LOG_PATTERN}</Pattern> </layout> </encoder> </appender> 完整的代码示例 Logback自定义字段 package pro.shushi.pamirs.demo.core.config; import ch.qos.logback.classic.Level; import ch.qos.logback.classic.Logger; import ch.qos.logback.classic.LoggerContext; import ch.qos.logback.classic.spi.LoggerContextListener; import ch.qos.logback.core.Context; import ch.qos.logback.core.spi.ContextAwareBase; import ch.qos.logback.core.spi.LifeCycle; import java.net.InetAddress; import java.net.UnknownHostException; /** * Logback自定义字段 * * @author wx@shushi.pro * @date 2024/4/17 */ public class DemoLogbackFiledConfig extends ContextAwareBase implements LoggerContextListener, LifeCycle { private boolean started = false; @Override public boolean isResetResistant() { return false; } @Override public void onStart(LoggerContext loggerContext) { } @Override public void onReset(LoggerContext loggerContext) { } @Override public void onStop(LoggerContext loggerContext) { } @Override public void onLevelChange(Logger logger, Level level) { } @Override public void start() { if (started) { return; } Context context = getContext();…

    2024年5月18日
    1.4K00
  • 工作流审核撤回/回退/拒绝/同意/反悔钩子使用

    目录 1. 流程撤回、拒绝和回退调用自定义函数1.1 工作流【撤销】回调钩子1.2 撤销【回退】回调钩子1.3 工作流【拒绝】回调钩子1.4 工作流【同意】回调钩子1.4 工作流【反悔】回调钩子1.4 回调钩子在业务系统中的调用示例2. 自定义审批方式、自定义审批节点名称 1.流程撤回、拒绝和回退调用自定义函数 1.1工作流【撤销】回调钩子 使用方式:把该方法放置到XXX模型的Action下面,或@Fun(XXX.MODEL_MODEL)触发方式:当流程实例被撤销时调用入口:pro.shushi.pamirs.workflow.app.core.service.impl.WorkflowInstanceServiceImpl#undoInstance /** * XXX为当前流程触发方式为模型触发时对应的触发模型、 * 对应返回不影响流程上下文 * @param data 入参为触发时的业务数据,数据的JsonString * @return */ @Function public XXX recall(String data) { // TODO: 根据实际的业务逻辑把data转换为对象 WorkRecord workRecord = JsonUtils.parseObject(data, new TypeReference<WorkRecord>(){}); // TODO: 增加自定义业务逻辑 return new XXX(); } 1.2撤销【回退】回调钩子 使用方式:把该方法放置到XXX模型的Action下面,或@Fun(XXX.MODEL_MODEL)触发方式:流程待办进行回退操作时调用入口:pro.shushi.pamirs.workflow.app.core.service.operator.ApprovalFallbackOperatorService /** * XXX为当前流程触发方式为模型触发时对应的触发模型 * 对应返回不影响流程上下文 * @param data 入参为触发时的业务数据,数据的JsonString * @return */ @Function public XXX fallBack(String data) { // TODO: 根据实际的业务逻辑把data转换为对象 WorkRecord workRecord = JsonUtils.parseObject(data, new TypeReference<WorkRecord>(){}); // TODO: 增加自定义业务逻辑 return new XXX(); } 1.3工作流【拒绝】回调钩子 使用方式:把该方法放置到XXX模型的Action下面,或@Fun(XXX.MODEL_MODEL)触发方式:流程待办进行拒绝操作时调用入口:pro.shushi.pamirs.workflow.app.core.service.operator.ApprovalFallbackOperatorService /** * XXX为当前流程触发方式为模型触发时对应的触发模型 * 对应返回不影响流程上下文 * @param data 入参为触发时的业务数据,数据的JsonString * @return */ @Function public XXX reject(String data) { // TODO: 根据实际的业务逻辑把data转换为对象 WorkRecord workRecord = JsonUtils.parseObject(data, new TypeReference<WorkRecord>(){}); // TODO: 增加自定义业务逻辑 return new XXX(); } 1.4 工作流【同意】回调钩子 使用方式:把该方法放置到XXX模型的Action下面,或@Fun(XXX.MODEL_MODEL)触发方式:流程待办进行同意操作时调用入口:pro.shushi.pamirs.workflow.app.core.util.ArtificialTaskUtils @Function(summary = "发起的审批同意时会自动调用此方法") @Function.Advanced(displayName = "审批同意") public Teacher agree(String data) { // TODO: 根据实际的业务逻辑把data转换为对象 // WorkRecord workRecord = JsonUtils.parseObject(data, new TypeReference<WorkRecord>(){}); // TODO: 增加自定义业务逻辑 return new Teacher(); } 1.4 工作流【反悔】回调钩子 使用方式:把该方法放置到XXX模型的Action下面,或@Fun(XXX.MODEL_MODEL)触发方式:流程待办进行反悔操作时使用场景:流程待办进行反悔操作时,需要额外更改其他的业务数据逻辑时可用该回调钩子。 注意:该函数的namespace需要设置为流程触发模型。 调用入口:pro.shushi.pamirs.workflow.app.core.service.operator.ArtificialRetractOperatorService @Function @Function.fun(WorkflowBizCallConstants.retract) public void retract(WorkflowUserTask workflowUserTask) { // 获取流程实例 workflowUserTask.fieldQuery(WorkflowUserTask::getInstance); WorkflowInstance instance = workflowUserTask.getInstance(); // 获取用户任务实例 WorkflowUserInstance userInstance = new WorkflowUserInstance() .setId(workflowUserTask.getWorkflowUserInstanceId()) .queryById(); // 反悔的用户id…

    2023年11月15日
    1.1K00
  • 【OceanBase】后端部署使用 OceanBase 数据库(海扬/OB)

    OceanBase 数据库配置 驱动配置 Maven配置(4.2.5.3版本可用) <oceanbase.version>2.4.14</oceanbase.version> <dependency> <groupId>com.oceanbase</groupId> <artifactId>oceanbase-client</artifactId> <version>${oceanbase.version}</version> </dependency> PS: oceanbase 驱动必须使用 2.4.5 版本或以上,低于此版本的驱动无法使用自增ID功能,无法正常启动。点击查看官方JDBC版本发布记录 JDBC连接配置 OceanBase – Oracle 版 pamirs: datasource: base: type: com.alibaba.druid.pool.DruidDataSource driverClassName: com.alipay.oceanbase.jdbc.Driver url: jdbc:oceanbase://10.xxx.xxx.xxx:1001/BASE?useServerPrepStmts=true&useOraclePrepareExecute=true&defaultFetchSize=4096 username: xxxxxx password: xxxxxx validConnectionCheckerClassName: com.alibaba.druid.pool.vendor.OracleValidConnectionChecker validationQuery: SELECT 1 FROM DUAL OceanBase – MySQL 版 pamirs: datasource: base: type: com.alibaba.druid.pool.DruidDataSource driverClassName: com.alipay.oceanbase.jdbc.Driver url: jdbc:oceanbase://10.xxx.xxx.xxx:1001/base username: xxxxxx password: xxxxxx 连接 URL 配置 点击查看官方JDBC连接配置说明 URL 格式(OceanBase – Oracle 版) jdbc:oceanbase://${host}:${port}/${database}?useServerPrepStmts=true&useOraclePrepareExecute=true&defaultFetchSize=4096 在jdbc连接配置时,useServerPrepStmts=true&useOraclePrepareExecute=true 必须配置,否则自增主键无法正常使用。 defaultFetchSize=4096 意味着在使用服务端预处理时,游标每次获取的结果集行数,驱动默认值为 10,在进行大量数据获取时会出现卡顿的现象,因此推荐使用 4096 作为其结果集大小。过大可能会导致 OOM,过小可能还是会出现卡顿,该值需要按实际情况进行配置。 其他连接参数如需配置,可自行查阅相关资料进行调优。 方言配置(OceanBase – Oracle 版) PS:OceanBase – MySQL 版无需配置方言,只需修改数据库连接即可正常使用。 pamirs方言配置 pamirs: dialect: ds: base: type: OceanBase version: 4.2.5.3 major-version: oracle-4.2 pamirs: type: OceanBase version: 4.2.5.3 major-version: oracle-4.2 plus: configuration: jdbc-type-for-null: "NULL" using-model-as-property: true using-statement-handler-dialect: true mapper: batch: collectionCommit default-batch-config: read: 500 write: 100 数据库版本 type version majorVersion 4.2.5.3 OceanBase 4.2.5.3 oracle-4.2 PS:由于方言开发环境为4.2.5.3版本,其他类似版本(4.x)原则上不会出现太大差异,如出现其他版本无法正常支持的,可在文档下方留言。 schedule方言配置 pamirs: event: enabled: true schedule: enabled: true dialect: type: Oracle version: 12.2 major-version: 12c type version majorVersion Oracle 12.2 12c PS:由于 schedule 的方言与 Oracle 数据库并无明显差异,OceanBase 数据库可以直接使用 Oracle 数据库方言。 其他配置(OceanBase – Oracle 版) 逻辑删除的值配置 pamirs: mapper: global: table-info: logic-delete-value: (CAST(SYSTIMESTAMP AS DATE) – TO_DATE('1970-01-01 08:00:00', 'YYYY-MM-DD HH24:MI:SS')) * 8640000000000

    2025年7月21日
    55100
  • Maven Setting 配置详解

    常用标签概览 servers/server:配置私有仓库用户名和密码进行认证,以 id 进行关联。 mirrors/mirror:配置镜像仓库拉取时的地址源和额外配置。 profiles/profile:配置多个可能使用的镜像仓库。 activeProfiles/activeProfile:配置默认激活的 profile,以 id 进行关联。 Oinone 私有仓库配置 以下配置可以在使用 Oinone 私有仓库的同时,也可以正常使用 aliyun 镜像源。 <servers> <server> <id>shushi</id> <username>${username}</username> <password>${password}</password> </server> </servers> <mirrors> <mirror> <id>shushi</id> <mirrorOf>shushi</mirrorOf> <url>http://ss.nexus.ixtx.fun/repository/public</url> <!– 忽略 https 认证,maven 版本过高时需要配置 –> <blocked>false</blocked> </mirror> </mirrors> <profiles> <profile> <id>shushi</id> <repositories> <repository> <!– 对应 server.id –> <id>shushi</id> <url>http://ss.nexus.ixtx.fun/repository/public</url> <releases> <enabled>true</enabled> </releases> <snapshots> <enabled>true</enabled> </snapshots> </repository> </repositories> <pluginRepositories> <pluginRepository> <!– 对应 server.id –> <id>shushi</id> <url>http://ss.nexus.ixtx.fun/repository/snapshots</url> <releases> <enabled>false</enabled> </releases> <snapshots> <enabled>true</enabled> </snapshots> </pluginRepository> </pluginRepositories> </profile> <profile> <id>aliyun</id> <repositories> <repository> <id>aliyun</id> <url>https://maven.aliyun.com/repository/public</url> <releases> <enabled>true</enabled> </releases> <snapshots> <enabled>false</enabled> </snapshots> </repository> </repositories> <pluginRepositories> <pluginRepository> <id>aliyun</id> <url>https://maven.aliyun.com/repository/public</url> <releases> <enabled>true</enabled> </releases> <snapshots> <enabled>false</enabled> </snapshots> </pluginRepository> </pluginRepositories> </profile> </profiles> <activeProfiles> <!– 使用 shushi 私有仓库 –> <activeProfile>shushi</activeProfile> <!– 使用 aliyun 镜像仓库 –> <activeProfile>aliyun</activeProfile> </activeProfiles> 常见问题 使用 mvn 时无法拉取 Oinone 最新版镜像,提示找不到对应的包 原因:在 Oinone 开源后,oinone-pamirs 内核相关包都被部署到 maven 中央仓库,但由于其他镜像仓库的同步存在延时,在未正确同步的其他镜像源拉取时会出现找不到对应的包相关异常。 解决方案:检查 mirrors 中是否配置了 aliyun 镜像源,如果配置了,使用上述 Oinone 私有仓库配置重新配置后,再进行拉取。这一问题是由于 mirrors 配置不当,拦截了所有从 maven 中央仓库拉取的地址替换为了 aliyun 镜像源导致的。

    2025年11月10日
    28400
  • docker status exited(255)

    虚拟机异常退出再启动后,docker run 出现错误: 查看所有容器发现确实存在一个容器,status是 exited(255) docker container ls -all 删除这个容器,命令 docker run 容器id docker rm 56e0  

    2024年11月23日
    71400

Leave a Reply

登录后才能评论