Exchange server will not accept username/password provided with javax.mail API
Apparently, MS Exchange SSL connection is not established properly by Java Mail API. It relies on using SSLSocketFactory
for that, but, if I remember correctly, MS Exchange requires a somewhat mixed approach.
Anyway, I have this piece of code in one of my projects:
import javax.net.SocketFactory;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManager;
import javax.net.ssl.*;
import java.io.IOException;
import java.net.InetAddress;
import java.net.Socket;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
public class ExchangeSSLSocketFactory extends SSLSocketFactory {
private SSLSocketFactory sslSocketFactory;
private SocketFactory socketFactory;
public ExchangeSSLSocketFactory() {
try {
socketFactory = SocketFactory.getDefault();
SSLContext context = SSLContext.getInstance("TLS");
context.init(null, new TrustManager[] { new EmptyTrustManager() }, null);
sslSocketFactory = (SSLSocketFactory)context.getSocketFactory();
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
private final class EmptyTrustManager implements X509TrustManager {
public void checkClientTrusted(X509Certificate[] cert, String authType) throws CertificateException {}
public void checkServerTrusted(X509Certificate[] cert, String authType) throws CertificateException {}
public X509Certificate[] getAcceptedIssuers() {
return new java.security.cert.X509Certificate[0];
}
}
public static SocketFactory getDefault() {
return new ExchangeSSLSocketFactory();
}
@Override
public Socket createSocket(Socket socket, String s, int i, boolean flag) throws IOException {
return sslSocketFactory.createSocket(socket, s, i, flag);
}
@Override
public Socket createSocket(InetAddress inaddr, int i, InetAddress inaddr1, int j) throws IOException {
return socketFactory.createSocket(inaddr, i, inaddr1, j);
}
@Override
public Socket createSocket(InetAddress inaddr, int i) throws IOException {
return socketFactory.createSocket(inaddr, i);
}
@Override
public Socket createSocket(String s, int i, InetAddress inaddr, int j) throws IOException {
return socketFactory.createSocket(s, i, inaddr, j);
}
@Override
public Socket createSocket(String s, int i) throws IOException {
return socketFactory.createSocket(s, i);
}
@Override
public Socket createSocket() throws IOException {
return socketFactory.createSocket();
}
@Override
public String[] getDefaultCipherSuites() {
return sslSocketFactory.getSupportedCipherSuites();
}
@Override
public String[] getSupportedCipherSuites() {
return sslSocketFactory.getSupportedCipherSuites();
}
}
You tell the Java Mail API to use this socket factory by setting following properties:
ssl.SocketFactory.provider
mail.smtp.socketFactory.class
to full class name of ExchangeSSLSocketFactory
From your debug output, it seems that you already have:
mail.smtp.starttls.enable
set to true
With all this in place, the problem should be solved.
Comments
-
Ami almost 4 years
I have a lovely little Java client that sends signed email messages. We have an Exchange server that requires username/password authentication to send a message.
When I connect to the exchange server, I get this error:
avax.mail.AuthenticationFailedException: failed to connect at javax.mail.Service.connect(Service.java:322) at javax.mail.Service.connect(Service.java:172)
When I connect to other servers (Unix servers), I have no problem.
Below is the full debug trace. I can't figure it out.
DEBUG: JavaMail version 1.4.2 DEBUG: successfully loaded resource: /META-INF/javamail.default.providers DEBUG: Tables of loaded providers DEBUG: Providers Listed By Class Name: {com.sun.mail.smtp.SMTPSSLTransport=javax.mail.Provider[TRANSPORT,smtps,com.sun.mail.smtp.SM} DEBUG: Providers Listed By Protocol: {imaps=javax.mail.Provider[STORE,imaps,com.sun.mail.imap.IMAPSSLStore,Sun Microsystems, Inc], } DEBUG: successfully loaded resource: /META-INF/javamail.default.address.map DEBUG: getProvider() returning javax.mail.Provider[TRANSPORT,smtp,com.sun.mail.smtp.SMTPTransport,Sun Microsystems, Inc] DEBUG SMTP: useEhlo true, useAuth true DEBUG SMTP: trying to connect to host "SERVER", port 25, isSSL false 220 SERVER ESMTP (deca81216f2ecf4fd6fedb030e3dcfd0) DEBUG SMTP: connected to host "SERVER", port: 25 EHLO CLIENT 250-SERVER Hello CLIENT [192.1.1.1], pleased to meet you 250-STARTTLS 250-PIPELINING 250-SIZE 100000000 250-AUTH LOGIN PLAIN 250-AUTH=LOGIN PLAIN 250-8BITMIME 250 HELP DEBUG SMTP: Found extension "STARTTLS", arg "" DEBUG SMTP: Found extension "PIPELINING", arg "" DEBUG SMTP: Found extension "SIZE", arg "100000000" DEBUG SMTP: Found extension "AUTH", arg "LOGIN PLAIN" DEBUG SMTP: Found extension "AUTH=LOGIN", arg "PLAIN" DEBUG SMTP: Found extension "8BITMIME", arg "" DEBUG SMTP: Found extension "HELP", arg "" STARTTLS 220 Ready to start TLS EHLO CLIENT 250-SERVER Hello CLIENT [192.1.1.1], pleased to meet you 250-PIPELINING 250-SIZE 100000000 250-AUTH LOGIN PLAIN 250-AUTH=LOGIN PLAIN 250-8BITMIME 250 HELP DEBUG SMTP: Found extension "PIPELINING", arg "" DEBUG SMTP: Found extension "SIZE", arg "100000000" DEBUG SMTP: Found extension "AUTH", arg "LOGIN PLAIN" DEBUG SMTP: Found extension "AUTH=LOGIN", arg "PLAIN" DEBUG SMTP: Found extension "8BITMIME", arg "" DEBUG SMTP: Found extension "HELP", arg "" DEBUG SMTP: Attempt to authenticate DEBUG SMTP: check mechanisms: LOGIN PLAIN DIGEST-MD5 AUTH LOGIN 334 VXNlcn5hbWU6 RVJOXHNsK2FyZmlu 334 UGFzc3dvcmQ6 UVdFUnF3ZXIxMjM0IUAjJA== 535 Error: authentication failed DEBUG SMTP: useEhlo true, useAuth true DEBUG SMTP: trying to connect to host "SERVER", port 25, isSSL false 220 SERVER ESMTP (deca81216f2ecf4fd6fedb030e3dcfd0) DEBUG SMTP: connected to host "SERVER", port: 25 EHLO CLIENT 250-SERVER Hello CLIENT [192.1.1.1], pleased to meet you 250-STARTTLS 250-PIPELINING 250-SIZE 100000000 250-AUTH LOGIN PLAIN 250-AUTH=LOGIN PLAIN 250-8BITMIME 250 HELP DEBUG SMTP: Found extension "STARTTLS", arg "" DEBUG SMTP: Found extension "PIPELINING", arg "" DEBUG SMTP: Found extension "SIZE", arg "100000000" DEBUG SMTP: Found extension "AUTH", arg "LOGIN PLAIN" DEBUG SMTP: Found extension "AUTH=LOGIN", arg "PLAIN" DEBUG SMTP: Found extension "8BITMIME", arg "" DEBUG SMTP: Found extension "HELP", arg "" STARTTLS 220 Ready to start TLS EHLO CLIENT 250-SERVER Hello CLIENT [192.1.1.1], pleased to meet you 250-PIPELINING 250-SIZE 100000000 250-AUTH LOGIN PLAIN 250-AUTH=LOGIN PLAIN 250-8BITMIME 250 HELP DEBUG SMTP: Found extension "PIPELINING", arg "" DEBUG SMTP: Found extension "SIZE", arg "100000000" DEBUG SMTP: Found extension "AUTH", arg "LOGIN PLAIN" DEBUG SMTP: Found extension "AUTH=LOGIN", arg "PLAIN" DEBUG SMTP: Found extension "8BITMIME", arg "" DEBUG SMTP: Found extension "HELP", arg "" DEBUG SMTP: Attempt to authenticate DEBUG SMTP: check mechanisms: LOGIN PLAIN DIGEST-MD5 AUTH LOGIN 334 VXNlcm5hbWU6 RVJOXHNsZ2FyZmlu 334 UGFzc3dvcmQ6 UVdFUnF3ZXIxMjM0IUAjJA== 535 Error: authentication failed Error sending mail: failed to connect javax.mail.AuthenticationFailedException: failed to connect at javax.mail.Service.connect(Service.java:322) at javax.mail.Service.connect(Service.java:172) at SignMessage.sendSigned(SignMessage.java:248) at SignMessage.main(SignMessage.java:340
-
nos almost 15 yearsI remember some similar thing with non java related clients, the username had to be in the form of DOMAIN\username and depending on how the excahnge server is set up, you might need the suffix also, so e.g. companyname\bob or companyname.COM\bob or companyname.local\bob
-
Ravi Wallau almost 15 yearsYeah, I would try that as well. Add the domain information before the username, it should help.
-
-
Ami almost 15 yearsThanks. Unfortunately that didn't do it. I have two Exchange servers available, they are both configured differently, and the both behave the same way with your code as they did with my code. In both cases the servers are saying they can do GSSAPI NTLM and LOGIN and my system is saying LOGIN PLAIN DIGEST-MD5, so the javax.mail system is trying to do AUTH LOGIN and that is failing. It's weird. It work on every other system, just not exchange. Is there a GSSAPI implementation that I can use?
-
Ami over 14 yearsInteresting, but I think that you are experiencing bystander effect. That is, I don't think that the changes you made resulted in the effect that you observed.
-
Admin over 14 yearsI think it was due to disabling McAfee. At my workplace McAfee has build in firewall (I have no idea whether it is the way McAfee is bundled) and the firewall was blocking some of the applications.
-
egerardus about 12 yearsDisrelated to the OP's problem, but this answer completely resolved the Exchange Server's "No Logon Method Supported" problem I had been struggling with for about a day. Thanks!
-
Max P Magee almost 9 yearsI know this is super-old, but I'm adding the package imports necessary to make this answer complete.