SpringBoot通过Jakarta SMTP跨IP发邮件遇Could not convert socket to TLS错误
解决SMTP跨IP发送时的"Could not convert socket to TLS"错误
我编写了一个MailMessageService类,在同一服务器使用localhost发送邮件时一切正常,但从其他IP发送、将SMTP主机设置为172.105.90.58时,出现了以下错误:
代码实现
@Service @Slf4j @Transactional(readOnly = true) public class MailMessageService extends SimpleMailMessage { static Properties prop = new Properties(); public MailMessageService() { super(); } public void sendMessage(String subject, String body, String mailTo, String pathToFile) throws MessagingException, IOException { log.info("Sending email to: *{}* ", mailTo); Session session = Session.getInstance(prop, new Authenticator() { @Override protected PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication("info", "oT2ct2UUii87"); } }); Message message = new MimeMessage(session); message.setFrom(new InternetAddress("info@taradell.com.com")); message.setRecipients(Message.RecipientType.TO, InternetAddress.parse(mailTo)); message.setSubject(subject); MimeBodyPart mimeBodyPart = new MimeBodyPart(); mimeBodyPart.setContent(body, "text/html; charset=utf-8"); Multipart multipart = new MimeMultipart(); multipart.addBodyPart(mimeBodyPart); log.info("pathToFile: *{}* ", pathToFile); if (pathToFile != null) { MimeBodyPart attachment = new MimeBodyPart(); attachment.attachFile(pathToFile); multipart.addBodyPart(attachment); } log.info("Setting content"); message.setContent(multipart); log.info("Sending message {} ", message); Transport.send(message); } public void sendMessage(String subject, String body, String mailTo) throws MessagingException, IOException { sendMessage(subject, body, mailTo, null); } @PostConstruct public void initProperties() { prop.put("mail.smtp.auth", true); prop.put("mail.smtp.starttls.enable", "true"); prop.put("mail.smtp.host", "172.105.90.58"); prop.put("mail.smtp.port", "25"); prop.put("mail.smtp.ssl.trust", "172.105.90.58"); } }
错误信息
jakarta.mail.MessagingException: Could not convert socket to TLS at org.eclipse.angus.mail.smtp.SMTPTransport.startTLS(SMTPTransport.java:2173) at org.eclipse.angus.mail.smtp.SMTPTransport.protocolConnect(SMTPTransport.java:741) at jakarta.mail.Service.connect(Service.java:367) at jakarta.mail.Service.connect(Service.java:225) at jakarta.mail.Service.connect(Service.java:174) at jakarta.mail.Transport.send0(Transport.java:232) at jakarta.mail.Transport.send(Transport.java:102)
解决方案
检查端口与TLS模式匹配
25端口通常用于非加密或STARTTLS升级,但部分服务器可能在该端口禁用了TLS。可以尝试:- 切换到标准TLS端口587,修改配置:
prop.put("mail.smtp.port", "587") - 若服务器支持SSL直连,改用465端口并调整配置:
prop.put("mail.smtp.ssl.enable", "true"); prop.put("mail.smtp.port", "465"); // 移除mail.smtp.starttls.enable配置
- 切换到标准TLS端口587,修改配置:
验证网络与防火墙规则
- 用
telnet 172.105.90.58 587或nc -zv 172.105.90.58 587测试发送端到SMTP服务器目标端口的连通性 - 确认SMTP服务器的防火墙允许发送端IP的访问请求
- 用
强制指定兼容的TLS版本
若JVM默认TLS版本与服务器不兼容,可强制指定支持的版本:prop.put("mail.smtp.starttls.required", "true"); prop.put("mail.smtp.ssl.protocols", "TLSv1.2 TLSv1.3");调整证书信任策略
如果SMTP服务器用的是自签名证书,可临时跳过身份验证(仅测试用,生产环境不推荐):prop.put("mail.smtp.ssl.checkserveridentity", "false");生产环境建议将服务器证书导入JVM的
cacerts信任存储。修复静态属性的潜在问题
静态prop可能导致多实例下的配置混乱,建议改为非静态,或用@Value注入配置:@Value("${mail.smtp.host}") private String smtpHost; @Value("${mail.smtp.port}") private String smtpPort; @PostConstruct public void initProperties() { Properties prop = new Properties(); prop.put("mail.smtp.auth", true); prop.put("mail.smtp.starttls.enable", "true"); prop.put("mail.smtp.host", smtpHost); prop.put("mail.smtp.port", smtpPort); prop.put("mail.smtp.ssl.trust", smtpHost); }
内容的提问来源于stack exchange,提问作者Nunyet Calçada
相关产品推荐
相关产品推荐

