(Probably) all of you get email, and just like this guy next to this text, we all are very happy with it :-p
I recently switched from VB.NET 2003 to 2008 and I wanted to do something with e-mail. So here is a DLL to read/download (POP3) email and to send (SMTP) email.
For the ones who just want the code: (download below)
POP3
Imports System
Imports System.Net.Sockets
Imports System.Text
Imports System.IO
Public Class POP3
Private Shared Server As TcpClient
Private Shared NetStrm As NetworkStream
Private Shared RdStrm As StreamReader
Public Shared Function Connect(ByVal POP3Server As String, ByVal User As String, ByVal Password As String) As Boolean
If POP3Server.Trim = “” Then
Return False
End If
Try
Server = New TcpClient(POP3Server.Trim, 110)
NetStrm = Server.GetStream
RdStrm = New StreamReader(Server.GetStream)
Catch exc As Exception
Return False
End Try
If RunQuery(”USER ” & User.Trim).Substring(0, 3) <> “+OK” Then
Return False
End If
If RunQuery(”PASS ” & Password).Substring(0, 3) <> “+OK” Then
Return False
End If
Return True
End Function
Public Shared Sub Disconnect()
Dim data As String = “Quit ” & vbCrLf
Dim szData() As Byte = System.Text.Encoding.ASCII.GetBytes(data.ToCharArray())
NetStrm.Write(szData, 0, szData.Length)
Dim tmpString As String = RdStrm.ReadLine()
End Sub
Public Shared Function DeleteMessage(ByVal msgIndex As Integer) As Boolean
If RunQuery(”DELE ” & msgIndex.ToString).Substring(0, 4) = “-ERR” Then
Return False
Else
Return True
End If
End Function
Public Shared Function NumberOfMessages() As Integer
If RunQuery(”STAT”).Substring(0, 4) = “-ERR” Then
Return -1
End If
Dim Stat As String = RunQuery(”STAT”)
If Stat.Substring(0, 4) = “-ERR” Then
Return -1
End If
Dim Number() As String
Number = Stat.Split(” “)
Return CInt(Number(1))
End Function
Public Structure Message
Dim _From As String
Dim _To As String
Dim _Date As String
Dim _Subject As String
Dim _CC As String
Dim _BCC As String
Dim _Body As String
Dim _Received As String
End Structure
Public Function ReadMessage(ByVal MsgIndex As Integer) As Message
Dim Response As String
Dim MsgText As String = “”
Dim MsgReturn As New Message
Dim BrkPos As Integer
Dim Header As String
Dim Headers() As String
Dim Body As String
Dim HeaderName As String
Dim HeaderValue As String
Try
Response = RunQuery(”RETR ” & MsgIndex.ToString)
If Response.Substring(0, 4) <> “-ERR” Then
While (Response <> “.”)
MsgText = MsgText & Response & vbCrLf
Response = RdStrm.ReadLine
End While
End If
Catch exc As InvalidOperationException
Throw New Exception(”Message Retrival Failed: ” & vbCrLf & Err.ToString())
Exit Function
End Try
BrkPos = InStr(1, MsgText, vbCrLf & vbCrLf)
If BrkPos Then
Header = MsgText.Substring(0, BrkPos - 1)
Body = MsgText.Substring(BrkPos + 1, _
MsgText.Length - Header.Length - 3)
MsgReturn._Body = Body
Else
Throw New Exception(”Invalid Message Format”)
Exit Function
End If
Headers = Split(Header, vbCrLf)
Dim _header As String
For Each _header In Headers
BrkPos = _header.IndexOf(”:”)
If BrkPos >= 0 Then
HeaderName = _header.Substring(0, BrkPos)
Else
HeaderName = “”
End If
HeaderValue = _header.Substring(BrkPos + 1)
Select Case HeaderName.ToLower
Case “received”
MsgReturn._Received = HeaderValue
Case “from”
MsgReturn._From = HeaderValue
Case “to”
MsgReturn._To = HeaderValue
Case “cc”
MsgReturn._CC = HeaderValue
Case “bcc”
MsgReturn._BCC = HeaderValue
Case “subject”
MsgReturn._Subject = HeaderValue
Case “date”
MsgReturn._Date = HeaderValue
End Select
Next
Return MsgReturn
End Function
Private Shared Function RunQuery(ByVal Query As String) As String
Query = Query & vbCrLf
Dim Data() As Byte = System.Text.Encoding.ASCII.GetBytes(Query.ToCharArray())
NetStrm.Write(Data, 0, Data.Length)
Dim Response As String = RdStrm.ReadLine
Return Response
End Function
End Class
STMP
Imports System.Net.MailPublic
Class SMTPPublic
Shared Function SendMail(ByVal MServer As String, _
ByVal MFrom As String, _
ByVal MTo As String, _
ByVal MSubject As String, _
ByVal MBody As String, _
Optional ByVal MBodyHTML As Boolean = False, _
Optional ByVal MCC As String = Nothing, _
Optional ByVal MBCC As String = Nothing, _
Optional ByVal MAttachment As String = Nothing, _
Optional ByVal MServerUser As String = Nothing, _
Optional ByVal MServerPass As String = Nothing, _
Optional ByVal MServerPort As Integer = 25, _
Optional ByVal MServerSLL As Boolean = False) As Boolean
Try
Dim Mail As New System.Net.Mail.MailMessage
With Mail
.From = New MailAddress(MFrom)
.To.Add(MTo)
.Subject = MSubject
.IsBodyHtml = MBodyHTML
.Body = MBody
If MBCC = Not Nothing Then .Bcc.Add(MBCC)
If MCC = Not Nothing Then .CC.Add(MCC)
If MAttachment = Not Nothing Then
Dim attachments() As String = Strings.Split(MAttachment, “;”)
Dim i As Integer
For i = 0 To UBound(attachments)
.Attachments.Add(New Attachment(attachments(i)))
Next
End If
End With
Dim SMTP As New SmtpClient(MServer)
If MServerUser.Length + MServerPass.Length > 0 Then
SMTP.Credentials = New Net.NetworkCredential(MServerUser, MServerPass)
End If
SMTP.Port = MServerPort
SMTP.Host = MServer
SMTP.EnableSsl = MServerSLL
SMTP.Send(Mail)
SMTP = Nothing
Mail.Dispose()
Return True
Catch ex As Exception
Return False
End Try
End Function
End Class
Download MailProtocol DLL
For the one of us who just want the DLL file, also download it, the DLL file is in the ‘bin’-folder.I created this DLL in VB.NET 2008 but it might be easily convertible to older copies.
Pakku


