Slow sendmail performance (javamail) with different mail api jars [duplicate]
Asked Answered
A

2

7

I am testing the sendmail example as stated in https://javaee.github.io/javamail/FAQ. It is a simple mail sending operation, without SSL and no attachments. It works fine everywhere but on client we have a degreading performance when the mail api gets newer.

Server is windows, java 1.8.131, use same mailserver and mail account and same to address and java source on all test cases. The only difference is the mailapi used. I run the program with

java -cp javax.mail.1.X.X.jar;sendmailtesttool.jar SendMail

I tried 100 times for each mail api and get the average duration.

  • JavaMailApi version: 1.4.0 duration < 1 sec.
  • JavaMailApi version: 1.4.2 duration 9-10 sec.
  • JavaMailApi version: 1.5.2 duration 29-30 sec.
  • JavaMailApi version: 1.5.6 duration 29-30 sec.
  • JavaMailApi version: 1.6.0 duration 29-30 sec.

Source used:

Properties properties = new Properties();
properties.put("mail.smtp.host", 192.168.0.X); // use default port25
Session session = Session.getInstance(properties);
MimeMessage msg = new MimeMessage(session);
msg.setFrom(..);
msg.setSubject(..);
msg.setRecipients(..);
//no attachments
MultiPart mp = new MultiPart();
MimeBodyPart bp = new MimeBodyPart();
DataSource ds = ByteArrayDataSource("foo"..);
DataHandler dh = new DataHandler(ds);
bp.setDataHandler(dh);
mp.addBodyPart(bp);
msg.setContent(mp);

Transport transport = session.getTransport("smtp");
transport.connect(host, username, password);
msg.saveChanges(); // is really needed ? (no reply/forward)
transport.sendMessage(msg, msg.getAllRecipients());
transport.close();

Output of the test tool

Java Mail Api 1.4.0

Sending mail.....start
Setting port to:25
Setting host to:192.168.0.213
Set additional session prop host to prevent HELO
Set additional session prop from to prevent EHLO
Session generated with authenticator took:63
Message generated took:47
Parse from address took:0
Set from address to message took:0
Set recipients took:0
Get all recipients took:0
Set cc, bcc took:0
Parse subject took:16
Set subject to message took:0
Set body text took:0
Set content took:0
Set sent date took:15
Transport generated took:32
Connected to transport took:93
Save changes took:0
Message send took:94
Transport closed took:0
Message id fetched took:0
Sending mail.....completed in 391
Average took: *391.0*

Java Mail Api 1.5.6

Sending mail.....start
Setting port to:25
Setting host to:192.168.0.213
Set additional session prop host to prevent HELO
Set additional session prop from to prevent EHLO
Session generated with authenticator took:62
Message generated took:63
Parse from address took:0
Set from address to message took:16
Set recipients took:0
Get all recipients took:0
Set cc, bcc took:0
Parse subject took:0
Set subject to message took:0
Set body text took:0
Set content took:0
Set sent date took:15
Transport generated took:32
Connected to transport took:9126
Save changes took:0
Message send took:47
Transport closed took:0
Message id fetched took:0
Sending mail.....completed in 9423
Average took: *9423.0*

The jvm mail debug outputs

Java Mail API 1.4.0

