Express.js Framework

Introduction to Express.js

Express.js is a minimal and flexible Node.js web application framework that provides a robust set of features for web and mobile applications.

Key Features:

  • Robust routing
  • Focus on high performance
  • Super-high test coverage
  • HTTP helpers (redirection, caching, etc)
  • View system supporting 14+ template engines
  • Content negotiation
  • Executable for generating applications

Why Express.js?

Express.js is one of the most popular web frameworks for Node.js, known for its simplicity, flexibility, and large ecosystem of middleware.

Getting Started

Installation

# Create a new directory
mkdir my-express-app
cd my-express-app

# Initialize package.json
npm init -y

# Install Express
npm install express
const express = require('express');
const app = express();
const port = 3000;

app.get('/', (req, res) => {
  res.send('Hello World!');
});

app.listen(port, () => {
  console.log(`App listening at http://localhost:${port}`);
});

Project Structure

my-express-app/
  ├── node_modules/
  ├── public/
  │   ├── css/
  │   ├── js/
  │   └── img/
  ├── routes/
  │   ├── index.js
  │   └── users.js
  ├── views/
  │   ├── layouts/
  │   └── partials/
  ├── app.js
  ├── package.json
  └── README.md

Routing

Basic Routing

// Basic routes
app.get('/', (req, res) => {
  res.send('Home page');
});

app.post('/submit', (req, res) => {
  res.send('Got a POST request');
});

// Route parameters
app.get('/users/:userId', (req, res) => {
  res.send(`User ID: ${req.params.userId}`);
});

// Query strings
app.get('/search', (req, res) => {
  const query = req.query.q;
  res.send(`Search query: ${query}`);
});

Router Module

// routes/users.js
const express = require('express');
const router = express.Router();

router.get('/', (req, res) => {
  res.send('Users list');
});

router.get('/:id', (req, res) => {
  res.send(`User profile: ${req.params.id}`);
});

module.exports = router;

// app.js
const usersRouter = require('./routes/users');
app.use('/users', usersRouter);

Middleware

Built-in Middleware

// Body parser middleware
app.use(express.json());
app.use(express.urlencoded({ extended: true }));

// Static files middleware
app.use(express.static('public'));

// Cookie parser
const cookieParser = require('cookie-parser');
app.use(cookieParser());

Custom Middleware

// Logger middleware
const logger = (req, res, next) => {
  console.log(`${req.method} ${req.url} ${new Date()}`);
  next();
};

// Error handling middleware
const errorHandler = (err, req, res, next) => {
  console.error(err.stack);
  res.status(500).send('Something broke!');
};

app.use(logger);
app.use(errorHandler);

Template Engines

EJS Setup

// Install EJS
// npm install ejs

// Set up EJS
app.set('view engine', 'ejs');
app.set('views', './views');

// Render template
app.get('/', (req, res) => {
  res.render('index', {
    title: 'Home Page',
    message: 'Welcome to Express'
  });
});

EJS Template





    
    
    

  <%= title %>




  

<%= message %>

<% if (users.length) { %>
    <% users.forEach(user => { %>
  • <%= user.name %>
  • <% }); %>
<% } %>

Database Integration

MongoDB with Mongoose

// Install Mongoose
// npm install mongoose

// Connect to MongoDB
const mongoose = require('mongoose');
mongoose.connect('mongodb://localhost/myapp', {
  useNewUrlParser: true,
  useUnifiedTopology: true
});

// Define Schema
const userSchema = new mongoose.Schema({
  name: String,
  email: { type: String, required: true, unique: true },
  password: { type: String, required: true },
  createdAt: { type: Date, default: Date.now }
});

const User = mongoose.model('User', userSchema);

Database Operations

// Create
app.post('/users', async (req, res) => {
  try {
    const user = new User(req.body);
    await user.save();
    res.status(201).send(user);
  } catch (error) {
    res.status(400).send(error);
  }
});

// Read
app.get('/users', async (req, res) => {
  try {
    const users = await User.find({});
    res.send(users);
  } catch (error) {
    res.status(500).send(error);
  }
});

Authentication

Passport.js Setup

// Install required packages
// npm install passport passport-local express-session

const passport = require('passport');
const LocalStrategy = require('passport-local').Strategy;
const session = require('express-session');

// Session setup
app.use(session({
  secret: 'your-secret-key',
  resave: false,
  saveUninitialized: false
}));

app.use(passport.initialize());
app.use(passport.session());

Authentication Logic

passport.use(new LocalStrategy(
  async (username, password, done) => {
    try {
      const user = await User.findOne({ username });
      if (!user) {
        return done(null, false);
      }
      const isValid = await user.validatePassword(password);
      if (!isValid) {
        return done(null, false);
      }
      return done(null, user);
    } catch (error) {
      return done(error);
    }
  }
));

// Protected route
app.get('/profile',
  isAuthenticated,
  (req, res) => {
    res.render('profile', { user: req.user });
  }
);

Deployment

Deployment Checklist:

  • Set environment variables
  • Configure error handling
  • Set up logging
  • Enable HTTPS
  • Set up monitoring

Production Setup

// Environment variables
require('dotenv').config();

// Production error handler
if (process.env.NODE_ENV === 'production') {
  app.use((err, req, res, next) => {
    console.error(err.stack);
    res.status(500).send('Server Error');
  });
}

// Start server
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => {
  console.log(`Server is running on port ${PORT}`);
});