Tips for Improving Performance


No matter which technique or technology you choose to send SMTP messages in your application, it s going to be a time- intensive operation. More than likely, the time needed to connect to the SMTP server is going to be the dominant time in this operation. Let s look at a technique that you can apply to improve the performance of sending e-mail in your application.

Creating a Delivery Queue

To minimize the impact of sending SMTP messages on your application s overall performance, you should consider queuing SMTP messages for delivery. Ideally, this delivery would be done in a separate thread or process. ATL Server provides functionality to make building a queuing system into your application very simple:

 Using CSMTPConnection::WriteFile/CSMTPConnection::SendMessage 

CSMTPConnection::WriteFile allows you to write out the complete SMTP transcript to a file. CSMTPConnection::SendMessage can read from a file that contains an SMTP transcript and send it to the appropriate SMTP server. This pair allows you to easily build an SMTP queuing system into your application.

Let s look at how you can queue up SMTP messages for later delivery. Consider the code in Listing 24-7 for sending an SMTP message.

Listing 24.7: Sending an SMTP Message
start example
 1  CMimeMessage msg;  2  3  msg.SetSender("bogdanc@microsoft.com");  4  msg.SetSenderName("Bogdan Crivat");  5  msg.AddRecipient("bogdanc@microsoft.com",  "Bogdan Crivat");  6  msg.SetPriority(ATL_MIME_NORMAL_PRIORITY);  7  msg.SetSubject("Hello World!");  8  9  CAtlTemporaryFile smtpFile;  10 smtpFile.Create();  11  12 smtpConnection.WriteToFile( smtpFile.TempFileName(), msg); 
end example
 

The notable lines of Listing 24-7 are 9 through 12. In these lines, the CAtlTemporaryFile class gives you a convenient way to create a temporary, uniquely named file. The CSMTPConnection::WriteToFile method allows you to write out your message object to a file, rather than sending it directly. The contents of the file created by this code look like this:

 DATA  Date: Tue, 14 Aug 2001 22:58:48 -0700  From: Bogdan Crivat <bogdanc@microsoft.com>  Subject: Hello World!  To: "Bogdan Crivat" <bogdanc@microsoft.com>  X-Priority: 3  MIME-Version: 1.0  Content-Type: text/html;    charset="iso-8859-1"  Content-Transfer-Encoding: 8bit  <html>      <body>         <h1>Hello!</h1>         <br><br>         <p>Test</p>         <img href='http://msimg.com/m/r/logo/msft/logo.gif'>Hello World!</img>      </body>  </html> 

This is the exact text that CSMTPConnection will send to a SMTP server when it s actually sending the message. For security reasons, you should make sure that these files are written to a directory structure whose file permissions deny access to the account that IIS is running under.

Now you have one half of SMTP message queuing system. Each time you call WriteToFile , you ll create a file with an SMTP transcript like the previous one. Let s now look at the code for a simple client that will process these transcripts.

Processing the Delivery Queue

In the interest of brevity, you ll create a simple console application to process these SMTP transcripts. You could use the Windows Task Scheduler to run this process on a regular basis to process messages, or you could create a Windows service with this functionality. Consider the code in Listing 24-8.

Listing 24.8: A Simple Application for Processing a Delivery Queue
start example
 1 int main(int argc, _TCHAR **argv)  2 {  3    ASSERT(argc);  4    ASSERT(argv);  5  6    if (argc != 1)  7    {  8      printf("usage: smtpclient <smtp server name> <smtp file directory>\n");  9      return 1;  10    }  11  12    _TCHAR *smtpServerName = NULL;  13    smtpServerName = argv[1];  14  15    _TCHAR *smtpFileDirectory = NULL;  16    smtpFileDirectory= argv[2];  17  18    HRESULT hr = E_FAIL;  19    hr = CoInitialize(NULL);  20  21    ASSERT(SUCCEEDED(hr));  22    if (FAILED(hr))  23    {  24      return 1;  25    }  26  27    CSMTPConnection smtpConnection;  28    if (!smtpConnection.Connect(smtpServerName))  29    {  30      return 1;  31    }  32  33    BOOL  hasMoreFiles = TRUE;  34    HANDLE tempHandle   = NULL;  35    WIN32_FIND_DATA findFileData;  36    ZeroMemory(&findFileData, sizeof(findFileData));  37  38    CHandle fileHandle(FindFirstFile(smtpFileDirectory, &findFileData));  39  40    while (fileHandle != INVALID_HANDLE_VALUE &&  41           hasMoreFiles)  42    {  43        smtpConnection.SendMessage(findFileData.cFileName);  44  45        hasMoreFiles = FindNextFile(fileHandle, &findFileData);  46    }  47 } 
end example
 

Let s look at the important parts of this code line-by-line :

  • Lines 12 through 16: Take the name of your SMTP server and directory where the SMTP transcripts are located as command-line parameters.

  • Lines 33 through 38: Use the Win32 API to find all of your SMTP transcript files.

  • Line 43: For each SMTP transcript file, call CSMTPConnection::SendMessage to send the SMTP message. You can optionally specify alternate recipients and senders as parameters to this method. By default, CSMTPConnection will assume that the recipients and senders are in the SMTP transcript file.

That s all the code necessary to implement a queued SMTP delivery system in your application. When you execute the actual SMTP send operation in a separate client executable, your main application is free to process requests without having to wait for a response from a SMTP server.




ATL Server. High Performance C++ on. NET
Observing the User Experience: A Practitioners Guide to User Research
ISBN: B006Z372QQ
EAN: 2147483647
Year: 2002
Pages: 181

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net