在此预定控制台应用中实施电子邮件生成的最佳方式

时间:2013-11-11 22:15:55

标签: c# email console-application email-attachments email-integration

我之前从未以编程方式生成和发送过电子邮件通知。我需要做的是,如果此程序无法移动文件或遇到异常以生成电子邮件并且(最好)将Log.txt文件附加到电子邮件然后发送它。此应用程序将从企业计划程序运行并运行1 /小时来管理文件和文件夹。

以下是我目前使用的功能代码(尚无电子邮件实施)我已在我要发送电子邮件的位置发表了评论

using System;
using System.Configuration;
using System.IO;
using System.Net;
using System.Net.Mail;
using System.Runtime.InteropServices;

namespace FileOrganizer
{
   class Program
   {
      //These are the folder to organize and delimeter that is in the filenames to split off a folder from
      static string folder = ConfigurationManager.AppSettings["folder"]; //"C:\Users\MyUserName\Desktop\Organize Me"
      static string delim = ConfigurationManager.AppSettings["delim"]; // delim = "__"

      //location for the log.txt file
      static string logPath = ConfigurationManager.AppSettings["logPath"]; //C:\Users\MyUserName\Desktop\Log.txt

      //contact list from the app.config
      static string emailTo = ConfigurationManager.AppSettings["notifyEmailAddress"]; //multiple email addresses delimited by a ; example = tom@domain.com;dick@differentDomain.com;harry@domain.com

      //for the log.txt reporting
      static int filesMoved = 0;
      static int filesNOTmoved = 0;
      static string fileNamesNOTmoved = "";
      static int foldersCreated = 0;
      static string message = "";
      static string stackTrace = "";
      //used for passing all the objects into the log method
      static object[] details = new object[6];

      static void Main(string[] args)
      {
         try
         { 
            using (StreamWriter w = File.AppendText(logPath))
            {
               int total = organizeFolder(delim, folder);
               details[0] = filesMoved;
               details[1] = filesNOTmoved;
               details[2] = fileNamesNOTmoved;
               details[3] = foldersCreated;
               details[4] = "No Errors Found";
               details[5] = "No Errors Found";
               Log(details, w);
               if (filesNOTmoved > Convert.ToInt32(filesNOTmoved))
               {
                  //generate email to notify of filesNames not moved (prefer to send Log.txt as attachment)
               }
            }
            using (StreamReader r = File.OpenText(logPath))
            {
               DumpLog(r);
            }
         }
         catch (Exception ex)
         {
            using (StreamWriter w = File.AppendText(logPath))
            {
               details[0] = filesMoved;
               details[1] = filesNOTmoved;
               details[2] = fileNamesNOTmoved;
               details[3] = foldersCreated;
               details[4] = ex.Message.ToString();
               details[5] = ex.StackTrace.ToString();
               Log(details, w);
            }
            //generate email to notify of Error and (prefer to send Log.txt as attachment)
            using (StreamReader r = File.OpenText(logPath))
            {
               DumpLog(r);
            }
         }   
      }   

      /*Takes a folder and organizes it into folder by naming folder whatever 
       * is in front of the delimeter Example -->(folderName__fileName.txt would be moved 
       * to a new or existing folder named folderName.  Final path for file would 
       * look like this folderName\folderName__fileName.txt)
       * 
       * It will not move file if it already exists in the new location, instead
       * it prompts user that they should rename file and run program again.*/
       static int organizeFolder(string delimeter, string rootPath)
       {
          //counter for total files in Folder
          int Count = 0;
          int totalMoved = 0;

          FileInfo[] fileNames;
          DirectoryInfo di = new DirectoryInfo(rootPath);

          //set all file names as a string from network directory into an array  
          fileNames = di.GetFiles("*.*");
          Count = fileNames.Length;

          //Count = 0;//just to test exception handling

          //if no files exist in network folder throw error message.
          if (Count == 0)
          {
             fileNamesNOTmoved = "No Files Were In Directory to Move."; 
          }
          else //files exist in network folder
          {
             int delimIndex = 0;
             string folderName;
             for (int i = 0; i < Count; i++)
             {
                if (fileNames[i].ToString().Contains(delimeter))
                {
                   delimIndex = fileNames[i].ToString().IndexOf(delimeter);
                   folderName = fileNames[i].ToString().Substring(0, delimIndex);
                   //if folder doesnt exist create it here.
                   folderCreation(rootPath, folderName);
                   if (!File.Exists(rootPath + @"\" + folderName + @"\" + fileNames[i].Name))
                   {
                      File.Move(rootPath + @"\" + fileNames[i].ToString(), rootPath + @"\" + folderName + @"\" + fileNames[i].Name);
                      filesMoved++;
                   }
                   else
                   {
                      if (fileNamesNOTmoved == "")
                         fileNamesNOTmoved += "| ";
                      fileNamesNOTmoved += fileNames[i].Name + " | ";
                      filesNOTmoved++;
                   }
                   totalMoved++;
                }
             }
          } 
          return totalMoved;
       }

       //if folder does not exist this method will create it
       private static void folderCreation(string strTempPath, string folderName)
       {
          strTempPath = strTempPath + @"\" + folderName;
          if (!Directory.Exists(strTempPath))
          {
             //Create \folderName
             Directory.CreateDirectory(strTempPath);
             foldersCreated++;
          }
       }

       //adds entries to the log.txt file
       public static void Log(object[] details, TextWriter w)
       {
          w.Write("\r\nLog Entry : ");
          w.WriteLine("{0} {1}", DateTime.Now.ToShortTimeString(), DateTime.Now.ToShortDateString());
          w.WriteLine("  :");
          w.WriteLine("  :{0}", "Files Moved = " + details[0].ToString());
          w.WriteLine("  :{0}", "Folders Created = " + details[3].ToString());
          w.WriteLine("  :{0}", "Files Not Moved = " + details[1].ToString());
          w.WriteLine("  :{0}", "Files Names Not Moved = {" + details[2].ToString() + "}");
          w.WriteLine("  :{0}", "Error Message = " + details[4].ToString());
          w.WriteLine("  :{0}", "Error Stack Trace = " + details[5].ToString());
          w.WriteLine("---------------------------------------------------------------------------------------");
       }

       public static void DumpLog(StreamReader r)
       {
          string line;
          while ((line = r.ReadLine()) != null)
          {
             Console.WriteLine(line);
          }
       }
    }
}   

基本上希望电子邮件说:

  1. 主题:数据管理错误通知
  2. 正文:这是一封自动生成的电子邮件,可通知您 尝试清理目录中的文件时出错。 有关更多详细信息,请参阅Attached Log.txt文件。
  3. 附件:Log.txt

1 个答案:

答案 0 :(得分:0)

事实证明,SMTP是要走的路。由于我本地机器的限制,我只能从Dev,Qua和&amp ;; Prd服务器。从任何这些地点作为管理员进行测试..电子邮件发送完美!!!

使用App.Config保存我的所有To,Froms和SMTP主机信息,并将HTML作为字符串对象传递给方法,这是我用来发送电子邮件的方法。

    public static void sendMail(string msg)
    {
        SmtpClient smtpClient = new SmtpClient();
        MailMessage message = new MailMessage();
        MailAddress fromAddress = new MailAddress(emailFrom);
        smtpClient.Host = smtpHost;
        message.From = fromAddress;
        message.Subject = "Test Email";
        message.IsBodyHtml = true;
        message.Body = msg;
        message.To.Add(emailTo);
        message.Priority = MailPriority.High;
        smtpClient.Send(message);
    }