Reading Messages  
 

The Post Office Protocol (POP3) and Internet Message Access Protocol (IMAP4) controls can be used to retrieve messages from the mail server for the client to process or store locally. Which protocol is used largely depends on what service the mail server supports. It is also important to remember that POP3 is a protocol that is primarily used with applications that store the messages locally; after a message has been downloaded, it is typically deleted from the server. On the other hand, IMAP4 is a protocol designed for clients that want to leave the messages on the server and manage those messages remotely.

Post Office Protocol

The Post Office Protocol gives you access to all of the messages that have arrived in a user's inbox. To read those messages, they must be downloaded one at a time and you must provide a message number which identifies the message that you wish to retrieve or store. The first message in the mailbox is number one, and it increases in order for each additional message. It is important to note that as new messages arrive and old messages are deleted from the mailbox, message numbers will not refer to the same message from session to session. In other words, if you connect to the server and retrieve message 12, disconnect and then re-connect, it is possible that message 12 will no longer be the same message that you previously downloaded. Your application should never depend on a message number referring to a specific message.

Here is an example of how to retrieve the first message in the user's mailbox:

Dim nMessageId As Long
Dim strMessage As String
Dim nError As Long

' Establish a connection to the mail server using the default port
' and the specified username and password
nError = PopClient1.Connect(strHostName, , strUserName, strPassword)
If nError Then
    MsgBox PopClient1.LastErrorString, vbExclamation
    Exit Sub
End If

If PopClient1.MessageCount = 0 Then
    MsgBox "There are no messages in this mailbox"
Else
    nMessageId = 1 ' Retrieve the first message from the mailbox
    nError = PopClient1.GetMessage(nMessageId, strMessage)

    ' If there were no errors, then use the Mail Message control
    ' to parse the message and update the interface
    If nError = 0 Then
        MailMessage1.Message = strMessage
        textFrom.Text = MailMessage1.From
        textTo.Text = MailMessage1.To
        textCc.Text = MailMessage1.Cc
        textDate.Text = MailMessage1.Date
        textSubject.Text = MailMessage1.Subject
        textMessage.Text = MailMessage1.Text
    Else
        MsgBox PopClient1.LastErrorString, vbExclamation
    End If
End If
    
PopClient1.Disconnect

In this example, the GetMessage method is used to retrieve the contents of the first message, message number 1, and store it in a string variable. If successful, then the Mail Message control is used to parse the message. This is easily done by assigning the Message property to the string which contains the message.

If you prefer to store the message on the local system, then you can use the StoreMessage method instead. It works in exactly the same way, except that instead of specifying a string or byte array, you specify the name of a file which will contain the message. If the file already exists it will be overwritten, otherwise it will be created.

For large messages, it can be useful to provide some sort of feedback to the user to let them know how much of the message has been downloaded. This can be easily done by adding an OnProgress event handler to update a ProgressBar control. For example:

Private Sub PopClient1_OnProgress(ByVal MessageNumber As Variant, _
                                  ByVal MessageSize As Variant, _
                                  ByVal MessageCopied As Variant, _
                                  ByVal Percent As Variant)
    ProgressBar1.Value = Percent
End Sub

As the message is being retrieved from the server, the OnProgress event will periodically fire which which cause the ProgressBar control to be updated with a new value.

Internet Message Access Protocol

The Internet Message Access Protocol enables you to access the messages in any of the user's mailboxes. To read those messages, you must specify the message number. The message numbers start with one and increase for each message in the mailbox. As with the Post Office Protocol, your application should never depend on a message number referring to a specific message. Messages that are deleted or moved from one mailbox to another may change the ordering of the messages. To identify messages over multiple client sessions, refer to the MessageUID property.

The following example retrieves the first message from the user's Inbox:

Dim nMessageId As Long
Dim strMessage As String
Dim nError As Long

' Establish a connection to the mail server using the default port
' and the specified username and password
nError = ImapClient1.Connect(strHostName, , strUserName, strPassword)
If nError Then
    MsgBox ImapClient1.LastErrorString, vbExclamation
    Exit Sub
End If

' Select the user's Inbox where new messages arrive
nError = ImapClient1.SelectMailbox("Inbox")
If nError Then
    MsgBox ImapClient1.LastErrorString, vbExclamation
    Exit Sub
End If

If ImapClient1.MessageCount = 0 Then
    MsgBox "There are no messages in this mailbox"
Else
    nMessageId = 1 ' Retrieve the first message from the mailbox
    nError = ImapClient1.GetMessage(nMessageId, 0, strMessage)

    ' If there were no errors, then use the Mail Message control
    ' to parse the message and update the interface
    If nError = 0 Then
        MailMessage1.Message = strMessage
        textFrom.Text = MailMessage1.From
        textTo.Text = MailMessage1.To
        textCc.Text = MailMessage1.Cc
        textDate.Text = MailMessage1.Date
        textSubject.Text = MailMessage1.Subject
        textMessage.Text = MailMessage1.Text
    Else
        MsgBox ImapClient1.LastErrorString, vbExclamation
    End If
End If

ImapClient1.Disconnect

This example is very similar to the code used with the POP3 control. The only significant changes are the use of the SelectMailbox method to select the user's Inbox, and the extra argument to the GetMessage method. Unlike the Post Office Protocol, IMAP4 has the ability to select specific sections of a multipart message and return them to the caller.

When working with multipart messages in the IMAP4 control, one important thing to keep in mind is that the IMAP4 protocol considers the first part of a multipart message to be part 1. Referencing part 0 tells the control that you want the entire multipart message including the main header block.

For large messages, it can be useful to provide some sort of feedback to the user to let them know how much of the message has been downloaded. This can be easily done by adding an OnProgress event handler to update a ProgressBar control. This is implemented in exactly the same way as it is for the POP3 control. For example:

Private Sub ImapClient1_OnProgress(ByVal MessageNumber As Variant, _
                                   ByVal MessageSize As Variant, _
                                   ByVal MessageCopied As Variant, _
                                   ByVal Percent As Variant)
    ProgressBar1.Value = Percent
End Sub

As the message is being retrieved from the server, the OnProgress event will periodically fire which which cause the ProgressBar control to be updated with a new value.