Express + EJS: Rendering Templates with Dynamic Content

res.render()

res.render() is the method that we use inside of an Express.js route to identify an HTML or EJS file that would like to render.

app.get("/", function(req, res){
    res.render(homepage.html);
});

or if you are using an .ejs file

app.get("/", function(req, res){
    res.render(homepage.ejs);
});

What is EJS

EJS is a simple templating language that lets you embed Javascript into HTML templates. IE, build dynamic content into your templates. It is faster and simpler than using a full framework like Angular or React, although less feature rich.

In addition to this post there is a Scotch.io tutorial on EJS here:

Scotch.io: Use EJS To Template Your Node Application

“views” directory

The “views” directory is the default directory that express will look in for EJS template files.

views directory

Adding Variables to EJS templates

Within your somepage.ejs template file you would add

<%= Javascript or Express Variable %>

EX:

<h1> Welcome to the <%= subreddit %> subreddit</h1>

Which you would then pass in the Variable from your Express app file

app.get("/r/:subreddit", function(req, res){
    var sub = req.params.subreddit;
    res.render("subreddit.ejs", {subreddit: sub});
});

An important thing to note about the example above is that we have included a new object in our response. This object is passing in our variable definitions, as they are not automatically shared. So in short the following is happening in our route:

  • Receive a request for a subreddit
  • Capture the requested subreddit and put it in a variable
  • Respond and send back the template and a list of variables

Then if we navigate to any subreddit, for example /r/capybaras

welcome to the capybaras subreddit

If you would like more information on how variables work with route parameters I have an extensive post on that subject here: Ncoughlin: Express.js Route Parameters

EJS Tags

In the example above we showed one of the EJS tags, however there are actually several and they are designed to do different things. There is a full list of tags in the EJS Docs but here are a couple of big ones.

<%= %>

As shown in the example above, the equals tag will output the value into the template so that it is visible. As shown in the word “capybaras” above

<% %>

This is the script tag, which is used for logic and control flow Javascript.

<% if (user) { %>
  <h2><%= user.name %></h2>
<% } %>

Looping Over An Array

Here is an example where we display information about articles by looping over an array.

Here is the routing code in the app:

// array sample
app.get("/articles", function(req, res){
    var articles = [
            {title: "Man Discovers Different Opinion", author: "Reginald", date: "9/2/45"},
            {title: "Tigers Aren't Great Pets", author: "Simon", date: "4/13/95"},
            {title: "Eating Cake for Breakfast", author: "Katie", date: "8/20/13"}
        ];
    res.render("articles.ejs", {articles: articles})
});

And the articles.ejs template file:

<% for(var i=0; i<articles.length; i++){ %>
<h1><%= articles[i].title %></h1>
<h3><%= articles[i].author %></h3>
<h4><%= articles[i].date %></h4>
<% } %>

Which gives us the following result:

basic list of articles

.forEach Loop

A more common way to loop over posts would actually be a .forEach loop.

Here is the routing code in the app:

// array sample 2
app.get("/comments", function(req, res){
    var comments = [
            {author: "Adam", content: "I personally have never encountered a different opinion"},
            {author: "Ryan", content: "But what about Ligers? Are they good pets?"},
            {author: "Nick", content: "This woman is a genius!"}
        ];
    res.render("comments.ejs", {comments: comments});
});

and the comments.ejs template:

<% comments.forEach(function(comment){ %>
<p><strong><%= comment.author %></strong></p>
<p><%= comment.content %></p>
<% }) %>

And the result

basic list of comments