springboot集成邮箱验证功能

准备工作

开启SMTP服务

前往你的邮箱网站,以网易邮箱为例,打开网易邮箱地址,登录你的邮箱,进入邮箱管理后台界面。点击“设置”》》“POP3/SMTP/IMAP”后,点击开启SMTP服务即可。

技术实现


Spring Boot 发送邮件验证码的功能,主要用到了spring-boot-starter-mail工具包实现邮件的发送功能,利用junit-vintage-engine工具包实现了html邮件模板功能,利用easy-captcha工具包生成随机验证码 的功能!

引入依赖

     <!--引入mail依赖-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-mail</artifactId>
        </dependency>
         <!--mail模板-->
         <dependency>
            <groupId>org.junit.vintage</groupId>
            <artifactId>junit-vintage-engine</artifactId>
            <scope>test</scope>
            <exclusions>
                <exclusion>
                    <groupId>org.hamcrest</groupId>
                    <artifactId>hamcrest-core</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
          <!--验证码-->
        <dependency>
            <groupId>com.github.whvcse</groupId>
            <artifactId>easy-captcha</artifactId>
            <version>1.6.2</version>
        </dependency>

相关配置

然后再spring的配置文件中,设置mail相关配置:

spring:
  mail:
    host: smtp.yeah.com
    username: 你的邮箱
    password: 邮箱授权码
    default-encoding: UTF-8
    protocol: smtp
    properties:
      mail:
        smtp:
           auth: true # 启用SMTP认证
           starttls:
              enabled: true # 启用SMTP认证
              required: true # 必须采用加密链接

代码实现

创建一个MailService类,实现邮件发送的功能,代码如下:

import com.tarzan.nav.modules.admin.service.sys.SysConfigService;
import com.tarzan.nav.utils.DateUtil;
import lombok.extern.slf4j.Slf4j;
import org.antlr.stringtemplate.StringTemplate;
import org.antlr.stringtemplate.StringTemplateGroup;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.mail.javamail.MimeMessageHelper;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;
import javax.mail.MessagingException;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeMessage;
import javax.mail.internet.MimeUtility;
import java.io.UnsupportedEncodingException;
import java.util.Objects;


/**
 * @author lsyong
 */
@Component("mailService")
@Slf4j
public class MailService {

	private static final StringTemplateGroup templateGroup;
	@Resource
	private  SysConfigService sysConfigService;

	static{
		String classpath = Objects.requireNonNull(MailService.class.getClassLoader().getResource("")).getPath();
		templateGroup = new StringTemplateGroup("mailTemplates", classpath + "/mailTemplates");
	}
	
	public static String IMG_BASE_URL;
	public static String ACTIVATE_CONTEXT="http:";
	public static String RESET_PWD_CONTEXT;

	@Value("${spring.mail.username}")
	private String username;
    @Resource
    private JavaMailSender mailSender;


    private void sendMail(String to, String subject, String body) {
    	MimeMessage mail = mailSender.createMimeMessage();	
    	try {
    		MimeMessageHelper helper = new MimeMessageHelper(mail, true, "utf-8");
			helper.setFrom(new InternetAddress(MimeUtility.encodeText(sysConfigService.getSiteName())+"<"+username+">").toString());
			helper.setTo(to);
			helper.setSubject(subject);
			helper.setText(body, true);
			helper.setSentDate(DateUtil.now());
			mailSender.send(mail);
		} catch (MessagingException|UnsupportedEncodingException e) {
			log.error(e.getMessage());
		}
	}
    
    /**
     * send activation mail to
     * @param to,key
     */
    public void sendAccountActivationEmail(String to, String key){
    	StringTemplate activation_temp = templateGroup.getInstanceOf("activation");
    	activation_temp.setAttribute("img_base_url", IMG_BASE_URL);
    	activation_temp.setAttribute("email", to);
    	activation_temp.setAttribute("href", ACTIVATE_CONTEXT+key+"?email="+to);
    	activation_temp.setAttribute("link", ACTIVATE_CONTEXT+key+"?email="+to);
    	sendMail(to, sysConfigService.getSiteName()+"账户激活", activation_temp.toString());
    }

	@Async
	public void sendEmailCode(String to, String code){
		StringTemplate activation_temp = templateGroup.getInstanceOf("verificationCode");
		activation_temp.setAttribute("img_base_url", IMG_BASE_URL);
		activation_temp.setAttribute("email", to);
		activation_temp.setAttribute("code", code);
		sendMail(to, sysConfigService.getSiteName()+"邮箱验证码", activation_temp.toString());
	}
    
