Search code examples
javaandroidemailgmailjakarta-mail

How to resolve javax.mail.AuthenticationFailedException


I have seen all answers on such question. But my mail doesnt send. Actually, it sends when i make the less google secure. But as for me its not a solution! Because it makes the gmail account non protected, also ppl who use the app dont want to make smth with their mail secure. So i have tried all suggested variants and read the Java Mail FAQ. And here is the code. Please, if there is a real solutions, help me. But please, dont suggest change google secure! I need the solution that does not require any actions from the app users.

public class Mail  {

    public Mail() {
        _host = "smtp.gmail.com"; // default smtp server
        _port = "587"; // default smtp port587

        _user = "[email protected]"; // username
        _pass = "password"; // password
        _from = "[email protected]"; // email sent from
        _to = {"[email protected]"};
        _subject = "go"; // email subject
        _body = "mail"; // email body

        _debuggable = true; // debug mode on or off - default off
        _auth = true; // smtp authentication - default on

        _multipart = new MimeMultipart();

        // There is something wrong with MailCap, javamail can not find a handler for the multipart/mixed part, so this bit needs to be added.
        MailcapCommandMap mc = (MailcapCommandMap) CommandMap.getDefaultCommandMap();
        mc.addMailcap("text/html;; x-java-content-handler=com.sun.mail.handlers.text_html");
        mc.addMailcap("text/xml;; x-java-content-handler=com.sun.mail.handlers.text_xml");
        mc.addMailcap("text/plain;; x-java-content-handler=com.sun.mail.handlers.text_plain");
        mc.addMailcap("multipart/*;; x-java-content-handler=com.sun.mail.handlers.multipart_mixed");
        mc.addMailcap("message/rfc822;; x-java-content-handler=com.sun.mail.handlers.message_rfc822");
        CommandMap.setDefaultCommandMap(mc);
    }

    public Mail(String user, String pass) {
        this();

        _user = user;
        _pass = pass;
    }

    public boolean send() throws Exception {
        Properties props = _setProperties();

        if(!_user.equals("") && !_pass.equals("") && _to.length > 0 && !_from.equals("") && !_subject.equals("") && !_body.equals("")) {

           Session session = Session.getInstance(props, new GMailAuthenticator(_user,_pass));

            MimeMessage msg = new MimeMessage(session);

            msg.setFrom(new InternetAddress(_from));

            InternetAddress[] addressTo = new InternetAddress[_to.length];
            for (int i = 0; i < _to.length; i++) {
                addressTo[i] = new InternetAddress(_to[i]);
            }
            msg.setRecipients(MimeMessage.RecipientType.TO, addressTo);
            msg.setSubject(_subject);
            msg.setSentDate(new Date());

            // setup message body
            BodyPart messageBodyPart = new MimeBodyPart();
            messageBodyPart.setText(_body);
            _multipart.addBodyPart(messageBodyPart);

            // Put parts in message
            msg.setContent(_multipart);

            // send email

            Transport t = session.getTransport("smtp");
            try {
                t.connect(_host, _user, _pass);
               t.sendMessage(msg, msg.getAllRecipients());

            } finally {
                t.close();
            }


            return true;
        } else {
            return false;
        }
    }

    private Properties _setProperties() {
        Properties props = new Properties();

        props.put("mail.smtp.host", _host);

        if(_debuggable) {
            props.put("mail.debug", "true");
        }

        if(_auth) {
            props.put("mail.smtp.auth", "true");
        }

        props.put("mail.smtp.port", _port);
        props.put("mail.smtp.starttls.enable", "true");
        props.put("mail.debug", "true");

        return props;
    }


    // class for secure access gmail

    class GMailAuthenticator extends Authenticator {
        String user;
        String pw;
        public GMailAuthenticator (String username, String password)
        {
            super();
            this.user = username;
            this.pw = password;
        }

        public PasswordAuthentication getPasswordAuthentication()
        {
            return new PasswordAuthentication(user, pw);
        }
    }

And the method send() i call in activity

final Button send = (Button) this.findViewById(R.id.send);
send.setOnClickListener(new View.OnClickListener() {

    public void onClick(View v) {
        // TODO Auto-generated method stub

       new SendClass().execute();

}
});

private class SendClass extends AsyncTask{

    @Override
    protected Object doInBackground(Object[] objects) {
        Mail m = new Mail();

        m.send();
        return null;
    }
}

Solution

  • I assume you're trying to use OAuth2, although nothing in your code indicates that. That's the only way to avoid configuring your account for "less secure apps". Using OAuth2 is much more complicated, this JavaMail web page will get you started.