June 23rd, 2008 at 1:31 pm
Hello,
Your MailProtocol DLL seems really wonderful, but for some bizarre reason I can’t seem to get it to work. It connects successfully to my mail server, and reports that there are no messages. Am I doing something wrong?
POP3.Connect(”pop.MYSERVER.com”, “MYEMAIL”, “MYPASSWORD”)
MsgBox(POP3.NumberOfMessages())
POP3.Disconnect()
I am using the server 1and1, if that helps.
June 23rd, 2008 at 1:32 pm
Argh… stupid smileys.
June 23rd, 2008 at 2:56 pm
@Michael B
POP3.NumberOfMessages() returns an integer. To show it in a MsgBos, you’ll need to convert it to a string by using POP3.NumberOfMessages().ToString
It also can return zero because there simply isn’t an e-mail message in your inbox
Pakku
June 24th, 2008 at 1:54 pm
Hello again,
I’m pretty sure you can msgbox integers too, but regardless there are messages in my inbox when I use this function and it still gives me a zero (even using the .ToString method).
My syntax is correct, isn’t it? And I’m using all of the necessary functions? I’ve tried reading specific E-Mails by index number and that doesn’t work either… is there something else going on?
June 24th, 2008 at 1:58 pm
Wait a minute…
Looking at your Connect code, at the very end it says Return True… even if it went through all that other stuff and was meant to Return False, won’t it just Return True regardless? Does this mean it may not be connecting to my server successfully and I just don’t know it?
June 24th, 2008 at 2:14 pm
And it’s me one more time.
It turns out I was probably wrong about the Connect function returning True all of the time, but either way I tried this with my Yahoo account now and it’s reporting -1, whether I use @yahoo.com or not. I know I’m using the right password too, and I checked my Yahoo mail manually and saw that there were a lot of messages in the Inbox.
Am I the only one having issues here? lol.
June 24th, 2008 at 2:48 pm
@Micael B
Are you sure your server(s) support POP3? Doesn’t block your firewall your connection?
You again
I tested it and for me it works fine. About the Return True thing, if you return something, the function exits itself, so after returning something, the next code will not be run.
Pakku
EDIT: I uploaded the code again, it might be that you have copied it in a strange way and that the code in your program is slightly different than mine.
June 24th, 2008 at 7:31 pm
I know 1and1 allows POP3 because I’ve used it in other applications (Microsoft Outlook and Outlook Express, for instance). I’m pretty sure Yahoo allows it too, or else why would they provide information for it?
Thanks for clearing up the Return thing for me, that’s good to know.
I’ll try the re-uploaded code and see if it works for me. Thanks!
June 24th, 2008 at 7:50 pm
Well, I tried the new, italicized code that you posted here on your page… I made a couple of new classes in my project and copied and pasted this to them (naming said classes POP3 and SMTP), and called the methods from those classes as before. Once again it said there were no messages on my server, and this time I even marked them all as unread and tried it… the same thing happened.
Could it still be a firewall problem? This isn’t the computer I use at home (although this is the computer I use Outlook with), so maybe I’ll try it at home and see if anything changes.
Could it be something else yet? Does anyone else use this code? This is the closest I’ve come to E-Mail functionality yet, heh.
June 24th, 2008 at 8:15 pm
Well, I’m not sure WHAT I did differently, but I fiddled around and got it to finally work! I can see that I have one E-Mail, and I figured out how to send mail as well. PHEW.
(My theory is that your function gets only the number of unread messages, and that it takes a while for a message to show up as “unread” if you mark it as such. I had read messages, and the ones I marked unread must not have refreshed with the server yet.)
Thanks for your help!
June 24th, 2008 at 8:22 pm
Umm, that was weird… it did work, and now it won’t again. Oh, son of a.
I got a 1 for number of messages, and I got a True for SendMail. It’s saying 0 again even though I haven’t touched my inbox, and the mail I supposedly sent never showed up.
Blargh, lol.
June 24th, 2008 at 8:25 pm
Wait again… the mail I sent did show up. So it’s just the reading of the mail that I’m having issues with.
Could I possibly spam this page more, by the way? Sorry about all this.
June 24th, 2008 at 10:46 pm
I finally figured it all out.
For 1and1, Outlook has been deleting the mail it downloads off of the server, but keeping it on the machine’s drive. I was under the illusion this whole time that the mail was still on the server, and it wasn’t.
The one time I saw 1 message, that E-Mail hadn’t been downloaded by Outlook yet.
And Yahoo doesn’t support free POP3, you have to sign up for it (and pay, I assume). So it connects but doesn’t allow me to do anything, which is why I keep getting -1 messages.
El oh el. I can’t believe it, it’s worked all along. Thanks for everything!
June 25th, 2008 at 10:21 am
@Michael B
Good to hear you figured it out. Outlook, Outlook Express, Windows Mail and likely most other mailcleint indeed downloads the mesages from the server and deletes them on the server. So this means that the functions only check the mail left on the server. If you use these functions after you checked your e-mail with the above programs, the functions should return 0 messages left (unless you just received a new mail) just because there are now messages left on the server because they are all on your own system.
Pakku