How to Send Email from Java Program with Example

Sending Email from Java program is a common requirement. It doesn't matter whether you are working on core Java application, web application or enterprise Java EE application, you may need to send email to alert support personal with errors, or just send email to users on registration, password reset or asking them to confirm their email after registration. There are many such scenarios, where you need ability to send emails from Java program. In mature applications, you already have a module or library dealing with all king of email functionality and issues e.g. ability to send attachments, images, including signatures and other rich text formatting on emails, but if you have to code something from scratch then Java's Mail API is perfect place.

In this article, we will learn how to send emails from Java application using mail API ( javax.mail ) . Before writing code, you must know some email basics e.g. you need a SMTP (Simple Mail Transfer Protocol) server.

If you are running your Java application in Linux, then you should know that SMTP daemon by default listen on port 25. You can use any mail server to send emails from Java, including public email servers like GMail, Yahoo or any other provider, all you need is their SMTP server details e.g. hostname, port, connection parameters etc.

You can also use SSL, TLS to securely connect and send emails, but in this example we have kept it simple and just focusing on minimum logic to send mail from Java application.

In further articles, we will learn how to send mail using attachments, how to send HTML formatted email, how to attach images in emails, how to use SSL authentication to connect GMail Server and send emails etc. For now, let's understand this simple example of Java Mail API.



Java Code Example to Send Email

In order to send email from Java program you need Java Mail API and Java Activation Framework (JAF), precisely you need mail-1.4.5.jar, smtp-1.4.4.jar, and activation-1.1.jar. You need to download these JAR files and include them in your Classpath to run this program. Alternatively you can use Maven for managing dependencies and can include all dependencies there. Once you have these JAR files covered, just follow below steps to create and send text email from Java.

Java Program to Send Email using Mail API
  1. Create Session object by calling Session.getDefaultInstance(properties), where properties contains all important properties e.g. hostname of SMTP server. 
  2. Create MimeMessage object by passing Session obtained in previous steps. we have to set different properties in this object such as recipient email address, subject, email body, attachments etc.
  3. Use javax.mail.Transport to send the email message by calling static method send(email), where email can be MimeMessage.

Number of properties you pass to create session differs based on the type of SMTP server, for example if SMTP server doesn't require any authentication you can create the Session object with just one property e.g. smtp.mail.host, no need to provide port even because it listen on default port 25. On the other hand if you are connecting to a SMTP server which requires TLS or SSL authentication, e.g. GMail's SMTP Host then you will need to provide few more properties e.g. mail.smtp.port=547 for TLS and mail.smtp.port=457 for SSL. Here is a complete Java program which connect to default SMTP Server without authentication and send a text email using Java's mail API.

import java.util.Properties;
import javax.mail.Message;
import javax.mail.MessagingException;
import javax.mail.Session;
import javax.mail.Transport;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeMessage;

/**
* Java Program to send text mail using default SMTP server and without authentication.
* You need mail.jar, smtp.jar and activation.jar to run this program.
*
* @author Javin Paul
*/
public class EmailSender{

    public static void main(String args[]) {
        String to = "receive@abc.om";            // sender email
        String from = "sender@abc.com";       // receiver email
        String host = "127.0.0.1";                   // mail server host

       Properties properties = System.getProperties();
        properties.setProperty("mail.smtp.host", host);

        Session session = Session.getDefaultInstance(properties); // default session

        try {
            MimeMessage message = new MimeMessage(session);        // email message
            message.setFrom(new InternetAddress(from));                    // setting header fields
            message.addRecipient(Message.RecipientType.TO, new InternetAddress(to));
            message.setSubject("Test Mail from Java Program"); // subject line

            // actual mail body
            message.setText("You can send mail from Java program by using mail API, but you need"
                    + "couple of more JAR files e.g. smtp.jar and activation.jar");

            // Send message
            Transport.send(message);
            System.out.println("Email Sent successfully....");
        } catch (MessagingException mex) {
            mex.printStackTrace();
        }
    }

}

Output :
You can Compile and run this program to send a simple e-mail from Java program:

$ javac EmailSender.java
$ java EmailSender
Sent email successfully....

As you can see it's very simple to send mails from Java program. Once you have created MimeMessage object, you need to add recipients which can be TO, CC or BCC. After setting recipients we have setup subject and finally email content itself by message.setText().  If you want to send an e-mail to multiple email ids then following methods would be used to specify those recipients:

void addRecipients(Message.RecipientType type, Address[] addresses) throws MessagingException

You can add peoples into TO field by using Message.RecipientType.TO, in CC by Message.RecipientType.CC and into BCC by Message.RecipientType.BCC.



Error and Exception

When many Java programmers first start to write program to send email, they ran into this error because most of them just think that mail.jar and activation.jar would be enough to send mail form Java application, which is not true especially if you are sending email via local SMTP server in Linux. If you run this program with just mail.jar and activation.jar in your CLASSPATH, you will most likely get this error.

