How do I send a gmail email in vb.net? - vb.net

I want to send an email, but it gives me an error.
I have this code:
Sub sendMail(ByVal title As String, ByVal content As String)
Dim SmtpServer As New SmtpClient("smtp.gmail.com", 25)
SmtpServer.Credentials = New Net.NetworkCredential("name#gmail.com", "password")
Dim mail As New MailMessage("name#gmail.com", "name#gmail.com", title, content)
SmtpServer.Send(mail)
End Sub
I have a try catch which tries to call this method, it doesnt work so the catch runs and i get thes exception: System.Net.Mail.SmtpException: The SMTP server requires a secure connection or the client was not authenticated. The server response was: 5.7.0 Must issue a STARTTLS command first. b6sm3176487lae.0 - gsmtp Why do I get this error? and how do I fix it?

Gmail uses SMTP over SSL on port 465.
Try doing:
Dim SmtpServer As New SmtpClient("smtp.gmail.com", 465)
...
SmtpServer.EnableSsl = True
...

Try this - I know it works.
Dim Mail As New MailMessage
Dim SMTP As New SmtpClient("smtp.gmail.com")
Mail.Subject = "Security Update"
Mail.From = New MailAddress("name#gmail.com")
SMTP.Credentials = New System.Net.NetworkCredential("name#gmail.com", "password") '<-- Password Here
Mail.To.Add(address & "#gmail.com") 'I used ByVal here for address
Mail.Body = "" 'Message Here
SMTP.EnableSsl = True
SMTP.Port = "587"
SMTP.Send(Mail)

