Spring Boot 整合 Redis 和 JavaMailSender 实现邮箱注册功能

Spring Boot 整合 Redis 和 JavaMailSender 实现邮箱注册功能

开篇

现在的网站基本都有邮件注册功能,毕竟可以通过邮件定期的给用户发送一些 垃圾邮件 精选推荐😂😂。

回到正题,首先我们得清楚一下几点

  • 邮件注册需要什么信息?

    ​ 最基本的:邮箱地址密码验证码

  • 这些信息放在什么位置?

    ​ 邮箱地址和密码没得说,以后会频繁使用,都得放到 MySQL 中,验证码呢,如果也放到 MySQL 还得给它新建一个字段,但注册后就不用了,这时候,redis 就可以很好的解决这个问题,而且 redis 还可以设置过期时间,各种数据类型也非常方便。

  • 如何发送邮件?

    ​ Spring Boot 整合了 JavaMailSender,导入 jar包即可使用,非常的方便

基本流程

  1. 点击发送邮件,后台生成一个随机验证码存入redis中,设置有效期5分钟
  2. 点击注册,拿用户输入的验证码和redis中的验证码比较是否一致

代码实现

只贴出核心代码,如果需要请前往我的 Github 查看
邮件服务器:邮件服务器地址大全

  1. 导入 Maven 依赖

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-mail</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-redis</artifactId>
    </dependency>
    
  2. 配置邮件、redis信息

    spring:
      # 配置邮件
      mail:
        host: smtp.qq.com #邮件服务器地址
        username: xxx #发送者邮箱
        password: xxx #密码
        default-encoding: utf-8
      # 配置redis
      redis:
        database: 0
        host: xxx
        port: 6379
        
    # 发送者邮箱
    beetle:
      sender:
        email: xxx
    
  3. 重新配置RedisTemplate,原生的RedisTemplate存在序列化问题,需要重新指定

    @Configuration
    @AutoConfigureAfter(CommunityApplication.class)
    public class RedisConfig {
    
        /**
         * 由于原生的redis自动装配,在存储key和value时,没有设置序列化方式,故自己创建redisTemplate实例
         * @param factory
         * @return
         */
        @Bean
        public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory factory) {
            RedisTemplate<String, Object> template = new RedisTemplate<>();
            template.setConnectionFactory(factory);
            Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class);
            ObjectMapper om = new ObjectMapper();
            om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
            om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
            jackson2JsonRedisSerializer.setObjectMapper(om);
            StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
            // key采用String的序列化方式
            template.setKeySerializer(stringRedisSerializer);
            // hash的key也采用String的序列化方式
            template.setHashKeySerializer(stringRedisSerializer);
            // value序列化方式采用jackson
            template.setValueSerializer(jackson2JsonRedisSerializer);
            // hash的value序列化方式采用jackson
            template.setHashValueSerializer(jackson2JsonRedisSerializer);
            template.afterPropertiesSet();
            return template;
        }
    }
    
    
  4. 写一个发送邮件的方法,到这里,我们已经把验证码生成并存到 redis 中了

    public Boolean sendEmail(String email) {
        if(!registered(email)){
            SimpleMailMessage simpleMailMessage = new SimpleMailMessage();
            simpleMailMessage.setTo(email);
            simpleMailMessage.setSubject("测试");
            //生成6位随机数
            int code = (int) ((Math.random() * 9 + 1) * 100000);
            //存入redis,过期时间5分钟
            redisTemplate.opsForValue().set(CODE_PRE + email, code, 5, TimeUnit.MINUTES);
            simpleMailMessage.setText("这是一封测试邮件,验证码:" + code);
            simpleMailMessage.setFrom(senderEmail);
            try {
                mailSender.send(simpleMailMessage);
                return true;
            } catch (MailException e) {
                log.error("邮件发送出错,{}", e);
            }
        }
        return false;
    }
    
  5. 注册的时候,需要先检查用户输入的验证码和 redis 中的是否一致,注册的其他逻辑我就不贴出来了

    public boolean checkCode(String email, Integer code) {
        Integer redisCode = (Integer) redisTemplate.opsForValue().get(CODE_PRE + email);
        return redisCode != null && redisCode.equals(code);
    }
    

效果演示

以我最近做的一个项目为例进行展示,源码:甲壳虫社区源码,线上地址:甲壳虫社区

  • 注册界面

  • redis 数据

  • 收到邮件

posted @ 2020-03-25 23:09  农夫三拳有点疼~  阅读(664)  评论(0编辑  收藏  举报