Raddy Website Design & Development Tutorials

Display Node.js Flash Messages using EJS

By Raddy in NodeJs ·

In this tutorial, we are going to learn how to use connect-flash to display server operation messages with EJS. We will use express-sessions and cookies-parser alongside the connect-flash package to deliver the messages to the views.

Connect-flash is used for passing messages between pages to display server operations such as success or errors messages. An example would be a registration form. Once the registration form is submitted you might want to display a ‘success’ or ‘error’ message to the user.

In this example, we will create a very simple page with a form where the user can enter their name and submit. On form submission, we can then display the user’s name and a success message.

Let’s start by creating a new application with Node.js.

To do that, create a new project folder and then run the following command in Command Line (Mac / Linux) or Powershell (Windows).

npm init

This will initialise a new project for you and it’s going to ask you a few questions about your project. The most important one is to give your package a name and then you can just keep pressing enter until the installation is over.

You can skip all questions by adding the “-y” flag like in the example below:

npm init -y

At this point, you should see a file called package.json in your project folder.

Dependencies Installation

We have to install a few dependencies (unfortunately too many, if you ask me):

[x] express
[x] express-session
[x] cookie-parser
[x] connect-flash
[x] ejs

Open the Command Line / Terminal / Powershell and install the dependencies listed above just like so:

npm install express express-session cookie-parser connect-flash ejs

