Python 2:SMTPServerDisconnected:连接意外关闭

时间:2013-07-20 07:25:58

标签: python python-2.7 email smtp

我在Python中发送电子邮件时遇到一个小问题:

#me == my email address
#you == recipient's email address
me = "some.email@gmail.com"
you = "some_email2@gmail.com"

# Create message container - the correct MIME type is multipart/alternative.
msg = MIMEMultipart('alternative')
msg['Subject'] = "Alert"
msg['From'] = me
msg['To'] = you

# Create the body of the message (a plain-text and an HTML version).
html = '<html><body><p>Hi, I have the following alerts for you!</p></body></html>'

# Record the MIME types of both parts - text/plain and text/html.
part2 = MIMEText(html, 'html')

# Attach parts into message container.
# According to RFC 2046, the last part of a multipart message, in this case
# the HTML message, is best and preferred.
msg.attach(part2)

# Send the message via local SMTP server.
s = smtplib.SMTP('aspmx.l.google.com')
# sendmail function takes 3 arguments: sender's address, recipient's address
# and message to send - here it is sent as one string.
s.sendmail(me, you, msg.as_string())
s.quit()

所以在此之前,我的程序没有给我一个错误,但它也没有给我发电子邮件。现在python给了我一个错误:

SMTPServerDisconnected: Connection unexpectedly closed

我该如何解决这个问题?

6 个答案:

答案 0 :(得分:9)

很可能gmail服务器在数据命令之后拒绝了连接(在这个阶段他们非常讨厌这样做:)。实际的消息很可能就是这个消息:

    retcode (421); Msg: 4.7.0 [ip.octets.listed.here      15] Our system has detected an unusual rate of
    4.7.0 unsolicited mail originating from your IP address. To protect our
    4.7.0 users from spam, mail sent from your IP address has been temporarily
    4.7.0 rate limited. Please visit
    4.7.0  https://support.google.com/mail/answer/81126 to review our Bulk Email
    4.7.0 Senders Guidelines. qa9si9093954wjc.138 - gsmtp

我怎么知道?因为我已经尝试过了s.set_debuglevel(1),它打印了SMTP会话,你可以直接看到问题所在。

你有两个选择:

  1. 继续使用该继电器; as explained by Google,它只是未加密的gmail-to-gmail,你必须通过他们的程序取消黑名单

  2. 最傻瓜式的选择是切换到带身份验证的TLS

  3. 以下是更改后的源代码:

    # skipped your comments for readability
    import smtplib
    from email.mime.multipart import MIMEMultipart
    from email.mime.text import MIMEText
    
    me = "some.email@gmail.com"
    my_password = r"your_actual_password"
    you = "some.email2@gmail.com"
    
    msg = MIMEMultipart('alternative')
    msg['Subject'] = "Alert"
    msg['From'] = me
    msg['To'] = you
    
    html = '<html><body><p>Hi, I have the following alerts for you!</p></body></html>'
    part2 = MIMEText(html, 'html')
    
    msg.attach(part2)
    
    # Send the message via gmail's regular server, over SSL - passwords are being sent, afterall
    s = smtplib.SMTP_SSL('smtp.gmail.com')
    # uncomment if interested in the actual smtp conversation
    # s.set_debuglevel(1)
    # do the smtp auth; sends ehlo if it hasn't been sent already
    s.login(me, my_password)
    
    s.sendmail(me, you, msg.as_string())
    s.quit()
    

    现在,如果试图'欺骗'系统并发送一个不同的(非gmail)地址,它将a)要求你连接到不同的主机名(gmail的一些MX记录),然后b)停止您并以黑名单ip为基础关闭连接,以及c)执行反向DNS,DKIM和许多其他对策,以确保您实际上控制了您在MAIL FROM:地址中显示的域名。

    最后,还有选项3) - 使用任何其他电子邮件中继服务,有很多好的:)

答案 1 :(得分:7)

我有同样的问题并通过指定正确的端口来解决它:

<html>
    <head>
        <title>Duckett Chapter 2 Example</title>
        <link href="styles.css" rel="stylesheet "type="text/css" >
    </head>
    <body>
        <h2 id="greeting">Howdy Molly, please check your order: </h2>
        <div>
          <ul id="left-col">
            <li><span>Custom Sign: </span> </li>
            <li><span>Total Tiles: </span></li>
            <li><span>Subtotal: </span></li>
            <li><span>Shipping: </span></li>
            <li><span>Grand Total: </span></li>
          </ul>
          <ul id="right-col">
            <li id="customSign">Montague Hotel</li>
            <li id="totalTiles">14</li>
            <li id="subtotal">$70</li>
            <li id="shipping">$7</li>
            <li id="grandTotal">$77</li>
          </ul>
            <div id="input-form">
                <input id="textInput" type="text">
                <button id="myButton">Calculate</button>  
            </div>  
        </div>
    <script src="scripts.js"></script>
    </body>
</html>

答案 2 :(得分:1)

使用smtplib.SMTP_SSL()代替smtplib.SMTP()对我有用。试试这个。

答案 3 :(得分:1)

我发现了一种奇怪的行为。我使用类似的代码提到了问题和答案。我的代码在最后几天一直在工作。但是,今天我遇到了问题中提到的错误消息。

我的解决方案: 我通过图书馆网络尝试了我的成功尝试。今天我通过星巴克网络(通过强制门户网站)尝试过它。我把它改成了我的移动网络。它又开始工作了。

Google可能拒绝来自不可靠网络的请求。

答案 4 :(得分:1)

我遇到了同样的问题。在我的情况下,密码几天前就改变了。所以,它给出了错误。当我在代码中更新密码时,它的工作就像一个魅力...... !!!

答案 5 :(得分:0)

Google员工:我有一台本地运行的测试smtp服务器。我收到此错误消息是因为我在关闭客户端smtp之前已关闭本地smtp服务器。