Exception 1:
com.sun.mail.util.MailConnectException: Couldn't connect to host, port: localhost, 25; timeout -1;
  nested exception is:
               java.net.ConnectException: Connection refused: connect
               at com.sun.mail.smtp.SMTPTransport.openServer(SMTPTransport.java:1984)
               at com.sun.mail.smtp.SMTPTransport.protocolConnect(SMTPTransport.java:656)
               at javax.mail.Service.connect(Service.java:345)
               at javax.mail.Service.connect(Service.java:226)
               at javax.mail.Service.connect(Service.java:175)
               at javax.mail.Transport.send0(Transport.java:253)
               at javax.mail.Transport.send(Transport.java:124)
               at Testing.main(Testing.java:62)
Caused by: java.net.ConnectException: Connection refused: connect
               at java.net.DualStackPlainSocketImpl.connect0(Native Method)
               at java.net.DualStackPlainSocketImpl.socketConnect(DualStackPlainSocketImpl.java:79)
               at java.net.AbstractPlainSocketImpl.doConnect(AbstractPlainSocketImpl.java:339)
               at java.net.AbstractPlainSocketImpl.connectToAddress(AbstractPlainSocketImpl.java:200)
               at java.net.AbstractPlainSocketImpl.connect(AbstractPlainSocketImpl.java:182)
               at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:172)
               at java.net.SocksSocketImpl.connect(SocksSocketImpl.java:392)
               at java.net.Socket.connect(Socket.java:579)
               at java.net.Socket.connect(Socket.java:528)
               at com.sun.mail.util.SocketFetcher.createSocket(SocketFetcher.java:301)
               at com.sun.mail.util.SocketFetcher.getSocket(SocketFetcher.java:229)
               at com.sun.mail.smtp.SMTPTransport.openServer(SMTPTransport.java:1950)
               ... 7 more

Solution : Though solution of this error is very simple, it may direct you into different direction. Since java.net.ConnectException: Connection refused: connect usually come when either server is down or the port you are connecting is not correct, and this happened to me as well in past. solution is apart from mail-1.4.5.jar, you also need smtp-1.4.4.jar and activation-1.1.jar


Exception 2:
This is another error, called NoClassDefFoundError, which is also related to missing JAR file in Classpath :

Exception in thread "main" java.lang.NoClassDefFoundError: javax/mail/MessagingException
        at java.lang.Class.getDeclaredMethods0(Native Method)
        at java.lang.Class.privateGetDeclaredMethods(Class.java:2521)
        at java.lang.Class.getMethod0(Class.java:2764)
        at java.lang.Class.getMethod(Class.java:1653)
        at sun.launcher.LauncherHelper.getMainMethod(LauncherHelper.java:494)
        at sun.launcher.LauncherHelper.checkAndLoadMain(LauncherHelper.java:486)
Caused by: java.lang.ClassNotFoundException: javax.mail.MessagingException
        at java.net.URLClassLoader$1.run(URLClassLoader.java:366)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:355)
        at java.security.AccessController.doPrivileged(Native Method)
        at java.net.URLClassLoader.findClass(URLClassLoader.java:354)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)


Solution : I managed to resolve my problem, it was because of incorrect Classpath. Even though I had all three required JAR and Java class file for program in same directory and I am running program from there, Java wasn't able to resolve that. I tried following command and it worked perfectly for me :

java -cp mail-1.4.5.jar:smtp-1.4.4.jar:activation-1.1.jar:. JavaMailSender
Sent email successfully....
Please notice current directory denoted by dot (.) at the end of Classpath argument. Since I was running my program on Linux, I have used colon as separator (:) instead of Windows semi colon (;)

That's all on how to send email from Java program using mail API. You can see it's very simple, apart from three JAR file you don't need much. It's much easy if you use Gradle or Maven for dependency management.  In next couple of tutorials we will see advanced example of Java's mail API to send email with attachments, with images and nicely HTML formatted emails to send reports and tables.



4 comments :

Anonymous said...

Even after release of Java 8, basic functionaltiy like sending mails requires too much configuration and code in Java. I think even UNIX's mail command is better. Ideally you would like config to be specified in one line and content to be another, that's it. By the way, can we send email in Java using Outlook and Gmail at same time?

Anonymous said...

log prints mail sent successfully,But unable to view the mail in inbox/sentbox.Anyone has the same issue?

Anonymous said...

Error resolved changed the host to correct one.

Anonymous said...

Quick note - depending on version, you _might_ not need all three files. On my version (1.6), I downloaded just javax.mail.jar. See http://www.oracle.com/technetwork/java/index-138643.html for more info.
Also, if you place in ..\Java\jre6\lib\ext no need to add -classpath arg. More info at http://docs.oracle.com/javase/tutorial/ext/basics/index.html (Installed Extensions link).

Post a Comment