Your packages.json file should look similar to this:

  "name": "Nodejs-EJS-Flash-Messages",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  "repository": {
    "type": "git",
    "url": "git+https://github.com/RaddyTheBrand/Nodejs-EJS-Flash-Messages.git"
  "keywords": [],
  "author": "",
  "license": "ISC",
  "bugs": {
    "url": "https://github.com/RaddyTheBrand/Nodejs-EJS-Flash-Messages/issues"
  "homepage": "https://github.com/RaddyTheBrand/Nodejs-EJS-Flash-Messages#readme",
  "dependencies": {
    "connect-flash": "^0.1.1",
    "cookie-parser": "^1.4.5",
    "ejs": "^3.1.6",
    "express": "^4.17.1",
    "express-session": "^1.17.2"

Note that the version of the dependencies might change in the future.

Project Structure

Our project is going to be simple. We just need our main application file which we will call ‘app.js‘ and we need a home page file which we will call ‘index.ejs‘.

📂 node_modules
📂 views
 📂 pages
  📜 index.ejs
🌍 app.js
📜 package-lock.json
📜 package-json

Creating our application – app.js

Instead of splitting everything into a separate section, I have briefly explained what each line of code does.

// Require the NPM packages that we need
const express = require('express');
const session = require('express-session');
const cookieParser = require('cookie-parser');
const flash = require('connect-flash');

// Initalise a new express application
const app = express();

// Set a default environment port or cutom port - 5000
const port = process.env.PORT || 5000;

// This allows us to pass data from the form
app.use(express.urlencoded({extended: true}));

// Set Cookie Parser, sessions and flash
  secret : 'something',
  cookie: { maxAge: 60000 },
  resave: true,
  saveUninitialized: true

// Setting our view engine as EJS
app.set('view engine', 'ejs');

/** GET /  Home Page */
app.get('/', function (req, res) {
  // Set a flash name and pass it to the home page.
  // If empty, we won't display. That's handled by EJS.  
  const userName = req.flash('user');
  res.render('pages/index', { userName } )

/** Post /  Home Page */
app.post('/', function(req, res){
  // On form submit set the flash user object to the userName input from the form
  req.flash('user', req.body.userName);

// Start out application
console.log(`Server is listening on port ${port}`);

Before we move on, let’s quickly reference some of the options that we used for the Cookie-Parser and Express-Sessions.

Cookie-Parser Options

cookieParser(secret, options)

Create a new cookie parser middleware function using the given secret and options.

  • secret a string or array used for signing cookies. This is optional and if not specified, will not parse signed cookies. If a string is provided, this is used as the secret. If an array is provided, an attempt will be made to unsign the cookie with each secret in order.
  • options an object that is passed to cookie.parse as the second option. See cookie for more information.
    • decode a function to decode the value of the cookie

Source: https://expressjs.com/en/resources/middleware/cookie-parser.html

Session Options


Settings object for the session ID cookie. The default value is { path: '/', httpOnly: true, secure: false, maxAge: null }.


Specifies the Date object to be the value for the Expires Set-Cookie attribute. By default, no expiration is set, and most clients will consider this a “non-persistent cookie” and will delete it on a condition like exiting a web browser application.


Forces the session to be saved back to the session store, even if the session was never modified during the request. Depending on your store this may be necessary, but it can also create race conditions where a client makes two parallel requests to your server and changes made to the session in one request may get overwritten when the other request ends, even if it made no changes (this behavior also depends on what store you’re using).

The default value is true, but using the default has been deprecated, as the default will change in the future. Please research into this setting and choose what is appropriate to your use-case. Typically, you’ll want false.

How do I know if this is necessary for my store? The best way to know is to check with your store if it implements the touch method. If it does, then you can safely set resave: false. If it does not implement the touch method and your store sets an expiration date on stored sessions, then you likely need resave: true.


Force the session identifier cookie to be set on every response. The expiration is reset to the original maxAge, resetting the expiration countdown.

The default value is false.

With this enabled, the session identifier cookie will expire in maxAge since the last response was sent instead of in maxAge since the session was last modified by the server.

This is typically used in conjuction with short, non-session-length maxAge values to provide a quick timeout of the session data with reduced potential of it occurring during on going server interactions.

Note When this option is set to true but the saveUninitialized option is set to false, the cookie will not be set on a response with an uninitialized session. This option only modifies the behavior when an existing session was loaded for the request.


Forces a session that is “uninitialized” to be saved to the store. A session is uninitialized when it is new but not modified. Choosing false is useful for implementing login sessions, reducing server storage usage, or complying with laws that require permission before setting a cookie. Choosing false will also help with race conditions where a client makes multiple parallel requests without a session.

The default value is true, but using the default has been deprecated, as the default will change in the future. Please research into this setting and choose what is appropriate to your use-case.

Note if you are using Session in conjunction with PassportJS, Passport will add an empty Passport object to the session for use after a user is authenticated, which will be treated as a modification to the session, causing it to be saved. This has been fixed in PassportJS 0.3.0

Source: https://www.npmjs.com/package/express-session

Now let’s build or home page and the form inside it.

Building our Home page using EJS

We’ll keep the page simple. Let’s create a very basic file with the ‘userName‘ object that we are passing from ‘app.js‘.

<!DOCTYPE html>
<html lang="en">
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Flash Messages</title>

  <h1>Hello <%= userName %></h1>

  <form action="/" method="POST">
    <label for="userName">Name:</label>
    <!-- name - userName is what we use to grab the data -->
    <input type="text" name="userName"><br><br>
    <button type="submit">Submit</button>
  <% if(userName != '') { %>
    <h1 style="color: green; font-family: Arial, Helvetica, sans-serif;">Your form has been submitted. Thank you, <%= userName %></h1>
  <% } %>


Finally, let’s run our application and submit the form.

To run this, open your console and run “app.js” with node by doing the following:

node app.js

This should run the application and you should be able to the website we just created under ‘localhost:5000‘.

That’s everything from this super quick tutorial. I hope that you found it useful.

More Resources:

Thank you for reading this article. Please consider subscribing to my YouTube Channel. It’s FREE!

  1. scathing says:

    Ꮩery good blog! Do yoս have any tips for aspiring writers?

    I’m hoping to start my own site soon but I’m a little lost on eveгything.
    Wօuld you recommend starting ԝith a free platform like WordPress or
    go for a pɑid option? There are so many choiⅽes оut there that I’m totally ϲοnfused ..
    Any suɡgestions? Thank yoս!

    1. Raddy says:

      My tip would be to just start. It doesn’t matter too much if you are on a paid platform or not when you are starting out. Saying this, there are benefits to owning your website.
      I do like the self-hosted WordPress and that would be my first recommendation. Easy to use, great for SEO, amazing plugins, themes and you can do pretty much anything you wish with it. As long as you are tech-savvy and you can set up a WordPress blog, you should be good.

      What are the other platforms that you are thinking of using?

      Shameless plug, but if you are thinking of hosting your own WordPress website and registering a professional domain name check out Hostinger (affiliate link below). It’s super cheap, easy to use and you get a free domain with it.

      I hope this helps and if you have any other questions I’ll be happy to answer.

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.