javax.mail.AuthenticationFailedException:连接失败,没有指定密码?

此程序尝试发送电子邮件但会引发运行时exception:

javax.mail.AuthenticationFailedException: failed to connect, no password specified? 

当我提供正确的用户名和密码进行身份validation时,为什么会出现此exception?

发件人和收件人都有g-mail帐号。 发件人和收件人都有g-mail帐号。 发件人已禁用两步validation流程。

这是代码:

 import javax.mail.*; import javax.mail.internet.*; import java.util.*; class tester { public static void main(String args[]) { Properties props = new Properties(); props.put("mail.smtp.host" , "smtp.gmail.com"); props.put("mail.stmp.user" , "username"); //To use TLS props.put("mail.smtp.auth", "true"); props.put("mail.smtp.starttls.enable", "true"); props.put("mail.smtp.password", "password"); //To use SSL props.put("mail.smtp.socketFactory.port", "465"); props.put("mail.smtp.socketFactory.class", "javax.net.ssl.SSLSocketFactory"); props.put("mail.smtp.auth", "true"); props.put("mail.smtp.port", "465"); Session session = Session.getDefaultInstance( props , null); String to = "me@gmail.com"; String from = "from@gmail.com"; String subject = "Testing..."; Message msg = new MimeMessage(session); try { msg.setFrom(new InternetAddress(from)); msg.setRecipient(Message.RecipientType.TO, new InternetAddress(to)); msg.setSubject(subject); msg.setText("Working fine..!"); Transport transport = session.getTransport("smtp"); transport.connect("smtp.gmail.com" , 465 , "username", "password"); transport.send(msg); System.out.println("fine!!"); } catch(Exception exc) { System.out.println(exc); } } } 

即使在给出密码后我也得到了例外。 为什么不进行身份validation?

尝试创建一个javax.mail.Authenticator对象,并将其与属性对象一起发送到Session对象。

validation者编辑:

您可以修改此选项以接受用户名和密码,您可以将它们存储在那里或任何您想要的地方。

 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; } 

在您发送电子邮件的class级中:

 SmtpAuthenticator authentication = new SmtpAuthenticator(); javax.mail.Message msg = new MimeMessage(Session .getDefaultInstance(emailProperties, authenticator)); 

您需要将对象身份validation作为参数添加到会话中。 如

 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 } }); 

现在你不会得到这种例外……

 javax.mail.AuthenticationFailedException: failed to connect, no password specified? 

您的电子邮件会话应该提供如下身份validation器实例

 Session session = Session.getDefaultInstance(props, new Authenticator() { protected PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication( "myemail@gmail.com", "password"); } }); 

一个完整的例子在这里http://bharatonjava.wordpress.com/2012/08/27/sending-email-using-java-mail-api/

除了RMT的答案。 我也不得不修改一下代码。

  1. 应该静态访问Transport.send
  2. 因此,transport.connect没有为我做任何事情,我只需要在初始的Properties对象中设置连接信息。

这是我的示例send()方法。 配置对象只是一个哑数据容器。

 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; } 

我已经解决了在Transport.send调用中添加用户和密码的问题:

 Transport.send(msg, "user", "password"); 

根据javax.mail中send函数的签名( 从1.5版开始 ):

public static void send(Message msg, String user, String password)

