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

如何用Python测试邮箱的SMTP有效性?

用Python编程测试自定义域名邮箱的SMTP有效性

要批量验证邮箱地址的有效性,核心思路是通过SMTP握手模拟——查询邮箱域名的MX记录,连接对应邮件服务器,通过RCPT TO命令验证收件人是否存在,无需实际发送邮件。以下是具体实现方案:

前置依赖

首先安装dnspython库用于解析MX记录:

pip install dnspython

完整实现代码

import smtplib
import dns.resolver
import socket
import time

def check_email_validity(email):
    # 第一步:验证邮箱格式合法性
    if '@' not in email:
        return "格式无效"
    local_part, domain = email.split('@', 1)
    if not local_part or not domain:
        return "格式无效"

    # 第二步:查询域名的MX记录
    try:
        mx_records = dns.resolver.resolve(domain, 'MX')
        # 按优先级排序,取最优先的邮件服务器
        mx_server = sorted(mx_records, key=lambda x: x.preference)[0].exchange.to_text()
    except dns.resolver.NXDOMAIN:
        return "域名不存在"
    except dns.resolver.NoAnswer:
        return "域名未配置MX记录"
    except dns.resolver.Timeout:
        return "MX记录查询超时"
    except Exception as e:
        return f"MX查询失败: {str(e)}"

    # 第三步:尝试连接SMTP服务器,遍历常用端口
    ports = [587, 465, 25]  # 优先尝试加密端口
    for port in ports:
        try:
            if port == 465:
                # 建立SSL加密连接
                smtp_conn = smtplib.SMTP_SSL(mx_server, port, timeout=15)
            else:
                smtp_conn = smtplib.SMTP(mx_server, port, timeout=15)
                # 587端口需启用STARTTLS加密
                if port == 587:
                    smtp_conn.starttls()
            
            # 发送EHLO命令初始化会话
            smtp_conn.ehlo()
            
            # 模拟发件人(部分服务器会验证发件人合法性,可替换为真实邮箱)
            smtp_conn.mail('verify@example.org')
            
            # 发送RCPT TO命令验证收件人
            response_code, response_msg = smtp_conn.rcpt(email)
            smtp_conn.quit()

            # 解析响应码:250/251表示收件人有效
            if response_code in (250, 251):
                return "有效"
            elif response_code >= 500:
                return f"无效: {response_msg.decode('utf-8', errors='ignore')}"
            else:
                return "状态不确定(临时错误)"
        
        except smtplib.SMTPConnectError:
            continue  # 当前端口无法连接,尝试下一个
        except smtplib.SMTPException as e:
            return f"SMTP会话错误: {str(e)}"
        except socket.timeout:
            continue
        except Exception as e:
            return f"连接异常: {str(e)}"
    
    return "所有SMTP端口均无法连接"

# 批量测试示例
if __name__ == "__main__":
    email_list = [
        "name@organisation.com",
        "invalid_user@example.com",
        "test@gmail.com"
    ]
    for email in email_list:
        result = check_email_validity(email)
        print(f"{email:30} → {result}")
        time.sleep(1)  # 添加延迟,避免触发反垃圾机制

关键注意事项

  • 反垃圾策略限制:主流邮箱服务商(如Gmail、Outlook)会屏蔽此类验证请求,或返回模糊响应,无法准确判断有效性。部分服务器要求MAIL FROM为真实存在的邮箱,否则直接拒绝。
  • IP封禁风险:短时间内大量请求会触发服务器的反垃圾机制,导致IP被拉黑。建议添加合理延迟(如1-2秒/次),避免高频请求。
  • 响应码解读:
    • 250:收件人有效
    • 251:收件人不在本地,但服务器会转发(视为有效)
    • 550:收件人不存在或被拒绝
    • 4xx:临时错误(如服务器繁忙),需稍后重试
  • 格式预验证:先通过简单的格式检查过滤明显无效的邮箱,减少后续不必要的SMTP连接。

内容的提问来源于stack exchange,提问作者dyna-soar

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.17 05:01:00