Sending Email with Node.js After Form Submission

Sending Email with Node.js

Sending Email with Node.js

Nodemailer is for sending email with nodejs without the hustle of writing many lines of code. It uses the prevailing email services (Outlook, Hotmail, Gmail then on) to authenticate and send messages. Authentication is completed by simply adding your email credentials as a mail option. It also handle various transport protocols (SMTP as default). during this post, we’ll use the nodemailer module to send email once the express app receives form submission.

Sending Email with Node.js

We will build the shape submission mailer functionality on top of what we’ve wiped out the previous post (Website Page Routing with Node.js Express and EJS). the main changes are:

  • Adding contact form in contact.ejs.
  • Adding different routers, including form post request handler and mailer.
  • Add redirect pages after sending emails.

Before we start, we can add the nodemailer module by running npm I nodemailer -SE. The rest of the dependencies are the same.

OK, let’s get started.

Folder Structure

Adding different routers and a few new ejs pages.

-- project_folder
 -- css
    -- style.css
 -- html
    -- about.ejs
    -- contact.ejs
    -- index.ejs
    -- include
        -- footer.ejs
        -- head.ejs
        -- nav.ejs
        -- scripts.ejs
        -- contact_send.ejs
        -- contact_error.ejs
 -- routes
    -- index.js
    -- contact.js
    -- pageRouter.js
 -- app.js
 -- package.json
 -- package-lock.json
 -- node_modules

Adding or Updating EJS Files

contact.ejs

Simply adding the form to the existing contact.ejs. The form will be sent to contact/sent, which will be handled by the post request handler in contact.js.

<!DOCTYPE html>
<html lang="en">
    <% include ./include/head %>
    <body>
        <% include ./include/nav %>
        <div class="container">
            <div class="row">
                <h1>Contact</h1>
            </div>
            <hr>
            <div class="row">
                <form class="col-12 col-md-8" method="post" action="contact/send">
                    <div class="form-group">
                        <label for="name">Name</label>
                        <input type="text" class="form-control" id="name" name="name">
                    </div>
                    <div class="form-group">
                        <label for="email">Email</label>
                        <input type="email" class="form-control" id="email" name="email">
                    </div>
                    <div class="form-group">
                        <label for="enquiry">Enquiry</label>
                        <textarea class="form-control" id="enquiry" name="enquiry" rows="6"></textarea>
                    </div>
                    <div class="float-right"> <!-- align button to the right -->
                        <button type="submit" class="btn btn-primary btn-lg">Submit</button>
                    </div>
                </form>
            </div>
            <div class="row">
                <p></p>
            </div>
        </div>
        <% include ./include/scripts %>
        <% include ./include/footer %>
    </body>
</html>

contact_send.ejs

Redirected to this page after successful email send.

<!DOCTYPE html>
<html lang="en">
    <% include ./include/head %>
    <body>
        <% include ./include/nav %>
        <div class="container">
            <div class="row">
                <h1>Thank you for your Enquiry!</h1>
            </div>
            <hr>
            <div class="row" style="height:300px;">
                <p>Thank you for contacting us. We will get back to you as soon as we can.</p>
                
               
            </div>
        </div>
        <% include ./include/scripts %>
        <% include ./include/footer %>
    </body>
</html>

contact_error.ejs

Redirected to this page after unsuccessful email send.

<!DOCTYPE html>
<html lang="en">
    <% include ./include/head %>
    <body>
        <% include ./include/nav %>
        <div class="container">
            <div class="row">
                <h1>Thank you for your Enquiry!</h1>
            </div>
            <hr>
            <div class="row" style="height:300px;">
                <p>Thank you for contacting us.</p>
                <p>We failed to send you an email. Please enter different one.</p>
               
            </div>
        </div>
        <% include ./include/scripts %>
        <% include ./include/footer %>
    </body>
</html>

Routers and Request Handlers

In the index file, we’ll define each router and that they are often imported within the app.js. Within app.js, we do a path-based routing. once you specify the router folder to import module in app.js, it’s for index.js by default. Therefore, you simply got to add the folder name.

index.js

This is for organising different request handlers so that importing them in the main app.js becomes cleaner.

module.exports = {
  pageRouter: require('./pageRouter.js'),
  contact: require('./contact.js')
}

contact.js

This handles post requests from the form. The example uses Hotmail. It supports all the major email service providers. See the documentation for further information about Nodemailer for your own implementation.

After successful email send, it routes to the email success page. It redirects the traffic to the get method in pageRouter.js.

const express = require('express');
const url = require('url');
const nodemailer = require('nodemailer');
const router = express.Router();

router.get('/', (req, res) => {
  console.log('Request for contact page recieved');
  res.render('contact');
});

router.post('/send', (req, res) => {
  var name = req.body.name;
  var email = req.body.email;
  var enquiry = req.body.enquiry;

  var emailMessage = `Hi ${name},\n\nThank you for contacting us.\n\nYour email is: ${email}.\n\nYour enquiry is: ${enquiry}\n.`;

  console.log(emailMessage);
  res.redirect('/contact_send');

  var transporter = nodemailer.createTransport({
    service: 'Hotmail',
    auth: {
      user: 'your email address',
      pass: 'your password'
    }
  });

  var emailOptions = {
    from: 'your name <your email address>',
    to: email,
    subject: 'Node Mailer Test',
    text: emailMessage
  };

  transporter.sendMail(emailOptions, (err, info) => {
    if (error) {
      console.log(error);
      res.redirect('/contact_send');
    } else {
      console.log('Message Sent: ' + info.response);
      console.log('Email Message: ' + emailMessage);
      res.redirect('/contact_error');
    }
  });
});

module.exports = router;

pageRouter.js

Routing direct and redirect traffic.

const express = require('express');
const router = express.Router();

router.get('/', (req, res) => {
  console.log('Request for home recieved');
  res.render('index');
});

router.get('/about', (req, res) => {
  console.log('Request for about page recieved');
  res.render('about');
});

router.get('/contact_send', (req, res) => {
  console.log('Request for contact send page recieved');
  res.render('contact_send');
});

router.get('/contact_error', (req, res) => {
  console.log('Request for contact error page recieved');
  res.render('contact_error');
});

module.exports = router;

app.js

The main difference is to import different routers and use each router according to the different path.

const express = require('express');
const path = require('path');
const bodyParser = require('body-parser');
const { pageRouter } = require('./routes');
const { contact } = require('./routes');

const app = express();
// Set the default views directory to html folder
app.set('views', path.join(__dirname, 'html'));

// Pass messages
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));

// Set the folder for css & java scripts
app.use(express.static(path.join(__dirname, 'css')));
app.use(express.static(path.join(__dirname, 'node_modules')));

// Set the view engine to ejs
app.set('view engine', 'ejs');

app.use('/contact', contact);
app.use('/', pageRouter);

app.listen(3000, () => {
  console.log('Server is running at localhost:3000');
});

All done. This is a simple demonstration on how easy it is to implement automated email functionality by Node.js Express and Nodemailer. Now it is time for you implement your own!