此外,如果使用此签名,则无需设置任何Authenticator ,也无需在“ Properties设置用户和密码(仅需要主机)。 所以你的代码可能是:

 private void sendMail(){ try{ Properties prop = System.getProperties(); prop.put("mail.smtp.host", "yourHost"); Session session = Session.getInstance(prop); Message msg = #createYourMsg(session, from, to, subject, mailer, yatta yatta...)#; Transport.send(msg, "user", "password"); }catch(Exception exc) { // Deal with it! :) } } 

可能值得validationgmail帐户由于多次登录尝试失败而未被锁定,您可能需要重置密码。 我和你有同样的问题,结果certificate这是解决方案。

我也有这个问题,所以不要担心。 由于外部身份validation问题,它来自邮件服务器端。 打开邮件,您将收到来自邮件服务器的邮件,告知您启用辅助function。 完成后,重试您的程序。

 import java.util.Properties; import javax.mail.Authenticator; import javax.mail.Message; import javax.mail.MessagingException; import javax.mail.PasswordAuthentication; import javax.mail.Session; import javax.mail.Transport; import javax.mail.internet.InternetAddress; import javax.mail.internet.MimeMessage; import com.opensymphony.xwork2.ActionSupport; import com.opensymphony.xwork2.ModelDriven; @SuppressWarnings("serial") public class RegisterAction { public String execute() { RegisterAction mailBean = new RegisterAction(); String subject="Your username & password "; String message="Hi," + username; message+="\n \n Your username is " + email; message+="\n \n Your password is " + password; message+="\n \n Please login to the web site with your username and password."; message+="\n \n Thanks"; message+="\n \n \n Regards"; //Getting FROM_MAIL String[] recipients = new String[1]; recipients[0] = new String(); recipients[0] = customer.getEmail(); try{ mailBean.sendMail(recipients,subject,message); return "success"; }catch(Exception e){ System.out.println("Error in sending mail:"+e); } return "failure"; } public void sendMail( String recipients[ ], String subject, String message) throws MessagingException { boolean debug = false; //Set the host smtp address Properties props = new Properties(); props.put("mail.smtp.host", "smtp.gmail.com"); props.put("mail.smtp.starttls.enable", true); props.put("mail.smtp.auth", true); // create some properties and get the default Session Session session = Session.getDefaultInstance(props, new Authenticator() { protected PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication( "username@gmail.com", "5373273437543");// Specify the Username and the PassWord } }); session.setDebug(debug); // create a message Message msg = new MimeMessage(session); InternetAddress[] addressTo = new InternetAddress[recipients.length]; for (int i = 0; i < recipients.length; i++) { addressTo[i] = new InternetAddress(recipients[i]); } msg.setRecipients(Message.RecipientType.TO, addressTo); // Optional : You can also set your custom headers in the Email if you Want //msg.addHeader("MyHeaderName", "myHeaderValue"); // Setting the Subject and Content Type msg.setSubject(subject); msg.setContent(message, "text/plain"); //send message Transport.send(msg); System.out.println("Message Sent Successfully"); } } 

即使使用Authenticator,我也必须将mail.smtp.auth属性设置为true。 这是一个工作示例:

 final Properties props = new Properties(); props.put("mail.smtp.host", config.getSmtpHost()); props.setProperty("mail.smtp.auth", "true"); Session session = Session.getDefaultInstance(props, new javax.mail.Authenticator() { protected PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication(config.getSmtpUser(), config.getSmtpPassword()); } }); 

在gmail帐户的安全设置中打开“访问安全性较低的应用程序”。(从邮件中),请参阅以下链接以获取参考

http://www.ghacks.net/2014/07/21/gmail-starts-block-less-secure-apps-enable-access/

此错误可能与密码字符有关。 如果您的密码包含特殊字符,并且您还将密码添加到Transport类方法中;

例如

 Transport transport = session.getTransport("smtp"); transport.connect("user","passw@rd"); 

要么

 Transport.send(msg, "user", "passw%rd"); 

你可能会得到那个错误。 因为Transport类的方法可能无法处理特殊字符。 如果您使用javax.mail.PasswordAuthentication类将您的用户名和密码添加到您的消息javax.mail.PasswordAuthentication ,我希望您将逃避该错误;

例如

 ... Session session = Session.getInstance(props, new javax.mail.Authenticator() { protected PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication("user", "pas$w@r|d"); } }); Message message = new MimeMessage(session); ... Transport.send(message); 

我刚刚面临这个问题,解决方案是属性“mail.smtp.user”应该是您的电子邮件(而不是用户名)。

gmail用户的示例:

 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");