zoukankan      html  css  js  c++  java
  • Pyqt Smtplib实现Qthread多线程发送邮件

    一. smtplib 的介绍

         smtplib.SMTP([host[, port[, local_hostname[, timeout]]]])

       SMTP类构造函数,表示与SMTP服务器之间的连接,通过这个连接可以向smtp服务器发送指令,执行相关操作(如:登陆、发送邮件)。所有参数都是可选的。

         host:smtp服务器主机名

         port:smtp服务的端口,默认是25;如果在创建SMTP对象的时候提供了这两个参数,在初始化的时候会自动调用connect方法去连接服务器。

       smtplib模块还提供了SMTP_SSL类和LMTP类,对它们的操作与SMTP基本一致。

      smtplib.SMTP提供的方法:

         SMTP.set_debuglevel(level):设置是否为调试模式。默认为False,即非调试模式,表示不输出任何调试信息。

         SMTP.connect([host[, port]]):连接到指定的smtp服务器。参数分别表示smpt主机和端口。注意: 也可以在host参数中指定端口号(如:smpt.yeah.net:25),这样就没必要给出port参数。

         SMTP.docmd(cmd[, argstring]):向smtp服务器发送指令。可选参数argstring表示指令的参数。

         SMTP.helo([hostname]) :使用"helo"指令向服务器确认身份。相当于告诉smtp服务器“我是谁”。

         SMTP.has_extn(name):判断指定名称在服务器邮件列表中是否存在。出于安全考虑,smtp服务器往往屏蔽了该指令。

         SMTP.verify(address) :判断指定邮件地址是否在服务器中存在。出于安全考虑,smtp服务器往往屏蔽了该指令。

         SMTP.login(user, password) :登陆到smtp服务器。现在几乎所有的smtp服务器,都必须在验证用户信息合法之后才允许发送邮件。

         SMTP.sendmail(from_addr, to_addrs, msg[, mail_options, rcpt_options]) :发送邮件。这里要注意一下第三个参数,msg是字符串,表示邮件。我们知道邮件一般由标题,发信人,收件人,邮件内容,附件等构成,发送邮件的时候,要注意msg的格式。这个格式就是smtp协议中定义的格式。

         SMTP.quit() :断开与smtp服务器的连接,相当于发送"quit"指令。(很多程序中都用到了smtp.close(),具体与quit的区别google了一下,也没找到答案。)

    参考:http://www.cnblogs.com/xiaowuyi/archive/2012/03/17/2404015.html

    二.创建Ui

    sendmail.Ui 

      1 <?xml version="1.0" encoding="UTF-8"?>
      2 <ui version="4.0">
      3  <class>SendMailer</class>
      4  <widget class="QWidget" name="SendMailer">
      5   <property name="geometry">
      6    <rect>
      7     <x>0</x>
      8     <y>0</y>
      9     <width>518</width>
     10     <height>519</height>
     11    </rect>
     12   </property>
     13   <property name="windowTitle">
     14    <string>Form</string>
     15   </property>
     16   <layout class="QVBoxLayout" name="verticalLayout">
     17    <item>
     18     <widget class="QGroupBox" name="groupBox">
     19      <property name="minimumSize">
     20       <size>
     21        <width>0</width>
     22        <height>90</height>
     23       </size>
     24      </property>
     25      <property name="maximumSize">
     26       <size>
     27        <width>16777215</width>
     28        <height>90</height>
     29       </size>
     30      </property>
     31      <property name="title">
     32       <string>配置项</string>
     33      </property>
     34      <layout class="QVBoxLayout" name="verticalLayout_4">
     35       <item>
     36        <layout class="QHBoxLayout" name="horizontalLayout_7">
     37         <item>
     38          <widget class="QLabel" name="label">
     39           <property name="text">
     40            <string>服务器地址:</string>
     41           </property>
     42          </widget>
     43         </item>
     44         <item>
     45          <widget class="QComboBox" name="comboBoxServer">
     46           <property name="minimumSize">
     47            <size>
     48             <width>150</width>
     49             <height>0</height>
     50            </size>
     51           </property>
     52          </widget>
     53         </item>
     54         <item>
     55          <widget class="QLineEdit" name="lineEditSMTP">
     56           <property name="text">
     57            <string>自定义</string>
     58           </property>
     59          </widget>
     60         </item>
     61        </layout>
     62       </item>
     63       <item>
     64        <widget class="Line" name="line_4">
     65         <property name="orientation">
     66          <enum>Qt::Horizontal</enum>
     67         </property>
     68        </widget>
     69       </item>
     70       <item>
     71        <layout class="QHBoxLayout" name="horizontalLayout_8">
     72         <item>
     73          <widget class="QLabel" name="label_2">
     74           <property name="text">
     75            <string>用户名:</string>
     76           </property>
     77          </widget>
     78         </item>
     79         <item>
     80          <widget class="QLineEdit" name="lineEditUser">
     81           <property name="inputMethodHints">
     82            <set>Qt::ImhNone</set>
     83           </property>
     84          </widget>
     85         </item>
     86         <item>
     87          <widget class="Line" name="line_5">
     88           <property name="orientation">
     89            <enum>Qt::Vertical</enum>
     90           </property>
     91          </widget>
     92         </item>
     93         <item>
     94          <widget class="QLabel" name="label_3">
     95           <property name="text">
     96            <string>密码:</string>
     97           </property>
     98          </widget>
     99         </item>
    100         <item>
    101          <widget class="QLineEdit" name="lineEditPasswd">
    102           <property name="echoMode">
    103            <enum>QLineEdit::Password</enum>
    104           </property>
    105          </widget>
    106         </item>
    107         <item>
    108          <widget class="QCheckBox" name="checkBoxRememberUP">
    109           <property name="text">
    110            <string>记住用户名密码</string>
    111           </property>
    112          </widget>
    113         </item>
    114        </layout>
    115       </item>
    116      </layout>
    117     </widget>
    118    </item>
    119    <item>
    120     <widget class="QGroupBox" name="groupBox_2">
    121      <property name="minimumSize">
    122       <size>
    123        <width>500</width>
    124        <height>0</height>
    125       </size>
    126      </property>
    127      <property name="title">
    128       <string>内容项</string>
    129      </property>
    130      <layout class="QVBoxLayout" name="verticalLayout_2">
    131       <item>
    132        <layout class="QHBoxLayout" name="horizontalLayout_2">
    133         <item>
    134          <widget class="QLabel" name="label_5">
    135           <property name="maximumSize">
    136            <size>
    137             <width>16777215</width>
    138             <height>16777215</height>
    139            </size>
    140           </property>
    141           <property name="text">
    142            <string>接收人:  </string>
    143           </property>
    144          </widget>
    145         </item>
    146         <item>
    147          <widget class="QLineEdit" name="lineEditReceiver"/>
    148         </item>
    149         <item>
    150          <widget class="QLabel" name="label_6">
    151           <property name="text">
    152            <string>多个用, 分隔开</string>
    153           </property>
    154          </widget>
    155         </item>
    156        </layout>
    157       </item>
    158       <item>
    159        <widget class="Line" name="line">
    160         <property name="orientation">
    161          <enum>Qt::Horizontal</enum>
    162         </property>
    163        </widget>
    164       </item>
    165       <item>
    166        <layout class="QHBoxLayout" name="horizontalLayout_3">
    167         <item>
    168          <widget class="QLabel" name="label_7">
    169           <property name="text">
    170            <string>邮件主题:</string>
    171           </property>
    172          </widget>
    173         </item>
    174         <item>
    175          <widget class="QLineEdit" name="lineEditCheme"/>
    176         </item>
    177        </layout>
    178       </item>
    179       <item>
    180        <widget class="Line" name="line_3">
    181         <property name="orientation">
    182          <enum>Qt::Horizontal</enum>
    183         </property>
    184        </widget>
    185       </item>
    186       <item>
    187        <layout class="QVBoxLayout" name="verticalLayout_3">
    188         <item>
    189          <widget class="QLabel" name="label_8">
    190           <property name="text">
    191            <string>邮件正文:</string>
    192           </property>
    193          </widget>
    194         </item>
    195         <item>
    196          <widget class="QTextEdit" name="textEditBody"/>
    197         </item>
    198         <item>
    199          <layout class="QHBoxLayout" name="horizontalLayout_4">
    200           <item>
    201            <widget class="QLabel" name="label_4">
    202             <property name="text">
    203              <string>邮件附件:</string>
    204             </property>
    205            </widget>
    206           </item>
    207           <item>
    208            <widget class="QPushButton" name="attachBtn">
    209             <property name="text">
    210              <string>选择附件</string>
    211             </property>
    212            </widget>
    213           </item>
    214           <item>
    215            <widget class="QLineEdit" name="lineEditAttach"/>
    216           </item>
    217          </layout>
    218         </item>
    219        </layout>
    220       </item>
    221      </layout>
    222     </widget>
    223    </item>
    224    <item>
    225     <layout class="QHBoxLayout" name="horizontalLayout_6">
    226      <item>
    227       <widget class="QProgressBar" name="progressBarSend">
    228        <property name="value">
    229         <number>24</number>
    230        </property>
    231       </widget>
    232      </item>
    233      <item>
    234       <widget class="QLabel" name="labelSendMsg">
    235        <property name="minimumSize">
    236         <size>
    237          <width>71</width>
    238          <height>0</height>
    239         </size>
    240        </property>
    241        <property name="text">
    242         <string>    发送消息</string>
    243        </property>
    244       </widget>
    245      </item>
    246      <item>
    247       <spacer name="horizontalSpacer_2">
    248        <property name="orientation">
    249         <enum>Qt::Horizontal</enum>
    250        </property>
    251        <property name="sizeHint" stdset="0">
    252         <size>
    253          <width>40</width>
    254          <height>20</height>
    255         </size>
    256        </property>
    257       </spacer>
    258      </item>
    259      <item>
    260       <widget class="QPushButton" name="sendingBtn">
    261        <property name="text">
    262         <string>开始发送</string>
    263        </property>
    264       </widget>
    265      </item>
    266     </layout>
    267    </item>
    268   </layout>
    269  </widget>
    270  <resources/>
    271  <connections/>
    272 </ui>

    转换为sendmail.py 

      1 # -*- coding: utf-8 -*-
      2 
      3 # Form implementation generated from reading ui file 'sendmail.ui'
      4 #
      5 # Created: Thu Mar 05 17:49:53 2015
      6 #      by: PyQt4 UI code generator 4.10.3
      7 #
      8 # WARNING! All changes made in this file will be lost!
      9 
     10 from PyQt4 import QtCore, QtGui
     11 
     12 try:
     13     _fromUtf8 = QtCore.QString.fromUtf8
     14 except AttributeError:
     15     def _fromUtf8(s):
     16         return s
     17 
     18 try:
     19     _encoding = QtGui.QApplication.UnicodeUTF8
     20     def _translate(context, text, disambig):
     21         return QtGui.QApplication.translate(context, text, disambig, _encoding)
     22 except AttributeError:
     23     def _translate(context, text, disambig):
     24         return QtGui.QApplication.translate(context, text, disambig)
     25 
     26 class Ui_SendMailer(object):
     27     def setupUi(self, SendMailer):
     28         SendMailer.setObjectName(_fromUtf8("SendMailer"))
     29         SendMailer.resize(518, 519)
     30         self.verticalLayout = QtGui.QVBoxLayout(SendMailer)
     31         self.verticalLayout.setObjectName(_fromUtf8("verticalLayout"))
     32         self.groupBox = QtGui.QGroupBox(SendMailer)
     33         self.groupBox.setMinimumSize(QtCore.QSize(0, 90))
     34         self.groupBox.setMaximumSize(QtCore.QSize(16777215, 90))
     35         self.groupBox.setObjectName(_fromUtf8("groupBox"))
     36         self.verticalLayout_4 = QtGui.QVBoxLayout(self.groupBox)
     37         self.verticalLayout_4.setObjectName(_fromUtf8("verticalLayout_4"))
     38         self.horizontalLayout_7 = QtGui.QHBoxLayout()
     39         self.horizontalLayout_7.setObjectName(_fromUtf8("horizontalLayout_7"))
     40         self.label = QtGui.QLabel(self.groupBox)
     41         self.label.setObjectName(_fromUtf8("label"))
     42         self.horizontalLayout_7.addWidget(self.label)
     43         self.comboBoxServer = QtGui.QComboBox(self.groupBox)
     44         self.comboBoxServer.setMinimumSize(QtCore.QSize(150, 0))
     45         self.comboBoxServer.setObjectName(_fromUtf8("comboBoxServer"))
     46         self.horizontalLayout_7.addWidget(self.comboBoxServer)
     47         self.lineEditSMTP = QtGui.QLineEdit(self.groupBox)
     48         self.lineEditSMTP.setObjectName(_fromUtf8("lineEditSMTP"))
     49         self.horizontalLayout_7.addWidget(self.lineEditSMTP)
     50         self.verticalLayout_4.addLayout(self.horizontalLayout_7)
     51         self.line_4 = QtGui.QFrame(self.groupBox)
     52         self.line_4.setFrameShape(QtGui.QFrame.HLine)
     53         self.line_4.setFrameShadow(QtGui.QFrame.Sunken)
     54         self.line_4.setObjectName(_fromUtf8("line_4"))
     55         self.verticalLayout_4.addWidget(self.line_4)
     56         self.horizontalLayout_8 = QtGui.QHBoxLayout()
     57         self.horizontalLayout_8.setObjectName(_fromUtf8("horizontalLayout_8"))
     58         self.label_2 = QtGui.QLabel(self.groupBox)
     59         self.label_2.setObjectName(_fromUtf8("label_2"))
     60         self.horizontalLayout_8.addWidget(self.label_2)
     61         self.lineEditUser = QtGui.QLineEdit(self.groupBox)
     62         self.lineEditUser.setInputMethodHints(QtCore.Qt.ImhNone)
     63         self.lineEditUser.setObjectName(_fromUtf8("lineEditUser"))
     64         self.horizontalLayout_8.addWidget(self.lineEditUser)
     65         self.line_5 = QtGui.QFrame(self.groupBox)
     66         self.line_5.setFrameShape(QtGui.QFrame.VLine)
     67         self.line_5.setFrameShadow(QtGui.QFrame.Sunken)
     68         self.line_5.setObjectName(_fromUtf8("line_5"))
     69         self.horizontalLayout_8.addWidget(self.line_5)
     70         self.label_3 = QtGui.QLabel(self.groupBox)
     71         self.label_3.setObjectName(_fromUtf8("label_3"))
     72         self.horizontalLayout_8.addWidget(self.label_3)
     73         self.lineEditPasswd = QtGui.QLineEdit(self.groupBox)
     74         self.lineEditPasswd.setEchoMode(QtGui.QLineEdit.Password)
     75         self.lineEditPasswd.setObjectName(_fromUtf8("lineEditPasswd"))
     76         self.horizontalLayout_8.addWidget(self.lineEditPasswd)
     77         self.checkBoxRememberUP = QtGui.QCheckBox(self.groupBox)
     78         self.checkBoxRememberUP.setObjectName(_fromUtf8("checkBoxRememberUP"))
     79         self.horizontalLayout_8.addWidget(self.checkBoxRememberUP)
     80         self.verticalLayout_4.addLayout(self.horizontalLayout_8)
     81         self.verticalLayout.addWidget(self.groupBox)
     82         self.groupBox_2 = QtGui.QGroupBox(SendMailer)
     83         self.groupBox_2.setMinimumSize(QtCore.QSize(500, 0))
     84         self.groupBox_2.setObjectName(_fromUtf8("groupBox_2"))
     85         self.verticalLayout_2 = QtGui.QVBoxLayout(self.groupBox_2)
     86         self.verticalLayout_2.setObjectName(_fromUtf8("verticalLayout_2"))
     87         self.horizontalLayout_2 = QtGui.QHBoxLayout()
     88         self.horizontalLayout_2.setObjectName(_fromUtf8("horizontalLayout_2"))
     89         self.label_5 = QtGui.QLabel(self.groupBox_2)
     90         self.label_5.setMaximumSize(QtCore.QSize(16777215, 16777215))
     91         self.label_5.setObjectName(_fromUtf8("label_5"))
     92         self.horizontalLayout_2.addWidget(self.label_5)
     93         self.lineEditReceiver = QtGui.QLineEdit(self.groupBox_2)
     94         self.lineEditReceiver.setObjectName(_fromUtf8("lineEditReceiver"))
     95         self.horizontalLayout_2.addWidget(self.lineEditReceiver)
     96         self.label_6 = QtGui.QLabel(self.groupBox_2)
     97         self.label_6.setObjectName(_fromUtf8("label_6"))
     98         self.horizontalLayout_2.addWidget(self.label_6)
     99         self.verticalLayout_2.addLayout(self.horizontalLayout_2)
    100         self.line = QtGui.QFrame(self.groupBox_2)
    101         self.line.setFrameShape(QtGui.QFrame.HLine)
    102         self.line.setFrameShadow(QtGui.QFrame.Sunken)
    103         self.line.setObjectName(_fromUtf8("line"))
    104         self.verticalLayout_2.addWidget(self.line)
    105         self.horizontalLayout_3 = QtGui.QHBoxLayout()
    106         self.horizontalLayout_3.setObjectName(_fromUtf8("horizontalLayout_3"))
    107         self.label_7 = QtGui.QLabel(self.groupBox_2)
    108         self.label_7.setObjectName(_fromUtf8("label_7"))
    109         self.horizontalLayout_3.addWidget(self.label_7)
    110         self.lineEditCheme = QtGui.QLineEdit(self.groupBox_2)
    111         self.lineEditCheme.setObjectName(_fromUtf8("lineEditCheme"))
    112         self.horizontalLayout_3.addWidget(self.lineEditCheme)
    113         self.verticalLayout_2.addLayout(self.horizontalLayout_3)
    114         self.line_3 = QtGui.QFrame(self.groupBox_2)
    115         self.line_3.setFrameShape(QtGui.QFrame.HLine)
    116         self.line_3.setFrameShadow(QtGui.QFrame.Sunken)
    117         self.line_3.setObjectName(_fromUtf8("line_3"))
    118         self.verticalLayout_2.addWidget(self.line_3)
    119         self.verticalLayout_3 = QtGui.QVBoxLayout()
    120         self.verticalLayout_3.setObjectName(_fromUtf8("verticalLayout_3"))
    121         self.label_8 = QtGui.QLabel(self.groupBox_2)
    122         self.label_8.setObjectName(_fromUtf8("label_8"))
    123         self.verticalLayout_3.addWidget(self.label_8)
    124         self.textEditBody = QtGui.QTextEdit(self.groupBox_2)
    125         self.textEditBody.setObjectName(_fromUtf8("textEditBody"))
    126         self.verticalLayout_3.addWidget(self.textEditBody)
    127         self.horizontalLayout_4 = QtGui.QHBoxLayout()
    128         self.horizontalLayout_4.setObjectName(_fromUtf8("horizontalLayout_4"))
    129         self.label_4 = QtGui.QLabel(self.groupBox_2)
    130         self.label_4.setObjectName(_fromUtf8("label_4"))
    131         self.horizontalLayout_4.addWidget(self.label_4)
    132         self.attachBtn = QtGui.QPushButton(self.groupBox_2)
    133         self.attachBtn.setObjectName(_fromUtf8("attachBtn"))
    134         self.horizontalLayout_4.addWidget(self.attachBtn)
    135         self.lineEditAttach = QtGui.QLineEdit(self.groupBox_2)
    136         self.lineEditAttach.setObjectName(_fromUtf8("lineEditAttach"))
    137         self.horizontalLayout_4.addWidget(self.lineEditAttach)
    138         self.verticalLayout_3.addLayout(self.horizontalLayout_4)
    139         self.verticalLayout_2.addLayout(self.verticalLayout_3)
    140         self.verticalLayout.addWidget(self.groupBox_2)
    141         self.horizontalLayout_6 = QtGui.QHBoxLayout()
    142         self.horizontalLayout_6.setObjectName(_fromUtf8("horizontalLayout_6"))
    143         self.progressBarSend = QtGui.QProgressBar(SendMailer)
    144         self.progressBarSend.setProperty("value", 24)
    145         self.progressBarSend.setObjectName(_fromUtf8("progressBarSend"))
    146         self.horizontalLayout_6.addWidget(self.progressBarSend)
    147         self.labelSendMsg = QtGui.QLabel(SendMailer)
    148         self.labelSendMsg.setMinimumSize(QtCore.QSize(71, 0))
    149         self.labelSendMsg.setObjectName(_fromUtf8("labelSendMsg"))
    150         self.horizontalLayout_6.addWidget(self.labelSendMsg)
    151         spacerItem = QtGui.QSpacerItem(40, 20, QtGui.QSizePolicy.Expanding, QtGui.QSizePolicy.Minimum)
    152         self.horizontalLayout_6.addItem(spacerItem)
    153         self.sendingBtn = QtGui.QPushButton(SendMailer)
    154         self.sendingBtn.setObjectName(_fromUtf8("sendingBtn"))
    155         self.horizontalLayout_6.addWidget(self.sendingBtn)
    156         self.verticalLayout.addLayout(self.horizontalLayout_6)
    157 
    158         self.retranslateUi(SendMailer)
    159         QtCore.QMetaObject.connectSlotsByName(SendMailer)
    160 
    161     def retranslateUi(self, SendMailer):
    162         SendMailer.setWindowTitle(_translate("SendMailer", "Form", None))
    163         self.groupBox.setTitle(_translate("SendMailer", "配置项", None))
    164         self.label.setText(_translate("SendMailer", "服务器地址:", None))
    165         self.lineEditSMTP.setText(_translate("SendMailer", "自定义", None))
    166         self.label_2.setText(_translate("SendMailer", "用户名:", None))
    167         self.label_3.setText(_translate("SendMailer", "密码:", None))
    168         self.checkBoxRememberUP.setText(_translate("SendMailer", "记住用户名密码", None))
    169         self.groupBox_2.setTitle(_translate("SendMailer", "内容项", None))
    170         self.label_5.setText(_translate("SendMailer", "接收人:  ", None))
    171         self.label_6.setText(_translate("SendMailer", "多个用, 分隔开", None))
    172         self.label_7.setText(_translate("SendMailer", "邮件主题:", None))
    173         self.label_8.setText(_translate("SendMailer", "邮件正文:", None))
    174         self.label_4.setText(_translate("SendMailer", "邮件附件:", None))
    175         self.attachBtn.setText(_translate("SendMailer", "选择附件", None))
    176         self.labelSendMsg.setText(_translate("SendMailer", "    发送消息", None))
    177         self.sendingBtn.setText(_translate("SendMailer", "开始发送", None))
    178 
    179 
    180 if __name__ == "__main__":
    181     import sys
    182     app = QtGui.QApplication(sys.argv)
    183     SendMailer = QtGui.QWidget()
    184     ui = Ui_SendMailer()
    185     ui.setupUi(SendMailer)
    186     SendMailer.show()
    187     sys.exit(app.exec_())

    三. 逻辑的实现

    MainSendMailer.py

      1 # -*- coding: utf-8 -*-
      2 
      3 
      4 from PyQt4 import QtGui, QtCore
      5 from sendmail import Ui_SendMailer
      6 import os
      7 import icoqrc
      8 
      9 
     10 class SendingMail(QtGui.QWidget):
     11     def __init__(self, parent=None):
     12         super(SendingMail, self).__init__(parent)
     13         self.Ui= Ui_SendMailer()
     14         self.Ui.setupUi(self)
     15         self.setWindowTitle(u'Pyqt 邮件发送')
     16         self.setWindowIcon(QtGui.QIcon(':myfavicon.ico'))
     17         reload(sys)
     18         sys.setdefaultencoding("utf-8")
     19         #初始化UI项目
     20         self.proparam()
     21         # 获取配置项
     22         self.GetConfig()
     23         self.Ui.comboBoxServer.activated.connect(self.ServerSmtp)   # stmp服务器
     24         self.Ui.attachBtn.clicked.connect(self.SelAttach)    # 选择附件
     25         self.connect(self.Ui.sendingBtn,QtCore.SIGNAL("clicked()"), self.sending)
     26 
     27         # 发送进度
     28         self.timer = QtCore.QBasicTimer()
     29 
     30 
     31 
     32     # def初始化UI项目
     33     def proparam(self):
     34         self.Ui.comboBoxServer.addItem(u'选择服务地址',QtCore.QVariant(''))
     35         self.Ui.comboBoxServer.addItem(u'网易163',QtCore.QVariant('smtp.163.com'))
     36         self.Ui.comboBoxServer.addItem(u'腾讯邮箱',QtCore.QVariant('smtp.qq.com'))
     37         self.Ui.comboBoxServer.addItem(u'新浪邮箱',QtCore.QVariant('smtp.sina.com.cn'))
     38         self.Ui.comboBoxServer.addItem(u'搜狐邮箱',QtCore.QVariant('smtp.sohu.com'))
     39         self.Ui.comboBoxServer.addItem(u'Google邮箱',QtCore.QVariant('smtp.gmail.com'))
     40         self.Ui.comboBoxServer.addItem(u'自定义',QtCore.QVariant(''))
     41         # 隐藏发送进度和发送提示
     42         self.Ui.progressBarSend.hide()
     43         self.Ui.labelSendMsg.hide()
     44         # 记住密码配置密钥
     45 
     46         self.keyt=0xa1a2a3a8
     47 
     48     # stmp 服务器
     49     def ServerSmtp(self):
     50         comboxserver= self.Ui.comboBoxServer.currentIndex()
     51         comboxItemData= self.Ui.comboBoxServer.itemData(comboxserver)
     52         self.Ui.lineEditSMTP.setText(comboxItemData.toPyObject())
     53 
     54     # 选择附件  后期判断文件大小,显示格式等
     55     def SelAttach(self):
     56         files = QtGui.QFileDialog.getOpenFileName(self, u'选择附件')
     57         self.Ui.lineEditAttach.setText(files)
     58 
     59     # 配置项
     60     def GetConfig(self, sendingSucc=''):
     61         isConfig = os.path.exists(r'SendMailerConfig.ini')
     62         if isConfig and sendingSucc == '':  # 存在记住用户名和密码
     63             self.Ui.checkBoxRememberUP.setChecked(True)
     64             file = QtCore.QFile("SendMailerConfig.ini")
     65             file.open(QtCore.QIODevice.ReadOnly)
     66             In = QtCore.QDataStream(file)
     67             In.setVersion(QtCore.QDataStream.Qt_4_0)
     68             magic = In.readUInt32()
     69             if magic != self.keyt:
     70                 QtGui.QMessageBox.information(self,"exception",u"记住密码数据格式错误!")
     71                 return
     72             comboBoxServer = In.readUInt32()
     73             LoginUser = In.readString()
     74             LoginPasswd = In.readString()
     75             self.Ui.comboBoxServer.setCurrentIndex(comboBoxServer)
     76             comboxItemData = self.Ui.comboBoxServer.itemData(comboBoxServer)
     77             self.Ui.lineEditSMTP.setText(comboxItemData.toPyObject())
     78             self.Ui.lineEditUser.setText(str(LoginUser))
     79             self.Ui.lineEditPasswd.setText(str(LoginPasswd))
     80         # 发送成功判断记住密码
     81         if sendingSucc:
     82             isChecked = self.Ui.checkBoxRememberUP.isChecked()
     83             if isChecked:
     84                 file = QtCore.QFile("SendMailerConfig.ini")
     85                 self.time = QtCore.QDateTime()
     86                 file.open(QtCore.QIODevice.WriteOnly)
     87                 out = QtCore.QDataStream(file)
     88                 out.setVersion(QtCore.QDataStream.Qt_4_0)
     89                 out.writeUInt32(self.keyt)  # writeUInt32  参数为int类型
     90                 out.writeUInt32(self.Ui.comboBoxServer.currentIndex())
     91                 out.writeString(self.Ui.lineEditUser.text())  # writeString 参数为string类型
     92                 out.writeString(self.Ui.lineEditPasswd.text())
     93                 out << self.time.currentDateTime()
     94 
     95     # 发送邮件
     96     def sending(self):
     97         exist = self.basicExist()
     98         if exist:
     99             success = self.CoreAction()
    100             if success:
    101                 #判断是否记住密码
    102                 self.GetConfig('sendSuccess')
    103                 self.timer.start(10, self)
    104 
    105     # 引入smtplib 发送邮件
    106     def CoreAction(self):
    107         import smtplib
    108         from email.mime.text import MIMEText
    109         from email.mime.multipart import MIMEMultipart
    110         # 发送进度显示
    111         self.Ui.labelSendMsg.show()
    112         self.Ui.labelSendMsg.setText(u'正在发送……')
    113         self.Ui.progressBarSend.show()
    114         self.step = 0
    115         self.timer.start(1000, self)
    116 
    117 
    118 
    119         smtpConfig = {}  # 配置
    120         smtpConfig['Connect'] = str(self.Ui.lineEditSMTP.text())
    121         smtpConfig['LoginUser'] = str(self.Ui.lineEditUser.text())
    122         smtpConfig['LoginPasswd'] = str(self.Ui.lineEditPasswd.text())
    123 
    124         # 判断Longinuser
    125         isExist=smtpConfig['LoginUser'].find('@')
    126         if isExist==-1:
    127             smtpConfig['LoginUser'] = smtpConfig['LoginUser']+smtpConfig['Connect'].replace('smtp.', '@', 1)
    128 
    129 
    130 
    131         try:
    132             smtp = smtplib.SMTP()
    133             smtp.connect(smtpConfig['Connect'])
    134             smtp.login(smtpConfig['LoginUser'], smtpConfig['LoginPasswd'])
    135             msg = MIMEMultipart()
    136             msg['Subject'] = str(self.Ui.lineEditCheme.text())
    137             # 内容
    138             content = MIMEText(str(self.Ui.textEditBody.toPlainText()), 'html', 'utf-8')    # 获取textedit数据
    139             # 附件
    140             isExistAttach = str(self.Ui.lineEditAttach.text())
    141             if isExistAttach:  # 如果存在附件
    142                 filename = os.path.basename(isExistAttach)
    143                 attach = MIMEText(open(isExistAttach, 'rb').read(), 'base64', 'gb2312')
    144                 attach["Content-Type"] = 'application/octet-stream'
    145                 attach["Content-Disposition"] = 'attachment; filename="'+filename+'"'
    146                 msg.attach(attach)  # 可能有附件没有内容
    147 
    148             msg.attach(content)
    149             Receiver=str(self.Ui.lineEditReceiver.text())
    150             ListReceiver= Receiver.split(',')
    151             smtp.sendmail(smtpConfig['LoginUser'], ListReceiver, msg.as_string())   # 发送者 和 接收人
    152             smtp.quit()
    153             return True
    154 
    155         except Exception, e:
    156             QtGui.QMessageBox.warning(self, u'错误提示', str(e), QtGui.QMessageBox.Yes)
    157             # 发送失败隐藏发送进度
    158             self.Ui.labelSendMsg.setText(u'成功失败')
    159             self.Ui.labelSendMsg.hide()
    160             self.Ui.progressBarSend.hide()
    161             return False
    162 
    163 
    164     '''
    165      获取配置项目
    166     '''
    167     def basicExist(self):
    168         if self.Ui.lineEditSMTP.text() == '':
    169             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写SMTP服务地址'), QtGui.QMessageBox.Yes)
    170             return False
    171         if self.Ui.lineEditUser.text() == '':
    172             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写发送者用户名'), QtGui.QMessageBox.Yes)
    173             return False
    174         if self.Ui.lineEditPasswd.text() == '':
    175             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写发送者密码'), QtGui.QMessageBox.Yes)
    176             return False
    177         if self.Ui.lineEditReceiver.text() == '':
    178             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写接收者邮箱'), QtGui.QMessageBox.Yes)
    179             return False
    180         if self.Ui.lineEditCheme.text() == '':
    181             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写邮件标题'), QtGui.QMessageBox.Yes)
    182             return False
    183         return True
    184 
    185     def keyPressEvent(self, event):
    186         if event.key() ==QtCore.Qt.Key_Escape:
    187             Ok = QtGui.QMessageBox.question(self,u'提示', u'确定要退出吗?',QtGui.QMessageBox.Yes, QtGui.QMessageBox.No)
    188             if Ok == QtGui.QMessageBox.Yes:
    189                 self.close()
    190     # 重写timer
    191     def timerEvent(self,event):
    192         if self.step >= 100:
    193             self.timer.stop()
    194             self.Ui.labelSendMsg.show()
    195             self.Ui.labelSendMsg.setText(u"发送完成!")
    196             return
    197         self.step = self.step+1
    198         self.Ui.progressBarSend.setValue(self.step)
    199 
    200 
    201 
    202 if __name__ == '__main__':
    203     import sys
    204     app = QtGui.QApplication(sys.argv)
    205     appSendingMail = SendingMail()
    206     appSendingMail.show()
    207     sys.exit(app.exec_())

    运行效果:

    四. 问题 

    发送附件超过2M以上或 网速慢的时候主程序会等待相应直到邮件发送完成,解决办法:多线程实现! 

    多线程实现   by 2015-04-17

    以上因为主进程进行通信导致Ui堵塞界面假死,想到的办法就是Qthread 多进程,

    今天就实现多线程逻辑部分

      1 # -*- coding: utf-8 -*-
      2 
      3 
      4 from PyQt4 import QtGui, QtCore
      5 from sendmail import Ui_SendMailer
      6 import os
      7 import icoqrc
      8 
      9 
     10 class SendingMail(QtGui.QWidget):
     11     def __init__(self, parent=None):
     12         super(SendingMail, self).__init__(parent)
     13         self.Ui = Ui_SendMailer()
     14         self.Ui.setupUi(self)
     15         self.setWindowTitle(u'Pyqt 邮件发送')
     16         self.setWindowIcon(QtGui.QIcon(':myfavicon.ico'))
     17         reload(sys)
     18         sys.setdefaultencoding("utf-8")
     19         #初始化UI项目
     20         self.proparam()
     21         # 获取配置项
     22         self.GetConfig()
     23         self.Ui.comboBoxServer.activated.connect(self.ServerSmtp)   # stmp服务器
     24         self.Ui.attachBtn.clicked.connect(self.SelAttach)    # 选择附件
     25         self.connect(self.Ui.sendingBtn, QtCore.SIGNAL("clicked()"), self.CoreAction)
     26 
     27         # 发送进度
     28         self.timer = QtCore.QBasicTimer()
     29 
     30         
     31          32          33          34 
     35 
     36 
     37     # def初始化UI项目
     38     def proparam(self):
     39         self.Ui.comboBoxServer.addItem(u'选择服务地址',QtCore.QVariant(''))
     40         self.Ui.comboBoxServer.addItem(u'网易163',QtCore.QVariant('smtp.163.com'))
     41         self.Ui.comboBoxServer.addItem(u'腾讯邮箱',QtCore.QVariant('smtp.qq.com'))
     42         self.Ui.comboBoxServer.addItem(u'新浪邮箱',QtCore.QVariant('smtp.sina.com.cn'))
     43         self.Ui.comboBoxServer.addItem(u'搜狐邮箱',QtCore.QVariant('smtp.sohu.com'))
     44         self.Ui.comboBoxServer.addItem(u'Google邮箱',QtCore.QVariant('smtp.gmail.com'))
     45         self.Ui.comboBoxServer.addItem(u'自定义',QtCore.QVariant(''))
     46         # 隐藏发送进度和发送提示
     47         self.Ui.progressBarSend.hide()
     48         self.Ui.labelSendMsg.hide()
     49         # 记住密码配置密钥
     50 
     51         self.keyt=0xa1a2a3a8
     52 
     53     # stmp 服务器
     54     def ServerSmtp(self):
     55         comboxserver= self.Ui.comboBoxServer.currentIndex()
     56         comboxItemData= self.Ui.comboBoxServer.itemData(comboxserver)
     57         self.Ui.lineEditSMTP.setText(comboxItemData.toPyObject())
     58 
     59     # 选择附件  后期判断文件大小,显示格式等
     60     def SelAttach(self):
     61         files = QtGui.QFileDialog.getOpenFileName(self, u'选择附件')
     62         self.Ui.lineEditAttach.setText(files)
     63 
     64     # 配置项
     65     def GetConfig(self, sendingSucc=''):
     66         isConfig = os.path.exists(r'SendMailerConfig.ini')
     67         if isConfig and sendingSucc == '':  # 存在记住用户名和密码
     68             self.Ui.checkBoxRememberUP.setChecked(True)
     69             file = QtCore.QFile("SendMailerConfig.ini")
     70             file.open(QtCore.QIODevice.ReadOnly)
     71             In = QtCore.QDataStream(file)
     72             In.setVersion(QtCore.QDataStream.Qt_4_0)
     73             magic = In.readUInt32()
     74             if magic != self.keyt:
     75                 QtGui.QMessageBox.information(self,"exception",u"记住密码数据格式错误!")
     76                 return
     77             comboBoxServer = In.readUInt32()
     78             LoginUser = In.readString()
     79             LoginPasswd = In.readString()
     80             self.Ui.comboBoxServer.setCurrentIndex(comboBoxServer)
     81             comboxItemData = self.Ui.comboBoxServer.itemData(comboBoxServer)
     82             self.Ui.lineEditSMTP.setText(comboxItemData.toPyObject())
     83             self.Ui.lineEditUser.setText(str(LoginUser))
     84             self.Ui.lineEditPasswd.setText(str(LoginPasswd))
     85         # 发送成功判断记住密码
     86         if sendingSucc:
     87             isChecked = self.Ui.checkBoxRememberUP.isChecked()
     88             if isChecked:
     89                 file = QtCore.QFile("SendMailerConfig.ini")
     90                 self.time = QtCore.QDateTime()
     91                 file.open(QtCore.QIODevice.WriteOnly)
     92                 out = QtCore.QDataStream(file)
     93                 out.setVersion(QtCore.QDataStream.Qt_4_0)
     94                 out.writeUInt32(self.keyt)  # writeUInt32  参数为int类型
     95                 out.writeUInt32(self.Ui.comboBoxServer.currentIndex())
     96                 out.writeString(self.Ui.lineEditUser.text())  # writeString 参数为string类型
     97                 out.writeString(self.Ui.lineEditPasswd.text())
     98                 out << self.time.currentDateTime()
     99 
    100     # 发送邮件
    101     def CoreAction(self):
    102         validate = self.basicExist()
    103         if validate:
    104             # 发送进度显示
    105             self.Ui.labelSendMsg.show()
    106             self.Ui.labelSendMsg.setText(u'正在发送……')
    107             self.Ui.progressBarSend.show()
    108             self.Ui.progressBarSend.reset()  # 重置进度条
    109             self.step = 0
    110             self.timer.start(1000, self)
    111             DictData={}
    112             smtpConfig = {}  # 配置
    113             smtpConfig['Connect'] = str(self.Ui.lineEditSMTP.text())
    114             smtpConfig['LoginUser'] = str(self.Ui.lineEditUser.text())
    115             smtpConfig['LoginPasswd'] = str(self.Ui.lineEditPasswd.text())
    116             # 判断Longinuser
    117             isExist=smtpConfig['LoginUser'].find('@')
    118             if isExist==-1:
    119                 smtpConfig['LoginUser'] = smtpConfig['LoginUser']+smtpConfig['Connect'].replace('smtp.', '@', 1)
    120 
    121             DictData['smtpConfig'] = smtpConfig  # 配置
    122             DictData['Subject'] = str(self.Ui.lineEditCheme.text())  # 主题
    123             DictData['content'] = str(self.Ui.textEditBody.toPlainText())  # 内容
    124             DictData['attach'] = str(self.Ui.lineEditAttach.text())  # 附件
    125             Receiver=str(self.Ui.lineEditReceiver.text())
    126             DictData['ListReceiver'] = Receiver.split(',')
    127             self.Theading = Theading(DictData)
    128             self.connect(self.Theading, QtCore.SIGNAL("updateresult"), self.updateResult)  # 创建一个信号,在线程状态结果时发射触发
    129             self.Theading.start()  # 线程开始
    130             self.disconnect(self.Ui.sendingBtn, QtCore.SIGNAL("clicked()"),  self.CoreAction)  # 取消connect事件
    131             self.Ui.sendingBtn.setEnabled(False)
    132 
    133     #发送邮件后,进程触发事件
    134     def updateResult(self,status):
    135         if status['status']==1:  # 发送成功
    136             #判断是否记住密码
    137             self.GetConfig('sendSuccess')
    138             self.timer.start(10, self)
    139         else:  # 发送失败
    140             self.Ui.labelSendMsg.hide()
    141             self.Ui.progressBarSend.hide()
    142             QtGui.QMessageBox.warning(self, u'错误提示', status['msg'], QtGui.QMessageBox.Yes)
    143             self.connect(self.Ui.sendingBtn, QtCore.SIGNAL("clicked()"),  self.CoreAction)  # connect事件
    144             self.Ui.sendingBtn.setEnabled(True)
    145 
    146 
    147 
    148     '''
    149      获取配置项目
    150     '''
    151     def basicExist(self):
    152         if self.Ui.lineEditSMTP.text() == '':
    153             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写SMTP服务地址'), QtGui.QMessageBox.Yes)
    154             return False
    155         if self.Ui.lineEditUser.text() == '':
    156             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写发送者用户名'), QtGui.QMessageBox.Yes)
    157             return False
    158         if self.Ui.lineEditPasswd.text() == '':
    159             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写发送者密码'), QtGui.QMessageBox.Yes)
    160             return False
    161         if self.Ui.lineEditReceiver.text() == '':
    162             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写接收者邮箱'), QtGui.QMessageBox.Yes)
    163             return False
    164         if self.Ui.lineEditCheme.text() == '':
    165             QtGui.QMessageBox.warning(self, (u'提示'),(u'请填写邮件标题'), QtGui.QMessageBox.Yes)
    166             return False
    167         return True
    168     # 重写keypress事件
    169     def keyPressEvent(self, event):
    170         if event.key() ==QtCore.Qt.Key_Escape:
    171             Ok = QtGui.QMessageBox.question(self,u'提示', u'确定要退出吗?',QtGui.QMessageBox.Yes, QtGui.QMessageBox.No)
    172             if Ok == QtGui.QMessageBox.Yes:
    173                 self.close()
    174     # 重写timer
    175     def timerEvent(self,event):
    176         if self.step >= 100:
    177             self.timer.stop()
    178             self.Ui.labelSendMsg.show()
    179             self.Ui.labelSendMsg.setText(u"发送完成!")
    180             return
    181         self.step = self.step+1
    182         self.Ui.progressBarSend.setValue(self.step)
    183 
    184 
    185 
    186 class Theading(QtCore.QThread):
    187     def __init__(self, dict, parent=None):
    188         super(Theading, self).__init__(parent)
    189         self.dict = dict
    190     def run(self):
    191         #引入smtplib 发送邮件
    192         import smtplib
    193         from email.mime.text import MIMEText
    194         from email.mime.multipart import MIMEMultipart
    195         result={}
    196         result['status'] = 0
    197         result['msg'] = ''
    198         try:
    199             smtp = smtplib.SMTP()
    200             smtp.connect(self.dict['smtpConfig']['Connect'])
    201             smtp.login(self.dict['smtpConfig']['LoginUser'], self.dict['smtpConfig']['LoginPasswd'])
    202             msg = MIMEMultipart()
    203             msg['Subject'] = self.dict['Subject']
    204             # 内容
    205             content = MIMEText(self.dict['content'], 'html', 'utf-8')    # 获取textedit数据
    206             # 附件
    207             isExistAttach =self.dict['attach']
    208             if isExistAttach:  # 如果存在附件
    209                 filename = os.path.basename(isExistAttach)
    210                 attach = MIMEText(open(isExistAttach, 'rb').read(), 'base64', 'gb2312')
    211                 attach["Content-Type"] = 'application/octet-stream'
    212                 attach["Content-Disposition"] = 'attachment; filename="'+filename+'"'
    213                 msg.attach(attach)  # 可能有附件没有内容
    214             msg.attach(content)
    215             smtp.sendmail(self.dict['smtpConfig']['LoginUser'], self.dict['ListReceiver'], msg.as_string())   # 发送者 和 接收人
    216             smtp.quit()
    217             result['status'] = 1
    218 
    219         except Exception, e:
    220             result['msg'] = str(e)
    221 
    222         self.emit(QtCore.SIGNAL("updateresult"), result)
    223 
    224 if __name__ == '__main__':
    225     import sys
    226     app = QtGui.QApplication(sys.argv)
    227     appSendingMail = SendingMail()
    228     appSendingMail.show()
    229     sys.exit(app.exec_())
  • 相关阅读:
    LeetCode 45 Jump Game II
    LeetCode 54. Spiral Matrix
    LeetCode 53. Maximum Subarray
    LeetCode 52. N-Queens II
    智齿的秘密
    《婚姻故事》观影笔记
    为什么在linux系统下安装anaconda的时候会报错
    pandas时间序列学习笔记
    极大似然估计和最小二乘法
    粗糙集学习笔记
  • 原文地址:https://www.cnblogs.com/dcb3688/p/4332794.html
Copyright © 2011-2022 走看看