文章首发自个人微信公众号: 小哈学Java

个人网站: https://www.exception.site/springboot/spring-boots-send-mail

大家好,后续会间断地奉上一些 Spring Boot 2.x 相关的博文,包括 Spring Boot 2.x 教程和 Spring Boot 2.x 新特性教程相关,如 WebFlux 等。还有自定义 Starter 组件的进阶教程,比如:如何封装一个自定义图床 Starter 启动器(支持上传到服务器内部,阿里 OSS 和七牛云等), 仅仅需要配置相关参数,就可以将图片上传功能集成到现有的项目中。

好吧,这些都是后话。今天主要来讲讲如何在 Spring Boot 2.x 版本中集成发送邮件功能。

可以说,邮件发送在企业级应用中是比较常见的服务了,如运维报警,用户激活,广告推广等场景,均会使用到它。废话少说,开干!

目录

一、添加依赖

二、添加邮件相关配置

三、关于授权码

  • 3.1 什么是 QQ 邮箱授权码
  • 3.2 如何获取

四、开始编码

  • 4.1 定义功能类
  • 4.2 项目结构
  • 4.3 单元测试,验证效果

五、总结

六、GitHub 源码地址

一、添加依赖

pom.xml 文件中添加 spring-boot-starter-mail 依赖:

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-mail</artifactId>
</dependency>

二、添加邮件相关配置

application.properties 配置文件中添加下面内容:

# 发送邮件的服务器,笔者这里使用的 QQ 邮件
spring.mail.host=smtp.qq.com
spring.mail.username=你的邮箱地址
spring.mail.password=授权码,或邮箱密码
spring.mail.properties.mail.smtp.auth=true
spring.mail.properties.mail.smtp.starttls.enable=true
spring.mail.properties.mail.smtp.starttls.required=true

yml 格式的配置文件,添加如下:

spring:
mail:
host: smtp.qq.com #发送邮件的服务器,笔者这里使用的 QQ 邮件
username: 你的邮箱地址
password: 授权码,或邮箱密码
properties.mail.smtp.auth: true
properties.mail.smtp.starttls.enable: true
default-encoding: utf-8

三、关于授权码

对于上面的配置,您肯定对密码配置那块还抱有疑问,如果您使用的是 163 邮箱,或者 Gmail 邮箱,直接使用密码就可以了,如果您使用的是 QQ 邮箱,则需要先获取授权码。

到底什么事授权码? :

3.1 什么是 QQ 邮箱授权码

下图截自 QQ 邮箱官方文档:

3.2 如何获取

登录 QQ 邮箱:

点击设置:

跳转页面后,点击账户,将页面往下拖动,您会看到:

验证成功过后,即可获取授权码:

四、开始编码

4.1 定义功能类

先定义一个邮件服务的接口类, MailService.java:

package site.exception.springbootmail.service;

/**
* @author 犬小哈(微信号: 小哈学Java)
* @site 个人网站: www.exception.site
* @date 2019/4/10
* @time 下午4:19
* @discription
**/
public interface MailService { /**
* 发送简单文本的邮件
* @param to
* @param subject
* @param content
* @return
*/
boolean send(String to, String subject, String content); /**
* 发送 html 的邮件
* @param to
* @param subject
* @param html
* @return
*/
boolean sendWithHtml(String to, String subject, String html); /**
* 发送带有图片的 html 的邮件
* @param to
* @param subject
* @param html
* @param cids
* @param filePaths
* @return
*/
boolean sendWithImageHtml(String to, String subject, String html, String[] cids, String[] filePaths); /**
* 发送带有附件的邮件
* @param to
* @param subject
* @param content
* @param filePaths
* @return
*/
boolean sendWithWithEnclosure(String to, String subject, String content, String[] filePaths); }

接口内定义了四个方法:

  1. send(): 发送简单文本的邮件;
  2. sendWithHtml(): 发送 html 的邮件;
  3. sendWithImageHtml(): 发送带有图片的 html 的邮件;
  4. sendWithWithEnclosure: 发送带有附件的邮件;

完成接口的定义以后,我们再定义一个具体实现类,MailServiceImpl.java:

