Send email using nodejs and express in 5 simple steps

Sending automatic emails is a very common task and doing so in nodejs is pretty straigtforward as well. In this article, I will demonstrate a simple example of sending emails using nodejs in 5 simple steps.

This article is written around the following scenario in mind

  • You have an email account with an email provider like Google which you want to specify as the ‘sender’. There is a simple reasoning behind doing so. Emails are sent from one server to another and in order to avoid landing your email in the recipient’s spam folder, you want to use a truster server as the sender of the email aka – Google’s mail servers. For the purpose of this article, we will assume this email address is [email protected].
  • You have a web page that has a contact form where a user enters some information and clicks on submit. Upon clicking submit your express server needs to capture this data and send the request information to another email address.

I assume that you have at least a basic understanding of nodejs and its routing. If not, take a look at this diagram that visually depicts how routing takes place in expressjs.

You probably also want to change some settings on the gmail account you want to use before proceeding.


There are just 5 steps to sending an email using nodejs

  • Install the nodemailer package.
  • Create a transport object using nodemailer.createTransport() and pass it your email credentials.
  • Prepare the message to be sent in the body.
  • Create an object with information about the sender, email subject, recipient and the body content that we prepared earlier.
  • Send the email using – transporter.sendMail()

In the code snippets that follow, we will go through each of the above steps.

STEP 1: Install the nodemailer package.

npm install nodemailer

Once you are done with this article, you should probably learn more about nodemailer library from here.
STEP 2: Creating a transport object in your route handler.

var nodemailer = require('nodemailer');

var router = express.Router();
app.use('/sayHello', router);'/', handleSayHello); // handle the route at

function handleSayHello(req, res) {
    // Not the movie transporter!
    var transporter = nodemailer.createTransport({
        service: 'Gmail',
        auth: {
            user: '[email protected]', // Your email id
            pass: 'password' // Your password

STEP 3: Prepare some plaintext or HTML content to be sent in the body. I am going to simply use some text.

var text = 'Hello world from \n\n' +;

STEP 4: Create a simple JSON object with the necessary values for sending the email.

var mailOptions = {
    from: '[email protected]>', // sender address
    to: '[email protected]', // list of receivers
    subject: 'Email Example', // Subject line
    text: text //, // plaintext body
    // html: '<b>Hello world ✔</b>' // You can choose to send an HTML body instead

STEP 5: Your moment of glory! – Actually send the email and handle the response.

transporter.sendMail(mailOptions, function(error, info){
        res.json({yo: 'error'});
        console.log('Message sent: ' + info.response);
        res.json({yo: info.response});

And thats pretty much all there is to it! It was quite simple, wasn’nt it?

Ryan Sukale

Ryan Sukale

Ryan is just a regular guy next door trying to manage his life and finances.

25 Responses

  1. Eros Garcia Ponte says:

    Great tutorial. Who would imagine it was so simple.

  2. Rafa Death says:

    I get Error: Invalid login with gmail 🙁

  3. tutorialhorizon says:

    Last I remember gmail had a per-day limit, around 500 for sending emails this way. Its either that or it does not allow you to send to more than 500 recipients.

    Using gmail would work for simple use cases. But for production scenarios, you probably want to use something like to send emails.

    Maybe I should do a quick writeup on that one too.

  4. tutorialhorizon says:

    I have just now posted a reply to Jodge for the same. You can check it out.

  5. Cl Sah says:

    I have an error message i.e “Unable to send email: Error: Unsupported configuration, downgrade Nodemailer to
    v0.7.1 to use it”

  6. Luís Cunha says:

    I get this error when running this

    TypeError: this.mailcomposer.setMessageOption is not a function

    at Nodemailer.setGeneralOptions (D:gitnodemailernode_modulesnodemailerlibnodemailer.js:228:23)

    at Nodemailer.generateMailObject (D:gitnodemailernode_modulesnodemailerlibnodemailer.js:184:10)

    at Nodemailer.sendMail (D:gitnodemailernode_modulesnodemailerlibnodemailer.js:172:10)

    at D:gitnodemailernode_modulesnodemailerlibnodemailer.js:69:20

    at Nodemailer.validateSettings (D:gitnodemailernode_modulesnodemailerlibnodemailer.js:161:5)

    at sendMail (D:gitnodemailernode_modulesnodemailerlibnodemailer.js:63:12)

    at Transport.transport.sendMail (D:gitnodemailernode_modulesnodemailerlibnodemailer.js:40:9)

    at Object. (D:gitnodemailerapp.js:19:13)

    at Module._compile (module.js:399:26)

    at Object.Module._extensions..js (module.js:406:10)

  7. jsconestilo says:

    Gracias por la información, muy útil

  8. Lucy says:

    I tried the same, but I keep getting POST http://localhost:8080/contact 404 (Not Found) error. Anyone know what could be reason?

  9. Lucy says:

    I follow the same, but keep getting error POST http://localhost:8080/contact 404 (Not Found)

    • Rohan Sharma says:

      404 status occurs when the browser is unable to access the URI (http://localhost:8080/contact) or may be you are trying to the access the URI directly through the browser, you can’t access POST apis directly by browser but you do this with GET apis.

  10. Mohit Mittal says:

    Awesome tutorial. Worked like charm in the first go. Never expected from a mail tutorial to work in the first go !

  11. this doesn’t send any emails, gmail does.. better headline: how to send emails through gmail with nodejs and Express…

  12. Sheikh Subtain Ishfaq says:

    Perfect .

  13. Mayur Kagade says:

    great tutorial its much easy but getting error like transporter is not defined

  14. K. Join says:

    Great tutorial. Thanks

  15. Hector Andres Perez Villatoro says:

    Hello – My problem is that it works locally but not in the ‘live’ site.
    I don’t know why this is. This is uploaded to heroku. : I’m not very experienced, and it’s my first time making a website.

  16. six1as says:

    The answer may be 1 year too late, however i hope it will help others who come here to look for an answer for the same error encountered.

    I hit the same exact error. There may be other factors that can cause this error, I am only reporting the one factor I found which fixed the error. Here goes :

    In my nodeJS gmail service call, I was using a gmail account that was created in a different country/region than the country/region where my nodeJS app is hosted. The moment I swapped out the gmail account in question with one that was created in the same country/region where my nodeJS app is hosted, the error disappeared !

    I am speculating perhaps when Google looks for signs of fraudulent mail account access – it flags subtle thing like “the mail account not created in same country as the app is hosted”. It is irrelevant if I got this right, what matters most : I got this error condition fixed by doing what I said above.

    Hope this helps.

  17. six1as says:

    After implementing this solution, I found the error below would pop up whenever my app (which is hosted in US) was accessed outside of US the first time (Subsequent time would be fine). On examined the gmail account used in my app’s NodeJS gmail service call, I suspected it was due to the gmail account was created in Europe, not in same region as my app is hosted. I swapped out the gmail account with one that was created in US, and the error went away.

    My guess : when Google checks for suspicious gmail account access, it flags subtle clue like the gmail account and app are not in same country/region.

    ‘534-5.7.14 Please log in via your web browser andn534-5.7.14 then try again.n534-5.7.14 Learn more atn534 5.7.14

  18. tutorialhorizon says:

    Youre right. This is an example of how to go about setting up the email service. Sensitive variables like passwords should always be read from environment variables.

  1. February 24, 2017

    […] Simple tutorial for node/express contact form. […]

Leave a Reply

Your email address will not be published.