DEBUG: setDebug: JavaMail version 1.4ea
DEBUG: getProvider() returning
javax.mail.Provider[TRANSPORT,smtp,com.sun.mail.s
mtp.SMTPTransport,Sun Microsystems, Inc]
DEBUG SMTP: useEhlo true, useAuth true
DEBUG SMTP: trying to connect to host "192.168.0.X", port 25, isSSL
false
220 mail.******.com ESMTP Postfix
DEBUG SMTP: connected to host "192.168.0.X", port: 25
EHLO WIN-0RL58R42TTN
250-mail.******.com
250-PIPELINING
250-SIZE 102400000
250-VRFY
250-ETRN
250-STARTTLS
250-AUTH PLAIN LOGIN
250-AUTH=PLAIN LOGIN
250-ENHANCEDSTATUSCODES
250-8BITMIME
250 DSN
DEBUG SMTP: Found extension "PIPELINING", arg ""
DEBUG SMTP: Found extension "SIZE", arg "102400000"
DEBUG SMTP: Found extension "VRFY", arg ""
DEBUG SMTP: Found extension "ETRN", arg ""
DEBUG SMTP: Found extension "STARTTLS", arg ""
DEBUG SMTP: Found extension "AUTH", arg "PLAIN LOGIN"
DEBUG SMTP: Found extension "AUTH=PLAIN", arg "LOGIN"
DEBUG SMTP: Found extension "ENHANCEDSTATUSCODES", arg ""
DEBUG SMTP: Found extension "8BITMIME", arg ""
DEBUG SMTP: Found extension "DSN", arg ""
DEBUG SMTP: Attempt to authenticate
AUTH LOGIN
334 VXNlcm5hbWU6
am9iaW4uZWxhbmppY2thbEBhbGNvbmVsZWN0cm9uaWNzLmNvbQ==
334 UGFzc3dvcmQ6
Sk9CSU5ANzc3TnM=
235 2.7.0 Authentication successful
DEBUG SMTP: use8bit false
MAIL FROM:<sender@******.com>
250 2.1.0 Ok
RCPT TO:<receiver@******.com>
250 2.1.5 Ok
DEBUG SMTP: Verified Addresses
DEBUG SMTP:   receiver@******.com
DATA
354 End data with <CR><LF>.<CR><LF>
Date: Thu, 14 Dec 2017 14:17:46 +0530 (IST)
From: sender@******.com
To: receiver@******.com
Message-ID: <396180261.01513241266298.JavaMail.sender@******
.com>
Subject: test3
MIME-Version: 1.0
Content-Type: multipart/mixed;
        boundary="----=_Part_0_2093176254.1513241266126"
------=_Part_0_2093176254.1513241266126
Content-Type: text/plain; charset=utf-8
Content-Transfer-Encoding: 7bit
test
------=_Part_0_2093176254.1513241266126--
.
250 2.0.0 Ok: queued as 7E38D48F0411
QUIT
221 2.0.0 Bye

Java Mail API 1.5.6

DEBUG: setDebug: JavaMail version 1.5.6
DEBUG: getProvider() returning
javax.mail.Provider[TRANSPORT,smtp,com.sun.mail.s
mtp.SMTPTransport,Oracle]
DEBUG SMTP: useEhlo true, useAuth true
DEBUG SMTP: trying to connect to host "192.168.0.X", port 25, isSSL
false
220 mail.******.com ESMTP Postfix
DEBUG SMTP: connected to host "192.168.0.X", port: 25
EHLO WIN-0RL58R42TTN
250-mail.******.com
250-PIPELINING
250-SIZE 102400000
250-VRFY
250-ETRN
250-STARTTLS
250-AUTH PLAIN LOGIN
250-AUTH=PLAIN LOGIN
250-ENHANCEDSTATUSCODES
250-8BITMIME
250 DSN
DEBUG SMTP: Found extension "PIPELINING", arg ""
DEBUG SMTP: Found extension "SIZE", arg "102400000"
DEBUG SMTP: Found extension "VRFY", arg ""
DEBUG SMTP: Found extension "ETRN", arg ""
DEBUG SMTP: Found extension "STARTTLS", arg ""
DEBUG SMTP: Found extension "AUTH", arg "PLAIN LOGIN"
DEBUG SMTP: Found extension "AUTH=PLAIN", arg "LOGIN"
DEBUG SMTP: Found extension "ENHANCEDSTATUSCODES", arg ""
DEBUG SMTP: Found extension "8BITMIME", arg ""
DEBUG SMTP: Found extension "DSN", arg ""
DEBUG SMTP: protocolConnect login, host=192.168.0.X, user=sender@alc
onelectronics.com, password=<non-null>
DEBUG SMTP: Attempt to authenticate using mechanisms: LOGIN PLAIN
DIGEST-MD5 NTL
M XOAUTH2
DEBUG SMTP: Using mechanism LOGIN
DEBUG SMTP: AUTH LOGIN command trace suppressed
DEBUG SMTP: AUTH LOGIN succeeded
DEBUG SMTP: use8bit false
MAIL FROM:<sender@******.com>
250 2.1.0 Ok
RCPT TO:<receiver@******.com>
250 2.1.5 Ok
DEBUG SMTP: Verified Addresses
DEBUG SMTP:   receiver@******.com
DATA
354 End data with <CR><LF>.<CR><LF>
Date: Thu, 14 Dec 2017 14:18:03 +0530 (IST)
From: sender@******.com
To: receiver@******.com
Message-ID: <1109371569.1.1513241292669@******.com>
Subject: test3
MIME-Version: 1.0
Content-Type: multipart/mixed;
        boundary="----=_Part_0_1349393271.1513241283434"