package site.exception.springbootmail.service.impl;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.mail.MailProperties;
import org.springframework.core.io.FileSystemResource;
import org.springframework.mail.SimpleMailMessage;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.mail.javamail.MimeMessageHelper;
import org.springframework.stereotype.Service;
import org.springframework.util.Assert;
import site.exception.springbootmail.service.MailService; import javax.mail.internet.MimeMessage; /**
* @author 犬小哈(微信号: 小哈学Java)
* @site 个人网站: www.exception.site
* @date 2019/4/10
* @time 下午4:19
* @discription
**/
@Service
public class MailServiceImpl implements MailService { private final static Logger logger = LoggerFactory.getLogger(MailServiceImpl.class); @Autowired
private MailProperties mailProperties;
@Autowired
private JavaMailSender javaMailSender; /**
* 发送简单文本的邮件
* @param to
* @param subject
* @param content
* @return
*/
@Override
public boolean send(String to, String subject, String content) {
logger.info("## Ready to send mail ..."); SimpleMailMessage simpleMailMessage = new SimpleMailMessage();
// 邮件发送来源
simpleMailMessage.setFrom(mailProperties.getUsername());
// 邮件发送目标
simpleMailMessage.setTo(to);
// 设置标题
simpleMailMessage.setSubject(subject);
// 设置内容
simpleMailMessage.setText(content); try {
// 发送
javaMailSender.send(simpleMailMessage);
logger.info("## Send the mail success ...");
} catch (Exception e) {
logger.error("Send mail error: ", e);
return false;
} return true;
} /**
* 发送 html 的邮件
* @param to
* @param subject
* @param html
* @return
*/
@Override
public boolean sendWithHtml(String to, String subject, String html) {
logger.info("## Ready to send mail ...");
MimeMessage mimeMessage = javaMailSender.createMimeMessage(); MimeMessageHelper mimeMessageHelper = null;
try {
mimeMessageHelper = new MimeMessageHelper(mimeMessage, true);
// 邮件发送来源
mimeMessageHelper.setFrom(mailProperties.getUsername());
// 邮件发送目标
mimeMessageHelper.setTo(to);
// 设置标题
mimeMessageHelper.setSubject(subject);
// 设置内容,并设置内容 html 格式为 true
mimeMessageHelper.setText(html, true); javaMailSender.send(mimeMessage);
logger.info("## Send the mail with html success ...");
} catch (Exception e) {
e.printStackTrace();
logger.error("Send html mail error: ", e);
return false;
} return true;
} /**
* 发送带有图片的 html 的邮件
* @param to
* @param subject
* @param html
* @param cids
* @param filePaths
* @return
*/
@Override
public boolean sendWithImageHtml(String to, String subject, String html, String[] cids, String[] filePaths) {
logger.info("## Ready to send mail ...");
MimeMessage mimeMessage = javaMailSender.createMimeMessage(); MimeMessageHelper mimeMessageHelper = null;
try {
mimeMessageHelper = new MimeMessageHelper(mimeMessage, true);
// 邮件发送来源
mimeMessageHelper.setFrom(mailProperties.getUsername());
// 邮件发送目标
mimeMessageHelper.setTo(to);
// 设置标题
mimeMessageHelper.setSubject(subject);
// 设置内容,并设置内容 html 格式为 true
mimeMessageHelper.setText(html, true); // 设置 html 中内联的图片
for (int i = 0; i < cids.length; i++) {
FileSystemResource file = new FileSystemResource(filePaths[i]);
// addInline() 方法 cid 需要 html 中的 cid (Content ID) 对应,才能设置图片成功,
// 具体可以参见,下面 4.3.3 单元测试的参数设置
mimeMessageHelper.addInline(cids[i], file);
} javaMailSender.send(mimeMessage);
logger.info("## Send the mail with image success ...");
} catch (Exception e) {
e.printStackTrace();
logger.error("Send html mail error: ", e);
return false;
} return true;
} /**
* 发送带有附件的邮件
* @param to
* @param subject
* @param content
* @param filePaths
* @return
*/
@Override
public boolean sendWithWithEnclosure(String to, String subject, String content, String[] filePaths) {
logger.info("## Ready to send mail ...");
MimeMessage mimeMessage = javaMailSender.createMimeMessage(); MimeMessageHelper mimeMessageHelper = null;
try {
mimeMessageHelper = new MimeMessageHelper(mimeMessage, true);
// 邮件发送来源
mimeMessageHelper.setFrom(mailProperties.getUsername());
// 邮件发送目标
mimeMessageHelper.setTo(to);
// 设置标题
mimeMessageHelper.setSubject(subject);
// 设置内容
mimeMessageHelper.setText(content); // 添加附件
for (int i = 0; i < filePaths.length; i++) {
FileSystemResource file = new FileSystemResource(filePaths[i]);
String attachementFileName = "附件" + (i + 1);
mimeMessageHelper.addAttachment(attachementFileName, file);
} javaMailSender.send(mimeMessage);
logger.info("## Send the mail with enclosure success ...");
} catch (Exception e) {
logger.error("Send html mail error: ", e);
return false;
}
return true;
}
}