    /**
     * send change password link to
     * @param to,key
     */
    public void sendResetPwdEmail(String to, String key){
    	StringTemplate activation_temp = templateGroup.getInstanceOf("resetpwd");
    	activation_temp.setAttribute("img_base_url", IMG_BASE_URL);
    	activation_temp.setAttribute("href", RESET_PWD_CONTEXT+"?key="+key+"&email="+to);
    	activation_temp.setAttribute("link", RESET_PWD_CONTEXT+"?key="+key+"&email="+to);
    	sendMail(to, sysConfigService.getSiteName()+"账户密码重置", activation_temp.toString());
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/207700.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

java审计之java反序列化-CC链

介绍 序列化的本质是内存对象到数据流的一种转换&#xff0c;我们知道内存中的东西不具备持久性&#xff0c;但有些场景却需要将对象持久化保存或传输。 在Java工程中&#xff0c;序列化还广泛应用于JMX&#xff0c;RMI&#xff0c;网络传输&#xff08;协议包对象&#xff09…

vivado实现分析与收敛技巧4

执行建议 满足以下条件时 &#xff0c; 在建议运行轮次期间执行建议 &#xff1a; • 这些建议处于已启用 (ENABLED) 状态。 • 必须运行 APPLICABLE_FOR 阶段。 • 这些建议必须设置为 AUTO 。 执行建议时 &#xff0c; APPLIED 设置将会更新 &#xff0c; 如下图所示…

vue3动态加载音频文件,用于不同场景加载不同的文件

本文主要介绍如何在vue3中动态加载音频文件。 目录 前言静态加载动态加载import函数watch函数使用watch函数和import函数动态加载音频文件 前言 在vue3中&#xff0c;我们通常使用import xxx from xxxxxx来加载文件&#xff0c;但是如果我们需要加载哪些文件&#xff0c;是需要…

java数据结构(哈希表—HashMap)含LeetCode例题讲解

目录 1、HashMap的基本方法 1.1、基础方法&#xff08;增删改查&#xff09; 1.2、其他方法 2、HashMap的相关例题 2.1、题目介绍 2.2、解题 2.2.1、解题思路 2.2.2、解题图解 2.3、解题代码 1、HashMap的基本方法 HashMap 是一个散列表&#xff0c;它存储的内容是键…

Peter算法小课堂—差分与前缀和

差分 Codeforces802 D2C C代码详解 差分_哔哩哔哩_bilibili 一维差分 差分与前缀和可以说成减法和加法的关系、除法和乘法的关系、积分和微分的关系&#xff08;听不懂吧&#xff09; 给定数组A&#xff0c;S为A的前缀和数组&#xff0c;则A为S的差分数组 差分数组构造 现…

电子学会C/C++编程等级考试2021年06月(四级)真题解析

C/C++等级考试(1~8级)全部真题・点这里 第1题:数字三角形问题 (图1) 图1给出了一个数字三角形。从三角形的顶部到底部有很多条不同的路径。对于每条路径,把路径上面的数加起来可以得到一个和,你的任务就是找到最大的和。 注意:路径上的每一步只能从一个数走到下一层上和它…

Android Studio新版UI介绍

顶部菜单栏 左侧主要菜单入口项目名称分支名称 展开之后&#xff0c;主要功能与原来菜单栏功能一样&#xff0c;最大的变化就是把setting独立出去了。 而项目名称这里&#xff0c;展开就可以看到打开的历史工程列表&#xff0c;可以直接新建工程&#xff0c;原来需要在项目名称…

vivado实现分析与收敛技巧3-面向非工程用户的智能设计运行建议

要使用智能设计运行功能特性 &#xff0c; 需要 Vivado 工程。这是因为需要进行运行管理。以下指示信息解释了创建综合后工程的最简单方法。这些信息适用于以下流程的用户&#xff1a; • 非工程实现运行 • 使用较低版本的 Vivado 或第三方综合工具进行综合 访问智能设计…

Git——分支应用进阶

主要内容包括以下几个方面&#xff1a; 长期分支和短期分支的类型以及用途。多种分支模型&#xff0c;其中包括基于工作流的主题分支。不同分支模型的发布流程。在多个预览版程序中使用分支修复安全问题。远程跟踪分支和refspecs规范&#xff0c;以及默认远程版本库配置。拉取…

测评补单助力亚马逊,速卖通,国际站卖家抢占市场,提升转化和评分

想要快速提升商品的销量&#xff0c;测评补单这种方法见效是最快的。特别是新品上线&#xff0c;缺少用户评价&#xff0c;转化率不好&#xff0c;很多商家新品上线都会做测评补单&#xff0c;搞些商品好评&#xff0c;不但可以提升转化&#xff0c;同时在平台也可以获得更多展…

Redis:主从复制

目录 概念配置步骤通过命令配置主从复制原理薪火相传反客为主哨兵(Sentinel)模式原理配置SpringBoot整合Sentinel模式 概念 主机更新后根据配置和策略&#xff0c;自动同步到备机的master/slave机制&#xff0c;Master以写为主&#xff0c;Slave以读为主。 作用&#xff1a; …

Python+Requests模块添加cookie

请求中添加cookies 对于某些网站&#xff0c;登录然后从浏览器中获取cookies&#xff0c;以后就可以直接拿着cookie登录了&#xff0c;无需输入用户 名密码。 一、在参数中添加cookie 在发送请求时使用cookies 代码示例&#xff1a; import requests # 1&#xff0c;在参数…

ZFPlayer 在tableView列表中播放视频架构设计

需求背景 需要在如图所示的列表中播放视频&#xff0c;并且播放视频在对应的卡片上&#xff0c;滚动结束的时候&#xff0c; 完整露出封面图的第一个视频自动播放 分析 根据需求&#xff0c;是滚动的时候获取符合条件的cell&#xff0c;并且 在cell的封面图上播放视频&#x…

CSS中的非布局样式+CSS布局 前端开发入门笔记(十一)

CSS中的非布局样式 在CSS中&#xff0c;非布局样式是指那些不会直接影响页面布局的样式。这些样式主要关注的是元素的颜色、字体、背景、边框、阴影等视觉效果。以下是一些常见的非布局CSS样式&#xff1a; 文本样式&#xff1a;包括字体&#xff08;font-family&#xff09;…

传统算法:使用 Pygame 实现归并排序

使用 Pygame 模块实现了归并排序的动画演示。首先,它生成一个包含随机整数的数组,并通过 Pygame 在屏幕上绘制这个数组的条形图。接着,通过归并排序算法对数组进行排序,动画效果可视化每一步的排序过程。在排序的过程中,程序将数组递归地分成两半,分别进行排序,然后再将…

小白备战蓝桥杯:Java常用API

一、什么是API 就是别人写好的一些类&#xff0c;给咱们程序员直接拿去调用即可解决问题的 我们之前接触过的Scanner和Random都是API 但java中提供的API很多&#xff0c;我们没有必要去学习所有的API&#xff0c;只需要知道一些常用的API&#xff0c;再借助帮助文档去使用AP…

从HumanEval到CoderEval: 你的代码生成模型真的work吗?

本文主要介绍了一个名为CoderEval的代码生成大模型评估基准&#xff0c;并对三个代码生成模型&#xff08;CodeGen、PanGu-Coder和ChatGPT&#xff09;在该基准上的表现进行了评估和比较。研究人员从真实的开源项目中的选取了代码生成任务来构建CoderEval&#xff0c;并根据对外…

Python函数专题(下)侯小啾python领航班系列(十三)】

Python函数专题(下)侯小啾python领航班系列(十三)】 大家好,我是博主侯小啾, 🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹꧔ꦿ🌹…

腾讯云年末感恩回馈:2核2G4M云服务器118元1年,新老用户同享!

腾讯云年末感恩回馈活动开始了&#xff0c;年度爆款2核2G4M云服务器118元/年&#xff0c;新老用户同享&#xff0c;记得抓住上云好时机&#xff01; 活动地址&#xff1a; 点此直达腾讯云年末感恩回馈 活动详情&#xff1a; 配置说明&#xff1a; 2核2G 独享CPU性能50GB SSD…

观《王牌对王牌:国宝回国》有感 —— AI绘画之古画修复对比图

一、前言 上周《王牌对王牌》节目的主题是《国宝回国》&#xff0c;而今天的AI绘画的灵感&#xff0c;就来源于这期节目。 下面这组图&#xff0c;左侧部分因时间的流逝而显现出褪色和损伤的痕迹&#xff0c;色彩变得暗淡&#xff0c;细节也因年代久远而变得模糊不清。 而右…