------=_Part_0_1349393271.1513241283434
Content-Type: text/plain; charset=utf-8
Content-Transfer-Encoding: 7bit
test
------=_Part_0_1349393271.1513241283434--
.
250 2.0.0 Ok: queued as D894D48F0411
DEBUG SMTP: message successfully delivered to mail server
QUIT
221 2.0.0 Bye
Adaptable answered 14/12, 2017 at 7:12 Comment(9)
What's the difference in JavaMail debug output between the different versions? Newer versions of support for NTLM authentication, which may be being used instead of simpler password authentication, and may perform slower on your server.Spill
I checked #44435957. I added session property mail.from, mail.host and mail.smtp.from properties, then witlh java mail api 1.5.6 it is recuded to 9seconds from 29seconds, but with 1.4.0 still it is below 1 sec. I will check now the debug output, as Bill Shannon says.Adaptable
I see: #4338312 it says: via SMTP - the NTLM Authentication did not work with an older version of javax.mail (up to 1.4.1) but it now works with version 1.4.5. How can we disable NTLM?Adaptable
@BillShannon i compared both logs, with debug options true, and they are close same, but I found the solution! setting the property mail.smtp.localhost to 127.0.0.1 solved the issue in Java Mail API 1.5.6, now it is same quick as 1.4.0Adaptable
Thanks for the comment I have already done the steps but why setting mail.smtp.localhost solved the issue? it this really a solution? why not needed in old mail api, has it anything with NTLM? if I set mail.smtp.localhost to foo the mails is sent quick, on the receiver we have recived from foo. but I remove the setting, it is sent in 9-10 seconds. Any name lookup hostname problem on the server? java is 1.8.111 upgrade needed? We do not control the server.Adaptable
As @Zilk describes in the answer below, it seems to be a problem in the configuration of the name service on your machine where it's taking a long time to return the canonical host name for your machine, or taking a long time to time out and give up trying to return it.Spill
Thanks Bill Shannon, and can you explain why it is fast in mail api 1.4.0? has it still sth with NTLM or anything else?Adaptable
ok i found it, the time consuming call is in the SMTPTransport getLocalhost method, localHost.getCanonicalHostName(). And in the old mail api which is fast on that case the call is localHost.getHostName(). As we see, there is a DNS config error on the server. But adding 127.0.0.1 localhost or 127.0.0.1 machinename to the host file (windows) did not helped. (restart needed?)Adaptable
You need an entry for the actual IP address your machine is using, not localhost.Spill
P
4

I don't believe there is just one reason to make it slower. You may need to change some defaults just below example.

In the 1.6 document of the mail api for property mail.mime.address.usecanonicalhostname it states:

Use the InetAddress.getCanonicalHostName method to determine the host name in the InternetAddress.getLocalAddress method. With some network configurations, InetAddress.getCanonicalHostName may be slow or may return an address instead of a host name. In that case, setting this System property to false will cause the InetAddress.getHostName method to be used instead. The default is true.

So if you change the default value with false, it may changes its performance.

I would also recommend that check the java mail apis release notes to find out some clue.

Petrology answered 14/12, 2017 at 8:40 Comment(0)
L
1

There are mistakes in your code. a Transport object is obtained with session.getTransport and not session.getInstance ; and we don't see where is initialized the host in your call transport.connect(host,..) ; connect(user , password) should be enough if you set the right Properties and if there aren't any DNS solving issue.

Lewin answered 14/12, 2017 at 8:49 Comment(2)
I fixed the session.getTransport() call, it is a typo. And i did not put all the working code, it is a sample. host, username etc are pure strings.Adaptable
From the solution you have found, this probably means a DNS solving issue as I was suggesting.Heywood

© 2022 - 2024 — McMap. All rights reserved.