4.2 项目结构

完成上面功能类的编码后,看下项目结构如下:

4.3 单元测试,验证效果

4.3.1 简单文本发送

填写相关测试参数,包括目标邮箱地址,标题,内容,运行单元测试:

单元测试通过,再看下实际效果:

邮件正常发送。

4.3.2 发送 Html

填写相关测试参数,包括目标邮箱地址,标题,html 内容,运行单元测试通过,直接看效果:

可以看到,邮件发送成功!

4.3.3 发送带有图片的 Html

填写相关测试参数,包括目标邮箱地址,标题,html 内容,html 中包含了两张图片,并且 src 中的内容是 cid:{flag}的格式,前缀 cid:是固定的,您需要改变是后面的标志位,通过 addInline(cid, file) 来将 cid 和具体的图片文件对应起来。

运行单元测试通过,看看效果如何:

可以看到 html 中图片也是 OK 的。

PS: 这里笔者在测试发送给 QQ 邮箱的时候,图片显示不成功,暂时还没找到问题在哪,如果有哪位读者知道,不妨后台发个消息告诉一下笔者哈。

4.3.4 发送带有附件的邮件

填写相关测试参数,包括目标邮箱地址,标题,内容,并添加了两个附件,运行单元测试,看看实际效果:

发送成功,到此所有的单元测试全部运行通过。

五、总结

本文中,我们学习如何在 Spring Boot 2.x 版本中集成发送邮件功能,包括发送简单文本,Html 内容,带有图片的 Html 内容,以及带有的附加的邮件,希望对您有所帮助!

六、GitHub 源码地址

https://github.com/weiwosuoai/spring-boot-tutorial/tree/master/spring-boot-mail

赠送 | 面试&学习福利资源

最近在网上发现一个不错的 PDF 资源《Java 核心面试知识.pdf》分享给大家,不光是面试,学习,你都值得拥有!!!

获取方式: 关注公众号: 小哈学Java, 后台回复 资源,既可获取资源链接,下面是目录以及部分截图:

重要的事情说两遍,获取方式: 关注公众号: 小哈学Java, 后台回复 资源,既可获取资源链接 !!!

欢迎关注微信公众号: 小哈学Java