There is some problem with google account, you need to switch off some security settings. After sending email over and over, I received email on one of my support account (for google), the email were:
You recently changed your security settings so that your Google Account [trdjoko#gmail.com] is no longer protected by modern security standards.
If you did not make this change
Please review your Account Activity page at https://security.google.com/settings/security/activity to see if anything looks suspicious. Whoever made the change knows your password; we recommend that you change it right away.
If you made this change
Please be aware that it is now easier for an attacker to break into your account. You can make your account safer again by undoing this change at https://www.google.com/settings/security/lesssecureapps then switching to apps made by Google such as Gmail to access your account.
Sincerely,
The Google Accounts team
So I switched of additional security and i worked fine.

Change the port to 587. Port 25 does not support SSL.

A super easy way of doing this(without changing any security settings) is by using IFTTT and my IFTTT Maker.net libary
First, in IFTTT create a new recipe that's triggered by the Maker channel and name the event "send_gmail".
Then, select the Gmail engine and click "Send an email", and replace To with {{value1}}, subject with {{value2}} and message/body with {{value3}}
After that, in Visual studio, add ifttt.vb to your project. Now for the code:
Try
makechannel.scode = "your account ID"
makechannel.fireevent("send_gmail", "TO", "SUBJECT", "MESSAGE")
'code goes here if done
Catch ex As Exception
'code goes here if it fails
End Try
Then fill in your account ID. You can find it at ifttt.com/maker
And that's it!

I Have written the class which can perform this task easyly.
Imports System.Net.Mail
Public Class GGSMTP_GMAIL
Dim Temp_GmailAccount As String
Dim Temp_GmailPassword As String
Dim Temp_SMTPSERVER As String
Dim Temp_ServerPort As Int32
Dim Temp_ErrorText As String = ""
Dim Temp_EnableSSl As Boolean = True
Public ReadOnly Property ErrorText() As String
Get
Return Temp_ErrorText
End Get
End Property
Public Property EnableSSL() As Boolean
Get
Return Temp_EnableSSl
End Get
Set(ByVal value As Boolean)
Temp_EnableSSl = value
End Set
End Property
Public Property GmailAccount() As String
Get
Return Temp_GmailAccount
End Get
Set(ByVal value As String)
Temp_GmailAccount = value
End Set
End Property
Public Property GmailPassword() As String
Get
Return Temp_GmailPassword
End Get
Set(ByVal value As String)
Temp_GmailPassword = value
End Set
End Property
Public Property SMTPSERVER() As String
Get
Return Temp_SMTPSERVER
End Get
Set(ByVal value As String)
Temp_SMTPSERVER = value
End Set
End Property
Public Property ServerPort() As Int32
Get
Return Temp_ServerPort
End Get
Set(ByVal value As Int32)
Temp_ServerPort = value
End Set
End Property
Public Sub New(ByVal GmailAccount As String, ByVal GmailPassword As String, Optional ByVal SMTPSERVER As String = "smtp.gmail.com", Optional ByVal ServerPort As Int32 = 587, Optional ByVal EnableSSl As Boolean = True)
Temp_GmailAccount = GmailAccount
Temp_GmailPassword = GmailPassword
Temp_SMTPSERVER = SMTPSERVER
Temp_ServerPort = ServerPort
Temp_EnableSSl = EnableSSl
End Sub
Public Function SendMail(ByVal ToAddressies As String(), ByVal Subject As String, ByVal BodyText As String, Optional ByVal AttachedFiles As String() = Nothing) As Boolean
Temp_ErrorText = ""
Dim Mail As New MailMessage
Dim SMTP As New SmtpClient(Temp_SMTPSERVER)
Mail.Subject = Subject
Mail.From = New MailAddress(Temp_GmailAccount)
SMTP.Credentials = New System.Net.NetworkCredential(Temp_GmailAccount, Temp_GmailPassword) '<-- Password Here
Mail.To.Clear()
For i As Int16 = 0 To ToAddressies.Length - 1
Mail.To.Add(ToAddressies(i))
Next i
Mail.Body = BodyText
Mail.Attachments.Clear()
If AttachedFiles IsNot Nothing Then
For i As Int16 = 0 To AttachedFiles.Length - 1
Mail.Attachments.Add(New Attachment(AttachedFiles(i)))
Next
End If
SMTP.EnableSsl = Temp_EnableSSl
SMTP.Port = Temp_ServerPort
Try
SMTP.Send(Mail)
Return True
Catch ex As Exception
Me.Temp_ErrorText = ex.Message.ToString
Return False
End Try
End Function
End Class
Its the way, how to use class:
Dim GGmail As New GGSMTP_GMAIL("MyFromAddress1#gmail.com", "AccPassword", )
Dim ToAddressies As String() = {"ToAddress1#gmail.com", "ToAddress2#gmail.com"}
Dim attachs() As String = {"d:\temp_Excell226.xlsx", "d:\temp_Excell224.xlsx", "d:\temp_Excell225.xlsx"}
Dim subject As String = "My TestSubject"
Dim body As String = "My text goes here ...."
Dim result As Boolean = GGmail.SendMail(ToAddressies, subject, body, attachs)
If result Then
MsgBox("mails sended successfully", MsgBoxStyle.Information)
Else
MsgBox(GGmail.ErrorText, MsgBoxStyle.Critical)
End If
Hope this helps. Good coding

Related

Oauth 2.0 SMTP send email with EASendEmail VB

Following the changes, I try to connect and send mails via EAGetMail/EASendMail.
The connection is good, I have good access to the token and also to my mailbox.
However, when I want to send an email via "smtp.office365.com" I get an error: 535 5.7.3 Authentication unsuccessful.
I do not understand where the error can come from, I take the same token as when connecting to the mailbox.
Below is just the code to send emails, I have a token and it works perfectly to connect to my email
If someone has a project that works with smtp and Oauth 2.0 (without using a browser)...
Module Module1
Sub Main(ByVal args As String())
Try
RetrieveEmail()
Catch ep As Exception
Console.WriteLine(ep.ToString())
End Try
Console.ReadKey()
End Sub
Function _generateFileName(ByVal sequence As Integer) As String
Dim currentDateTime As DateTime = DateTime.Now
Return String.Format("{0}-{1:000}-{2:000}.eml",
currentDateTime.ToString("yyyyMMddHHmmss", New CultureInfo("en-US")),
currentDateTime.Millisecond,
sequence)
End Function
Function _postString(ByVal uri As String, ByVal requestData As String) As String
Dim httpRequest As HttpWebRequest = TryCast(WebRequest.Create(uri), HttpWebRequest)
httpRequest.Method = "POST"
httpRequest.ContentType = "application/x-www-form-urlencoded"
Using requestStream As Stream = httpRequest.GetRequestStream()
Dim requestBuffer As Byte() = Encoding.UTF8.GetBytes(requestData)
requestStream.Write(requestBuffer, 0, requestBuffer.Length)
requestStream.Close()
End Using
Try
Dim httpResponse As HttpWebResponse = TryCast(httpRequest.GetResponse(), HttpWebResponse)
Using reader As New StreamReader(httpResponse.GetResponseStream())
Dim responseText = reader.ReadToEnd()
Return responseText
End Using
Catch ex As WebException
If ex.Status = WebExceptionStatus.ProtocolError Then
Dim response = TryCast(ex.Response, HttpWebResponse)
If response IsNot Nothing Then
Console.WriteLine("HTTP: " & response.StatusCode)
' reads response body
Using reader As StreamReader = New StreamReader(response.GetResponseStream())
Dim responseText As String = reader.ReadToEnd()
Console.WriteLine(responseText)
End Using
End If
End If
Throw ex
End Try
End Function
Public Sub RetrieveEmail()
Try
Dim client_id As String = "XXXXXXXXXXXXXXXXXXXX"
Dim client_secret As String = "XXXXXXXXXXXXXXXXXXXXXXXXX"
' If your application is not created by Office365 administrator,
' please use Office365 directory tenant id, you should ask Offic365 administrator to send it to you.
' Office365 administrator can query tenant id in https://portal.azure.com/ - Azure Active Directory.
Dim tenant As String = "XXXXXXXXXXXXXXXXXX"
Dim requestData As String = String.Format("client_id={0}&client_secret={1}&scope=https://outlook.office365.com/.default&grant_type=client_credentials",
client_id, client_secret)
Dim tokenUri As String = String.Format("https://login.microsoftonline.com/{0}/oauth2/v2.0/token", tenant)
Dim responseText As String = _postString(tokenUri, requestData)
Dim parser As EASendMail.OAuthResponseParser = New EASendMail.OAuthResponseParser()
parser.Load(responseText)
Dim officeUser As String = "tma#XXXX.fr"
Dim oServerSend As SmtpServer = New SmtpServer("smtp.office365.com")
oServerSend.ConnectType = SmtpConnectType.ConnectSSLAuto
oServerSend.Port = 587
oServerSend.AuthType = SmtpAuthType.XOAUTH2
oServerSend.User = officeUser
oServerSend.Password = parser.AccessToken
Dim oMailSend As SmtpMail = New SmtpMail("TryIt")
oMailSend.From = "tma#XXX.fr"
' Please change recipient address to yours for test
oMailSend.[To] = "XXXXXXXXXXX"
oMailSend.Subject = "test email from Hotmail account with OAUTH 2"
oMailSend.TextBody = "this is a test email sent from VB.NET project with Hotmail."
Console.WriteLine("start to send email using OAUTH 2.0 ...")
Dim oSmtp As SmtpClient = New SmtpClient()
oSmtp.SendMail(oServerSend, oMailSend)
' Quit and expunge emails marked as deleted from server.
Console.WriteLine("Completed!")
Catch ep As Exception
Console.WriteLine(ep.ToString())
End Try
End Sub
End Module

"Object reference not set to an instance of an object." SQL Connection failing on .Open()

I am working on a VB app that uses a SQL Server database.
The issue I am having is that users are no longer able to login from the website.
However, when I run locally against the same database, it works just fine.
I have gone through the logs and determined its the SqlConnection() object that is throwing the
Object reference not set to an instance of an object.
error once oCn.Open() is called.
Public Function ValidLogin(ByVal EmpNum As String, ByVal Password As String, ByRef ErrMsg As String) As Boolean
Dim oCn As New SqlConnection(GetAPP2Password())
Dim oDr As SqlDataReader = Nothing
Dim oCmd As SqlCommand = Nothing
Dim sResponse As String = ""
ErrMsg = ""
Try
oCn.Open()
// do whatever else i need to do
Finally
oDr.Close()
oCn.Close()
oCmd.Dispose()
End Try
Return sResponse = "VALID"
Public Function GetAPP2Password() As String
Return sAPP2Password
End Function
this is the function that sets "sAPP2Password"
Public Function LoadPasswordString(ByVal databaseName As String) As String
'Reads a given setting from the <appSettings> section in the Web.config file.
'The setting key is prefixed with the current HostName to enable us to have one
'Web.config file that works for DVLP,ACPT and PROD with no mods required when
'moving between environments.
Dim strReturn As String = ""
Dim cc As New CECCoupler
strReturn = cc.getSecret(databaseName)
If InStr(strReturn, "Error:") Then ' check strReturn for ERROR
LogEvent("Globals.vb", "System", "Localhost", strReturn)
End If
Return strReturn
End Function
I am trying to figure out what the issue is on the application so I can get users back to logging in to the site.
below is the logged error from the application
Object reference not set to an instance of an object. at APP.APP2DataAccess.ValidLogin(String EmpNum, String Password, String& ErrMsg)
at APP.Login.cmdLogin_Click(Object sender, EventArgs e)

sending e-mail via exchange unsuccessfully

I can't find anywhere where I have a problem sending emails, it only happens to some users, while for others everything normally works with this code:
Dim service As New ExchangeService(requestedServerVersion:=ExchangeVersion.Exchange2013_SP1)
Sub SendMail(ByVal Mailadressen As List(Of String), ByVal CCAdressen As List(Of String), ByVal Betreff As String, ByVal MailText As String, ByVal Anhang As List(Of String), Optional ByVal Absender As String = "")
service.Url = New Uri("https://mail.server.com/ews/exchange.asmx")
'Add a valid user credentials
service.Credentials = New WebCredentials("someuser", "somepasw", "somedomain")
'To address the SSL challenge
ServicePointManager.ServerCertificateValidationCallback = New RemoteCertificateValidationCallback(AddressOf ValidateCertificate)
Try 'Create new message object and set properties required to send a mail
Dim sender As New Microsoft.Exchange.WebServices.Data.EmailAddress
Dim message As EmailMessage = New EmailMessage(service)
message.Subject = Betreff
message.Body = MailText
If Absender <> "" Then
Absender = Absender
sender.Address = Absender
message.From = sender
End If
For Each adr As String In Mailadressen
message.ToRecipients.Add(adr)
Next
For Each cc As String In CCAdressen
message.CcRecipients.Add(cc)
Next
For Each a As String In Anhang
message.Attachments.AddFileAttachment(a)
Next
message.SendAndSaveCopy()
Catch ex As Exception
MessageBox.Show(vbNewLine & "" & vbNewLine & String.Format("Error: {0}", ex.StackTrace))
End Try
End Sub
error I'm getting:
At Microsoft.Excange.WebServices.Data.ServiceRequestBase.GetEwsHttpWebResponse
(IEwsHttpWebRequest request) at
Microsoft.Excange.WebServices.Data.ServiceRequestBase.ValidateAndEmitRequest
(IEwsHttpWebRequest & request
.WebServices.Data.ExchangeService.InternalCreateItems (Inumerable1
items, FolderId parentFolderId, NUllable1 messageDisposition,
NUllable1 sendInvitationsMode, ServiceErrorHandling errorHandling) at
Microsoft.Excange.WebServices.Data.Item.InternalCreate1
messageDisposition1 .WebServices.Data.EmailMessage.InternalSend
(FolderId parentFolderId, MessageDisposition messageDispostition)
can you please give me some suggestion what could be the problem here? thanks a lot

checking login credentials to see if they are valid in Active Directory AND check to see if they are apart of a specific group in AD

below is a method used to check to see if the Creds entered are good. i also would like to add on to this to see if they are part of group "XXX".
Private Function ValidateActiveDirectoryLogin(ByVal Domain As String, ByVal Username As String, ByVal Password As String) As Boolean
Dim Success As Boolean = False
Dim Entry As New System.DirectoryServices.DirectoryEntry("LDAP://" + Domain, Username, Password)
Dim Searcher As New System.DirectoryServices.DirectorySearcher(Entry)
Searcher.SearchScope = DirectoryServices.SearchScope.OneLevel
Try
Dim Results As System.DirectoryServices.SearchResult = Searcher.FindOne
Success = Not (Results Is Nothing)
Catch ex As Exception
Success = False
End Try
Return Success
End Function
and below i tried to play around with stuff i found on stack but im not having much luck. how can i use existing method and add to it in order to get my results?
Public Function IsInGroup(ByVal UserName As String) As Boolean
'Dim MyIdentity As System.Security.Principal.WindowsIdentity = New WindowsPrincipal(New WindowsIdentity(UserName)) ' System.Security.Principal.WindowsIdentity.GetCurrent()
'Dim userPrincipal = New WindowsPrincipal(New WindowsIdentity(Username))
Dim MyPrincipal As System.Security.Principal.WindowsPrincipal = New WindowsPrincipal(New WindowsIdentity(UserName)) 'New System.Security.Principal.WindowsPrincipal(userPrincipal)
Return MyPrincipal.IsInRole("XXX_YYY")
End Function
Also Tried to do something like this but getting the error i screenshotted.
Public Function IsInGroup(ByVal UserName As String) As Boolean
Dim Result As Boolean
Dim de As New DirectoryEntry("LDAP://AD")
Dim MemberSearcher As New DirectorySearcher
With MemberSearcher
.SearchRoot = de
.Filter = "(&(ObjectClass=Group)(CN=VAL_ITS))"
.PropertiesToLoad.Add("Member")
End With
Dim mySearchResults As SearchResult = MemberSearcher.FindOne()
For Each User In mySearchResults.Properties("Member")
If User = UserName Then
Result = True
Else
Result = False
End If
Next
Return Result
End Function
'Project > Add Reference > System.DirectoryServices.AccountManagement & System.DirectoryServices
Validate using the System.DirectoryServices.AccountManagement namespace
Imports System.DirectoryServices.AccountManagement
Public function validate(username as string, password as string, domain as string)
Dim valid As Boolean = False
Using context As New PrincipalContext(ContextType.Domain, domain)
valid = context.ValidateCredentials(username, password)
End Using
return valid
End Function
Public function checkgroup(domain as string, username as string, groupname as string)
Dim isMember as boolean = false
Dim ctx As New PrincipalContext(ContextType.Domain, domain)
Dim user As UserPrincipal = UserPrincipal.FindByIdentity(ctx, username)
Dim group As GroupPrincipal = GroupPrincipal.FindByIdentity(ctx, groupname)
If user IsNot Nothing Then
If user.IsMemberOf(group) Then
isMember = True
End If
End If
return isMember
End Function

Test whether vb.net code working or not

Maybe this is a stupid question but I am really new in this field..
I am working about authentication in vb.net using AD. After doing some searching, I found a lot of codes related to this. for example:
Private m_ServerName As String
Private m_LoginName As String
Private m_Authenicate As String
Public Sub New()
' This call is required by the Windows Form Designer.
InitializeComponent()
' Add any initialization after the InitializeComponent() call.
m_ServerName = DOMAIN_NAME ' Your Domain Name
m_LoginName = Environment.UserName.ToString
m_Authenicate = My.User.Name
End Sub
Public Function IsLogonValid() As Boolean
Dim m_LoginName As String
Dim dirEntry As System.DirectoryServices.DirectoryEntry
Dim dirSearcher As System.DirectoryServices.DirectorySearcher
lblStatus.Text = "Validating User Account"
Try
m_LoginName = Environment.UserName.ToString 'The logged in user ID
dirEntry = New System.DirectoryServices.DirectoryEntry("LDAP://" & DOMAIN_NAME)
dirSearcher = New System.DirectoryServices.DirectorySearcher(dirEntry)
dirSearcher.Filter = "(samAccountName=" & m_LoginName & ")"
'Use the .FindOne() Method to stop as soon as a match is found
Dim sr As SearchResult = dirSearcher.FindOne()
If sr Is Nothing Then 'return false if user isn't found
lblStatus.Text = "User authentication failed"
Return False
End If
Dim de As System.DirectoryServices.DirectoryEntry = sr.GetDirectoryEntry()
sUserName = de.Properties("GivenName").Value.ToString()
lblStatus.Text = "User authentication success"
Return True 'Valid user
Catch ex As Exception ' return false if exception occurs
lblStatus.Text = "User authentication failed"
Return False
End Try
End Function
How can I know whether the code is working or not? Do I have to make a login form?
Just create a form with a textbox/label = lblStatus and run the function.