前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Blog接入腾讯云短信

Blog接入腾讯云短信

作者头像
姜同学
发布2022-10-27 17:00:10
7.4K0
发布2022-10-27 17:00:10
举报
文章被收录于专栏:姜同学姜同学

这个网站搭建也快有两年了,这两年虽然没有什么产出,但是经过两年的积累也算是收益颇丰。因为一开始只是打算用来做一些笔记,并没有考虑网站本身的交互性,评论几乎都是置之不理,前几天突然心血来潮查了一下评论表,居然收获了上百条的评论,然而这些评论中的绝大多数我都是第一次见,其中不乏一些加油以及对知识点提出疑问的评论,我要在这里向留下评论的你们表示感谢。但是光是感谢是不够的,我要提高网站的交互性,对于这些评论我要第一时间知道,如何第一时间知道?想必脑海中冒出来的第一个念头就是短信了吧,打开腾讯云搜索短信,我又打开了一片新世界。

腾讯云短信平台

短信签名和短信模板被驳回了2次。。。我也是醉了,不过结果还好审核通过了,并发现了一个小惊喜,腾讯云个人认证账户每个月可以白嫖100条的免费短信,very good.点开开发者指南去学习如何引入SDK发短信就好啦,中文的文档不会还有人看不懂吧,不会吧不会吧。。

引入SDK 腾讯云短信接入文档 我把文档看完了,在这里做个小总结,首先你需要把SDK的依赖引入到工程的POM中,想要发短信的话还需要实例化一个认证对象,入参需要传入腾讯云账户密钥对 secretId 和 secretKey: 还需要实例化一个发短信的客户端:

最后还需要将短信的详细信息封装到一个对象中

最后使用短信客户端把短信的详细信息发送出去就好了吧,就这样**client.SendSms(req)**嗖的一下就发出去了。

引入依赖

代码语言:javascript
复制
<!-- https://mvnrepository.com/artifact/com.tencentcloudapi/tencentcloud-sdk-java -->
<dependency>
	<groupId>com.tencentcloudapi</groupId>
	<artifactId>tencentcloud-sdk-java</artifactId>
	<version>4.0.11</version>
</dependency>

创建对象

emm,认证对象只要传入两个固定的参数就好啦非常ESAY,所以就把他交给Spring管理就好啦,这个客户端对象一个系统也有一个就可以啦,那就单例模式搞一个,emm~~短信对象创建起来有点复杂,而且要根据不同的评论进行定制,所以工厂模式安排!

注入IOC容器
代码语言:javascript
复制
package com.jmy.config;

import com.jmy.factory.SmsClientBeanFactory;
import com.jmy.util.SmsUtils;
import com.tencentcloudapi.common.Credential;
import com.tencentcloudapi.sms.v20190711.SmsClient;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class SmsConfig {

    @Bean
    public Credential credential(){
        return new Credential(SmsUtils.SECRETID, SmsUtils.SECRETKEY);
    }

    @Bean
    public SmsClient smsClient(Credential credential){
        return SmsClientBeanFactory.getSmsClientInstance(credential);
    }

}

单例模式创建SmsClient
代码语言:javascript
复制
package com.jmy.config;

import com.jmy.factory.SmsClientBeanFactory;
import com.jmy.util.SmsUtils;
import com.tencentcloudapi.common.Credential;
import com.tencentcloudapi.sms.v20190711.SmsClient;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class SmsConfig {

    @Bean
    public Credential credential(){
        return new Credential(SmsUtils.SECRETID, SmsUtils.SECRETKEY);
    }

    @Bean
    public SmsClient smsClient(Credential credential){
        return SmsClientBeanFactory.getSmsClientInstance(credential);
    }

}
工厂模式创建SendSmsRequestBeanFactory
代码语言:javascript
复制
package com.jmy.factory;

import com.jmy.util.SmsUtils;
import com.tencentcloudapi.sms.v20190711.models.SendSmsRequest;

public class SendSmsRequestBeanFactory{

    public static SendSmsRequest getInstance() {
        SendSmsRequest req = new SendSmsRequest();
        req.setSmsSdkAppid(SmsUtils.APPID);
        req.setSign(SmsUtils.SIGN);
        req.setSenderId(SmsUtils.SENDERID);
        req.setTemplateID(SmsUtils.TEMPLATEID);
        req.setPhoneNumberSet(SmsUtils.PHONENUMBERS);
        return req;
    }
}

编写切面接入短信功能

评论发送短信通知博主,这功能一听就是与评论业务无关只是对评论功能单纯的一个增强,这不正是面向切面编程的意义所在吗?心动不如行动,还在有犹豫什么呢,快去编写发送短信的切面吧。