Spring Boot 2.0 图文教程 | 集成邮件发送功能的更多相关文章

  1. SpringBoot 2.X从0到1实现邮件发送功能

    Spring中提供了JavaMailSender接口实现邮件发送功能,在SpringBoot2.X中也封装了发送邮件相关的Starter并且提供了自动化配置. 本文目录 一.添加对应的Starter二 ...

  2. Spring Boot 2.0 WebFlux 教程 (一) | 入门篇

    目录 一.什么是 Spring WebFlux 二.WebFlux 的优势&提升性能? 三.WebFlux 应用场景 四.选 WebFlux 还是 Spring MVC? 五.异同点 六.简单 ...

  3. SpringBoot集成邮件发送

    一:简述 在日常中的工作中难免会遇到程序集成邮件发送功能.接收功能:此篇文章我将使用SpringBoot集成邮件发送功能和接收功能:若对邮件一些基本协议和发送流程不懂的请务必参考我之前写的博客或者浏览 ...

  4. Spring Boot 2.0 的快速入门(图文教程)

    摘要: 原创出处 https://www.bysocket.com 「公众号:泥瓦匠BYSocket 」欢迎关注和转载,保留摘要,谢谢! Spring Boot 2.0 的快速入门(图文教程) 大家都 ...

  5. Spring Boot 2.0 教程 | 快速集成整合消息中间件 Kafka

    欢迎关注个人微信公众号: 小哈学Java, 每日推送 Java 领域干货文章,关注即免费无套路附送 100G 海量学习.面试资源哟!! 个人网站: https://www.exception.site ...

  6. Spring Boot 2.0 教程 | 配置 Undertow 容器

    欢迎关注个人微信公众号: 小哈学Java, 文末分享阿里 P8 资深架构师吐血总结的 <Java 核心知识整理&面试.pdf>资源链接!! 文章首发于个人网站 https://ww ...

  7. Spring Boot 2.0 教程 | AOP 切面统一打印请求日志

    欢迎关注微信公众号: 小哈学Java 文章首发于个人网站 https://www.exception.site/springboot/spring-boot-aop-web-request 本节中,您 ...

  8. Spring Boot 2.0(八):Spring Boot 集成 Memcached

    Memcached 介绍 Memcached 是一个高性能的分布式内存对象缓存系统,用于动态Web应用以减轻数据库负载.它通过在内存中缓存数据和对象来减少读取数据库的次数,从而提高动态.数据库驱动网站 ...

  9. Spring Boot 2.0 快速集成整合消息中间件 Kafka

    欢迎关注个人微信公众号: 小哈学Java, 每日推送 Java 领域干货文章,关注即免费无套路附送 100G 海量学习.面试资源哟!! 个人网站: https://www.exception.site ...

随机推荐

  1. 第三方支付设计——自有账户支付

    笔者在上一篇blog<<第三方支付架构设计之-帐户体系>>中已经稍微全面的阐述了第三方支付架构设计中的账户体系,在该体系中,其实涉及了各种各样的账户:银行侧账户(包括用户在银行 ...

  2. Spring中IOC和AOP的理解

    IOC和AOP是Spring的核心 IOC:控制反转:将创建对象以及维护对象之间的关系由代码交给了spring容器进行管理,也就是创建对象的方式反转了,交由spring容器进行管理. DI:依赖注入: ...

  3. php获取指定目录下的所有文件列表

    在我们实际的开发需求中,经常用到操作文件,今天就讲一下关于获取指定目录下的所有文件的几种常用方法: 1.scandir()函数 scandir() 函数返回指定目录中的文件和目录的数组. scandi ...

  4. Unity pdb2mdb错误

    错误: D:\sandbox\sandbox_art\sandbox_artprj\Assets\Plugins\Sandbox\Editor>"C:\ProgramFiles/Uni ...

  5. udp客户端收发数据流程

    1.创建客户端socket开始进行通讯.2.这时服务端应该先启动,并在知道服务端的ip以及端口号的时候才能进行通讯.3.本地不需要绑定ip以及端口号,在用此套接字对象发送消息的时候会自动分配活动端口( ...

  6. Maven学习(四)-- Maven的核心概念

    摘自:http://www.cnblogs.com/xdp-gacl/p/4051819.html 一.Maven坐标 1.1.什么是坐标? 在平面几何中坐标(x,y)可以标识平面中唯一的一点. 1. ...

  7. android dp深度解析(转)

    我转载地方的连接:http://zhangkun716717-126-com.iteye.com/blog/1772696  当笔记记录一下 dip: device independent pixel ...

  8. java并发之ReentrantLock学习理解

    简介 java多线程中可以使用synchronized关键字来实现线程间同步互斥,但在jdk1.5中新增加了ReentrantLock类也能实现同样的效果,并且在扩展功能上也更加强大,比如具有嗅探锁定 ...

  9. mybatis的使用

    1.like 的使用范例 name like CONCAT(CONCAT('%', #{name}), '%') 2.时间的比较的范例 <![CDATA[ and bill_date >= ...

  10. 远程备份binlog服务

    Ⅰ.bonlog server介绍 对于binlog的备份,之前文章里说的是有从机,一般不备份,那现在人家就是 要备份嘛,怎么办嘛, 写个脚本每天夜里去把前一天产生的binlog拷贝出来可以不? 行啊 ...