【问题标题】:How to validate SMTP server如何验证 SMTP 服务器
【发布时间】:2010-10-31 14:58:26
【问题描述】:

我正在进行一个项目,我必须验证给定的 SMTP 服务器,即在文本框中,用户将提供详细信息,然后他将单击测试按钮。我要检查用户输入的服务器是否是Smtp Server?

有什么想法吗??

【问题讨论】:

    标签: c# .net smtp


    【解决方案1】:

    尝试连接到 SMTP 端口,并确保从该端口收到一条以“220”开头并包含字母“SMTP”的行。一个典型的示例响应是:

    220 prod.monadic.cynic.net ESMTP Postfix (2.5.5)
    

    那就客气了,发“QUIT\r\n”挂断。

    如果愿意,您可以进行一些进一步的测试,例如测试用户是否有可能传递消息。为此,您将发送一个带有您的主机名(或任何字符串,实际上)的 HELO 命令、一个使用用户电子邮件地址的 MAIL FROM 命令和一个 RCPT TO:<example@example.com>。那时大多数服务器会告诉您是否不允许中继。 (我假设您是从稍后发送邮件的计算机上执行此操作的。)只要您在此之后 QUIT,而不是发出 DATA 命令和 消息数据,不会发送任何内容。

    这是一个示例会话,使用“netcat”命令从 shell 完成,显示我的服务器存在,但不会为来自随机 IP 地址的人中继邮件。

    $ nc prod.monadic.cynic.net。 25 220 prod.monadic.cynic.net ESMTP 后缀(2.5.5) HELO cynic.net 第250章 发件人: 250 2.1.0 好的 RCPT 收件人: 554 5.7.1 :中继访问被拒绝 放弃 221 2.0.0 再见 $

    【讨论】:

    • 正如 Curt 所说,尝试连接并检查是否可以打开端口。然后看看您是否收到响应,但如果配置了服务器,最初不会向您发送任何内容。所以要确保首先从“HELO”或“EHLO”命令开始并检查它的响应。 RFC 821、2821 和 5321 中列出了您可以尝试检查的任何其他命令。
    • 服务器确实会在您连接后立即向您发送 220 线路。我在上面添加了一个示例以使这一点更清楚。
    • 嗨,Curt,这确实是,但我可以正确地遵循第一部分,但我无法理解 synatx RCPT TO: 你能在 c# 中给出一些代码吗?
    • 所有服务器都应该发送 220 回复,您应该等待它发生。在规范中,一行的前 3 个字符是响应代码,之后的字符是可配置的,并且可能不包含 SMTP。相当多的服务器会在发送 220 回复作为垃圾邮件过滤器的一部分之前等待任意时间,如果您在收到 220 响应之前发送 HELO 或 EHLO,则您更有可能遇到垃圾邮件过滤。
    • Vinay,以美元符号开头的两行之间的所有内容都只是网络流量。您需要通过网络连接发送“RCPT TO:”。自己玩一下 netcat (nc) 命令,也许这会更有意义。另外,我强烈建议您阅读 Richard Stevens 的 TCP/IP Illustrated Volume 1 的几章;它将使您更好地了解这些网络协议的工作原理。
    【解决方案2】:

    您可能希望通过适当的异常处理以及设置超时来改进此快速代码 - 如果无法连接,则失败大约需要 15 秒,但这可能是 TCP/IP 握手的限制。

    按照 Curt 的建议发送 QUIT 命令会很好。

    private bool ValidSMTP(string hostName)
    {
        bool valid = false;
        try
        {
            TcpClient smtpTest = new TcpClient();
            smtpTest.Connect(hostName, 25);
            if (smtpTest.Connected)
            {
                NetworkStream ns = smtpTest.GetStream();
                StreamReader sr = new StreamReader(ns);
                if (sr.ReadLine().Contains("220"))
                {
                    valid = true;
                }
                smtpTest.Close();
            }
        }
        catch
        {
    
        }
        return valid;
    }
    

    【讨论】:

    • 如果不想等这么久,设置 smtpTest.ReceiveTimeout = 500;
    • 谢谢 - 这大致也适用于 POP - 只是端口而不是 220,我寻找 +OK。
    猜你喜欢
    • 1970-01-01
    • 2021-02-03
    • 1970-01-01
    • 2021-06-16
    • 2015-09-19
    • 2012-06-16
    • 2014-11-25
    • 2010-12-09
    • 2018-11-13
    相关资源
    最近更新 更多