CRUD (Create, Read, Update, Delete) operations using Express.js, EJS


Implementing CRUD (Create, Read, Update, Delete) operations using Express.js, EJS, and Mongoose involves setting up a complete web application where users can create, read, update, and delete records in a MongoDB database. Here’s a comprehensive guide to setting up a basic CRUD application:

1. Set Up Your Project

  1. Initialize the Project:

    Create a new directory for your project and initialize it with npm:

    mkdir express-crud-app cd express-crud-app npm init -y
  2. Install Required Packages:

    Install Express, Mongoose, EJS, and other dependencies:

    npm install express mongoose ejs body-parser

2. Define Mongoose Model

Create a schema and model to represent the data in MongoDB.

models/Item.js

const mongoose = require('mongoose'); const itemSchema = new mongoose.Schema({ name: { type: String, required: true }, description: String }); const Item = mongoose.model('Item', itemSchema); module.exports = Item;

3. Set Up Express Application

  1. Create app.js:

    Set up the basic Express server, connect to MongoDB using Mongoose, and configure middleware.

    const express = require('express'); const mongoose = require('mongoose'); const path = require('path'); const bodyParser = require('body-parser'); const app = express(); // Connect to MongoDB mongoose.connect('mongodb://localhost:27017/crud-app', { useNewUrlParser: true, useUnifiedTopology: true }).then(() => { console.log('Connected to MongoDB'); }).catch(err => { console.error('Failed to connect to MongoDB', err); }); // Middleware app.use(bodyParser.urlencoded({ extended: true })); app.use(express.json()); // Set view engine to EJS app.set('view engine', 'ejs'); app.set('views', path.join(__dirname, 'views')); // Import Item model const Item = require('./models/Item'); // Routes will be defined here // Start the server app.listen(3000, () => { console.log('Server is running on http://localhost:3000'); });

4. Define Routes for CRUD Operations

  1. Create Route to Display All Items:

    app.get('/', async (req, res) => { try { const items = await Item.find(); res.render('index', { items }); } catch (err) { console.error(err); res.status(500).send('Server Error'); } });
  2. Create Route to Display Form for Adding a New Item:

    app.get('/items/new', (req, res) => { res.render('new'); });
  3. Create Route to Handle Form Submission for Creating a New Item:

    app.post('/items', async (req, res) => { try { const newItem = new Item(req.body); await newItem.save(); res.redirect('/'); } catch (err) { console.error(err); res.status(500).send('Server Error'); } });
  4. Create Route to Display Form for Editing an Item:

    app.get('/items/edit/:id', async (req, res) => { try { const item = await Item.findById(req.params.id); if (!item) { return res.status(404).send('Item not found'); } res.render('edit', { item }); } catch (err) { console.error(err); res.status(500).send('Server Error'); } });
  5. Create Route to Handle Form Submission for Updating an Item:

    app.post('/items/:id', async (req, res) => { try { const { name, description } = req.body; await Item.findByIdAndUpdate(req.params.id, { name, description }, { new: true }); res.redirect('/'); } catch (err) { console.error(err); res.status(500).send('Server Error'); } });
  6. Create Route to Handle Deleting an Item:

    app.post('/items/delete/:id', async (req, res) => { try { await Item.findByIdAndDelete(req.params.id); res.redirect('/'); } catch (err) { console.error(err); res.status(500).send('Server Error'); } });

5. Create EJS Templates

  1. Create views/index.ejs:

    This template displays the list of items and includes forms to edit and delete items.

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Items List</title> </head> <body> <h1>Items</h1> <a href="/items/new">Add New Item</a> <ul> <% items.forEach(item => { %> <li> <strong><%= item.name %></strong>: <%= item.description %> <a href="/items/edit/<%= item._id %>">Edit</a> <form action="/items/delete/<%= item._id %>" method="POST" style="display:inline;"> <button type="submit">Delete</button> </form> </li> <% }) %> </ul> </body> </html>
  2. Create views/new.ejs:

    This template displays the form for creating a new item.

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Add New Item</title> </head> <body> <h1>Add New Item</h1> <form action="/items" method="POST"> <label for="name">Name:</label> <input type="text" id="name" name="name" required> <br> <label for="description">Description:</label> <textarea id="description" name="description"></textarea> <br> <button type="submit">Add Item</button> </form> <a href="/">Back to Items List</a> </body> </html>
  3. Create views/edit.ejs:

    This template displays the form for editing an existing item.

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Edit Item</title> </head> <body> <h1>Edit Item</h1> <form action="/items/<%= item._id %>" method="POST"> <label for="name">Name:</label> <input type="text" id="name" name="name" value="<%= item.name %>" required> <br> <label for="description">Description:</label> <textarea id="description" name="description"><%= item.description %></textarea> <br> <button type="submit">Update Item</button> </form> <a href="/">Back to Items List</a> </body> </html>

6. Test the CRUD Operations

  1. Start the Server:

    Run your application:

    node app.js
  2. Test Create Operation:

    • Navigate to http://localhost:3000/items/new and add a new item.
    • Check if the item appears in the list.
  3. Test Read Operation:

    • The list of items should be displayed on the homepage (http://localhost:3000).
  4. Test Update Operation:

    • Click the “Edit” link next to an item to update it.
    • Modify the details and submit the form.
    • Verify that the changes are reflected in the item list.
  5. Test Delete Operation:

    • Click the “Delete” button next to an item to remove it.
    • Verify that the item is removed from the list.

Summary

  1. Set Up Project: Initialize the project, install dependencies, and configure Express and Mongoose.
  2. Define Mongoose Model: Create a schema and model for your data.
  3. Implement Routes: Set up routes to handle CRUD operations (create, read, update, delete).
  4. Create EJS Templates: Build views for listing, adding, editing, and deleting items.
  5. Test Operations: Ensure that all CRUD operations work as expected by testing them in the application.