后置通知发送短信

代码语言:javascript
复制
/**
 * Created by jmy on 2021/4/29.
 */

@Aspect
@Component
public class SmsAspect {

    private final Logger logger = LoggerFactory.getLogger(this.getClass());

    @Autowired
    private SmsClient smsClient;
    @Autowired
    private RedisTemplate<String,String> redisTemplate;

    @Pointcut("@annotation(com.jmy.aspect.SendMessage)")
    public void sendMessage(){}

    @After("sendMessage()")
    public void doAfter(JoinPoint joinPoint) {
        Object[] args = joinPoint.getArgs();
        Comment comment = (Comment) args[];

        // 发送短信
        SendSmsRequest req = SendSmsRequestBeanFactory.getInstance();
        /* 模板参数: 若无模板参数,则设置为空*/
        String title = comment.getBlog().getTitle();
        String[] templateParams = {title.length() >  ? title.substring(,):title};
        req.setTemplateParamSet(templateParams);
        HttpServletRequest request = RepeatCommentInterceptor.threadLocal.get();
        String tll = RepeatCommentInterceptor.TLL.get();
        String remoteAddr = request.getRemoteAddr();
        new Thread(() -> {
            try {
                String boo = redisTemplate.opsForValue().get("comment:ip:" + remoteAddr);
                if (!StringUtils.isEmpty(boo) && tll.equals(boo)) {
                    smsClient.SendSms(req);
                }
            } catch (TencentCloudSDKException e) {
                logger.error(e.getMessage());
            }
        }).start();

    }
}

切面写好了怎么通知到我们的评论功能呢?当然是按照我们编写好的切入规则@Pointcut(“@annotation(com.jmy.aspect.SendMessage)”),在评论的方法上加上我们自定义的SendMessage注解就好啦。

不讲武德,耗子尾汁

短信通知的功能倒是实现啦,但是我眉头一紧突然意识到一个严重的问题,如果有不讲武德的小伙子刷评论我这白嫖的100条短信不是很快就没了吗,所以要小小的改造一下加个拦截器将请求的IP地址放到Redis中保存一小段时间用来校验是否刷评论就可以了,如何在拦截器中注入Spring管理的对象以及如何在切面中如何使用Request对象,这些都是不可忽视的小细节哦.

代码语言:javascript
复制
/**
 * Created by jmy on 2021/4/30.
 * 重复评论短信拦截器
 */

public class RepeatCommentInterceptor implements HandlerInterceptor {

    public static ThreadLocal<HttpServletRequest> threadLocal = new ThreadLocal<>();
    public static ThreadLocal<String> TLL = new ThreadLocal<>();
    @Autowired
    private RedisTemplate<String,String> redisTemplate;
    @Override
    public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception {
        threadLocal.set(httpServletRequest);
        String remoteAddr = httpServletRequest.getRemoteAddr();
        String tll = UUID.randomUUID().toString();
        TLL.set(tll);
        redisTemplate.opsForValue().setIfAbsent("comment:ip:" + remoteAddr, tll);
        redisTemplate.expire("comment:ip:" + remoteAddr,,TimeUnit.MINUTES);
        return true;
    }
代码语言:javascript
复制
/**
 * Created by jmy on 2021/4/30.
 */
@Configuration
public class WebConfig extends WebMvcConfigurerAdapter {

    @Bean
    public RepeatCommentInterceptor repeatCommentInterceptor(){
        return new RepeatCommentInterceptor();
    }
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new LoginInterceptor())
                .addPathPatterns("/admin/**")
                .excludePathPatterns("/admin")
                .excludePathPatterns("/admin/login");

        registry.addInterceptor(repeatCommentInterceptor())
                .addPathPatterns("/comments");
    }
}
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2022-08-06T,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 腾讯云短信平台
    • 引入依赖
      • 创建对象
        • 注入IOC容器
        • 单例模式创建SmsClient
        • 工厂模式创建SendSmsRequestBeanFactory
    • 编写切面接入短信功能
      • 后置通知发送短信
      • 不讲武德,耗子尾汁
      相关产品与服务
      短信
      腾讯云短信(Short Message Service,SMS)可为广大企业级用户提供稳定可靠,安全合规的短信触达服务。用户可快速接入,调用 API / SDK 或者通过控制台即可发送,支持发送验证码、通知类短信和营销短信。国内验证短信秒级触达,99%到达率;国际/港澳台短信覆盖全球200+国家/地区,全球多服务站点,稳定可靠。
      领券
      问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档