This program attempts to send e-mail but throws a run time exception:
javax.mail.AuthenticationFailedException: failed to connect, no password specified?
Try to create an javax.mail.Authenticator Object, and send that in with the properties object to the Session object.
Authenticator edit:
You can modify this to accept a username and password and you can store them there, or where ever you want.
public class SmtpAuthenticator extends Authenticator {
public SmtpAuthenticator() {
super();
}
@Override
public PasswordAuthentication getPasswordAuthentication() {
String username = "user";
String password = "password";
if ((username != null) && (username.length() > 0) && (password != null)
&& (password.length () > 0)) {
return new PasswordAuthentication(username, password);
}
return null;
}
In your class where you send the email:
SmtpAuthenticator authentication = new SmtpAuthenticator();
javax.mail.Message msg = new MimeMessage(Session
.getDefaultInstance(emailProperties, authenticator));
In addition to RMT's answer. I also had to modify the code a bit.
here is my sample send() methods. The config object is just a dumb data container.
public boolean send(String to, String from, String subject, String text) {
return send(new String[] {to}, from, subject, text);
}
public boolean send(String[] to, String from, String subject, String text) {
Properties props = new Properties();
props.put("mail.smtp.auth", "true");
props.put("mail.smtp.host", config.host);
props.put("mail.smtp.user", config.username);
props.put("mail.smtp.port", config.port);
props.put("mail.smtp.password", config.password);
Session session = Session.getInstance(props, new SmtpAuthenticator(config));
try {
Message message = new MimeMessage(session);
message.setFrom(new InternetAddress(from));
InternetAddress[] addressTo = new InternetAddress[to.length];
for (int i = 0; i < to.length; i++) {
addressTo[i] = new InternetAddress(to[i]);
}
message.setRecipients(Message.RecipientType.TO, addressTo);
message.setSubject(subject);
message.setText(text);
Transport.send(message);
} catch (MessagingException e) {
e.printStackTrace();
return false;
}
return true;
}
Your email session should be provided an authenticator instance as below
Session session = Session.getDefaultInstance(props,
new Authenticator() {
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(
"myemail@gmail.com", "password");
}
});
a complete example is here http://bharatonjava.wordpress.com/2012/08/27/sending-email-using-java-mail-api/
You need to add the Object Authentication as the Parameter to the Session. such as
Session session = Session.getDefaultInstance(props,
new javax.mail.Authenticator(){
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(
"XXXX@gmail.com", "XXXXX");// Specify the Username and the PassWord
}
});
now You will not get this kind of Exception....
javax.mail.AuthenticationFailedException: failed to connect, no password specified?
First of all, enable the less secure app in your Gmail account from which you will send emails using this link:- https://myaccount.google.com/lesssecureapps?pli=1
Then you simply add the following code in your session creation. It will work fine then.
Session mailSession = Session.getInstance(props, new javax.mail.Authenticator(){
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(
"your_email", "your_password");// Specify the Username and the PassWord
}
});
if you want the more elaborated one use the following:-
import java.util.Properties;
import javax.mail.Message;
import javax.mail.MessagingException;
import javax.mail.NoSuchProviderException;
import javax.mail.PasswordAuthentication;
import javax.mail.Session;
import javax.mail.Transport;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeBodyPart;
import javax.mail.internet.MimeMessage;
import javax.mail.internet.MimeMultipart;
public class MailSender {
public Properties mailProperties() {
Properties props = new Properties();
props.setProperty("mail.transport.protocol", "smtp");
props.setProperty("mail.smtp.host", "smtp.gmail.com");
props.setProperty("mail.smtp.port", "587");
props.setProperty("mail.smtp.user", "your_email");
props.setProperty("mail.smtp.password", "your_password");
props.setProperty("mail.smtp.starttls.enable", "true");
props.setProperty("mail.smtp.auth", "true");
return props;
}
public String sendMail(String from, String to, String subject, String msgBody) {
Properties props = mailProperties();
Session mailSession = Session.getInstance(props, new javax.mail.Authenticator(){
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(
"your_email", "your_password");// Specify the Username and the PassWord
}
});
mailSession.setDebug(false);
try {
Transport transport = mailSession.getTransport();
MimeMessage message = new MimeMessage(mailSession);
message.setSubject(subject);
message.setFrom(new InternetAddress(from));
message.addRecipients(Message.RecipientType.TO, to);
MimeMultipart multipart = new MimeMultipart();
MimeBodyPart messageBodyPart = new MimeBodyPart();
messageBodyPart.setContent(msgBody, "text/html");
multipart.addBodyPart(messageBodyPart);
message.setContent(multipart);
transport.connect();
transport.sendMessage(message, message.getRecipients(Message.RecipientType.TO));
transport.close();
return "SUCCESS";
} catch (NoSuchProviderException e) {
e.printStackTrace();
return "INVALID_EMAIL";
} catch (MessagingException e) {
e.printStackTrace();
}
return "ERROR";
}
public static void main(String args[]) {
System.out.println(new MailSender().sendMail("your_email/from_email", "to_email", "Subject", "Message"));
}
}
Hope! it helps. Thanks!
I have just faced this problem, and the solution is that the property "mail.smtp.user" should be your email (not username).
The example for gmail user:
properties.put("mail.smtp.starttls.enable", "true");
properties.put("mail.smtp.host", host);
properties.put("mail.smtp.user", from);
properties.put("mail.smtp.password", pass);
properties.put("mail.smtp.port", "587");
properties.put("mail.smtp.auth", "true");