You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Ubuntu服务器使用VaporSMTPKit发送邮件请求超时问题求助

VaporSMTPKit邮件发送超时问题排查

在Ubuntu服务器上使用VaporSMTPKit发送邮件,通过GET请求触发发送操作时,出现「The request timed out.」错误。已确认网站和服务器的25端口均开放,尝试更换端口或使用POP3时会出现警告提示,排除端口/协议问题,使用的是第三方网站邮箱(非服务器本地邮箱)。

相关代码

请求处理函数

func sendTestEmailHandler(_ req : Request) -> EventLoopFuture<String> {
    
    let email = Mail(
        from: "myemail@exemple.fr",
        to: [
            MailUser(name: "Myself", email: "myemail@exemple.fr")
        ],
        subject: "Your new mail server!",
        contentType: .plain,
        text: "You've set up mail!"
    )
    
    return req.application.sendMail(email, withCredentials: .default).map {
        return "Check your mail!"
    }
}

路由配置

routes.get("sendEmail", use : sendTestEmailHandler)

SMTP凭证配置

import Foundation
import VaporSMTPKit

extension SMTPCredentials {
    static var `default`: SMTPCredentials {
        return SMTPCredentials(
            hostname: "smtp.ionos.fr",
            port: 25,
            ssl: .tls(configuration: .default),
            email: "myemail@exemple.fr",
            // a changer sur le serveur
            password: "XXXX"
        )
    }
}

请求触发方式

通过GET请求触发:

http://XXXX/sendEmail

排查解决思路

  • 检查SMTP服务器TLS配置兼容性:部分邮件服务商对TLS版本或验证规则有特定要求,可尝试调整TLS配置:

    // 示例:禁用证书验证(仅测试环境使用)
    var tlsConfig = TLSConfiguration.makeClientConfiguration()
    tlsConfig.certificateVerification = .none
    // 在凭证配置中使用该tlsConfig
    ssl: .tls(configuration: tlsConfig)
    
  • 确认服务器出站25端口可用性:多数云服务商默认封禁25端口,即便服务器安全组开放,服务商层面仍可能拦截。可在服务器上用telnet测试连通性:

    telnet smtp.ionos.fr 25
    

    若连接超时,改用465(SSL)或587(STARTTLS)端口,并对应调整SSL配置:

    // 587端口配合STARTTLS示例
    static var `default`: SMTPCredentials {
        return SMTPCredentials(
            hostname: "smtp.ionos.fr",
            port: 587,
            ssl: .startTLS(configuration: .default),
            email: "myemail@exemple.fr",
            password: "XXXX"
        )
    }
    
  • 优化异步处理逻辑:当前请求会同步等待邮件发送完成,若发送耗时超过Vapor默认请求超时时间(通常60秒),就会触发超时。可将邮件发送放到后台队列,立即返回响应:

    func sendTestEmailHandler(_ req : Request) -> EventLoopFuture<String> {
        let email = Mail(
            from: "myemail@exemple.fr",
            to: [MailUser(name: "Myself", email: "myemail@exemple.fr")],
            subject: "Your new mail server!",
            contentType: .plain,
            text: "You've set up mail!"
        )
        
        // 投递到后台队列执行发送
        req.application.queue.dispatch {
            _ = req.application.sendMail(email, withCredentials: .default)
                .whenComplete { result in
                    switch result {
                    case .success: print("邮件发送成功")
                    case .failure(let error): print("邮件发送失败:\(error.localizedDescription)")
                    }
                }
        }
        
        return req.eventLoop.makeSucceededFuture("邮件已提交发送,请稍后查收!")
    }
    
  • 验证SMTP凭证有效性:确认邮箱密码是否正确,部分服务商要求使用SMTP授权码而非登录密码,需前往邮箱后台开启SMTP服务并获取对应授权码替换当前密码。

  • 查看详细日志定位问题:在configure.swift中开启调试日志,查看邮件发送过程中的具体错误:

    app.logger.logLevel = .debug
    

    启动服务后查看服务器日志,可获取SMTP握手、认证、发送阶段的具体报错信息,帮助精准定位问题。

内容的提问来源于stack exchange,提问作者Emmanuel Leicher

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 01:42:20