日期:2010-02-17  浏览次数:20429 次

用asp.net发送Email已经不是一件新鲜的事情了.可以采用很多种方法来发送,比如SmtpMail方法,Socket方法,通过第三方组件Jmail等方式都可以.但是本文讨论的不是发送邮件采用的技术,而是通过公司的一个项目(手机主题)实践说说邮件引擎的架构,有不足和改进之处,欢迎同行批评指正.

我们以前发送邮件的时候采用的方法就是,在页面里面触发进行发送,比如注册了会员,点了提交按钮之后,将会员数据插入到数据库,然后进行发送.这种方法虽然简单方便,但是有一个弱点,如果邮件发送失败,就不能重发了.因此,在我们项目中采用的方法是,将需要发送的邮件统一插入到一个邮件队列,然后由引擎来处理这个队列.具体的做法是,数据库设计:
Win_EmailQueue(邮件队列表)
QueueId    int   自动编号,主键Id
ToEmail    nvarchar(100)  收件人
Title      nvarchar(100)  邮件标题
Content    ntext          邮件内容
AddDate    datetime       添加时间
TryTimes   int            错误重试次数
LastSendTime datetime     最后一次发送的时间
Status     int            状态:0 未发送 1 已经发送

需要发送邮件的时候,如注册会员成功后,将邮件的内容插入到表中.

邮件引擎可以用一个系统服务来完成,安装在Web服务器同一台服务器上面,也可以根据负载实际情况安装在另外一台服务器上面,减轻Web服务器负担.邮件引擎的任务是间隔一个时间(比如5秒),查询邮件队列,根据时间顺序发送邮件,为了降低引擎的负担,可以设置每次发送15封,当然这个数字要根据实际情况来配置.

以下是处理队列和发送邮件的一些代码.

 ///
        /// 发送Email队列,来自 手机主题 http://www.shouji138.com
        ///
        public static void SendEmailQueue()
        {
            //取最新的15条未成功的进行发送。
            string sql = "select top 15 * from Win_EmailQueue where Status=0 and ToEmail<>'' order by AddDate desc";
            DataTable dt = DbHelperSQL.Query(sql).Tables[0];
            for (int i = 0; i < dt.Rows.Count; i++)
            {
                string title = dt.Rows[i]["Title"].ToString();
                string content = dt.Rows[i]["Content"].ToString();
                string to = dt.Rows[i]["ToEmail"].ToString();
                string CreateTime = dt.Rows[i]["AddDate"].ToString();
                string QueueID = dt.Rows[i]["QueueID"].ToString();
                bool flag = EmailUtil.Send(title, to, content);
                if (flag)
                {
      //发送成功,将Status设置为1
                    sql = "update  Win_EmailQueue set Status=1 where QueueID=" + QueueID + "";
                }
                else
                {
      //发送失败,将失败次数增加1
                    sql = "update&n