Creating an E-commerce Site with MERN Stack — Part II

Tókos Bence
7 min readJan 15, 2024

--

Retrospection

In the previous article, we set it up the environments and we set it up our base project.

At the moment we have a React frontend project and a Node.js backend project. In this article, I’m focusing on the main aspects of connecting our backend to Mongo DB and learning the Mongo DB basics.

If you are new to these technologies please read the first part if you are familiar then enjoy the ride. :)

Introduction

Connecting Node.js with MongoDB is a crucial step in developing applications that require a backend database.

By combining these two technologies, we can create powerful and efficient applications that can handle large amounts of data and provide fast response times. In this article, we will explore how to connect Node.js with MongoDB using the Mongoose package, which provides a higher level of abstraction over MongoDB and allows us to define data models in a structured way. We will also cover some best practices and tips for working with MongoDB in Node.js.

Setting up the connection

const express = require("express");

//Importing the mongoose package

const mongoose = require("mongoose");

const app = express();

const port = 5000;

//Creating the connection

mongoose

.connect("mongodb://127.0.0.1/ECommerce")

.then(() => console.log("Connected to MongoDB..."))

.catch((err) => console.error("Could not connect to MongoDB..."));

app.get("/", (req, res) => {

res.send("Hello World!");

});

app.listen(port, () => {

console.log(`Server running on port ${port}`);

});

In the above code, we are connecting to a MongoDB database running on localhost. Once the connection is established, we can use the mongoose object to interact with the database.

Additional installation and setup

Cross-Origin Resource Sharing (CORS) is a security mechanism that restricts HTTP requests made from a web application to a different domain. By default, web browsers block such requests to prevent unauthorized access to user data. In the case of a Node.js Express server and a React application, you may encounter a CORS error if the server doesn’t allow requests from the React app’s domain. To avoid this error, you can set up your Express server to allow requests from your React app’s domain by adding the cors middleware and configuring it to allow the appropriate origin. This will allow your React app to make requests to the server and retrieve data without encountering CORS errors.

Install the cors package with the following command:

npm install cors

and add the following code after the mongoose connection and import the package at the top of the file:

const cors = require("cors");
app.use(cors());

Defining our product model

In MongoDB, data is stored as documents, which are similar to JSON objects. Models provide a way to define the structure of these documents, including their fields and data types. By defining models, we can ensure that our data is consistent, valid, and easy to manage. We can also define relationships between different models, which allows us to efficiently query and manipulate data across multiple collections.

As long as we are building an e-commerce website, first, we define a product model. We will cover the basics of schema definition, data validation, and querying, as well as some best practices for working with MongoDB models in Node.js.

In the backend folder create a Models folder and create a product.js. Inside the product.js file, add the following code:

const mongoose = require("mongoose");

const productSchema = new mongoose.Schema({
title: {
type: String,
required: true,
},
description: {
type: String,
required: true,
},
price: {
type: Number,
required: true,
},
discountPercentage: {
type: Number,
required: true,
},
rating: {
type: Number,
required: true,
},
stock: {
type: Number,
required: true,
},
brand: {
type: String,
required: true,
},
category: {
type: String,
required: true,
},
thumbnail: {
type: String,
required: true,
},
images: {
type: String,
required: true,
},
});

const Product = mongoose.model("Product", productSchema);

exports.Product = Product;

In the above code, we are defining a model for a product using the Mongoose package. The model defines the properties that a product can have, such as title, description, price, discount percentage, rating, stock, brand, category, thumbnail, and images. The first line imports the Mongoose package that we need to create a schema. Then, we create a new schema for our product using the mongoose.Schema() method. This method takes an object with key-value pairs, where the key is the name of the property and the value is an object that describes the property.

Each property has a type and required field. The type field specifies the data type of the property, and the required field specifies whether the property is mandatory for a product.

After defining the schema, we create a model using the mongoose.model() method. This method takes two arguments, the name of the model and the schema we created earlier. In this case, the model is named Product and is assigned the schema productSchema.

Finally, we export the Product model so that we can use it in other parts of our application.

The basic CRUD functions

Basic CRUD functions refer to the four fundamental operations of persistent storage for any database system: Create, Read, Update, and Delete. These functions are used to manipulate data in a database.

  • The Create operation is used to add new data to a database.
  • The Read operation is used to retrieve existing data from a database.
  • The Update operation is used to modify existing data in a database.
  • The Delete operation is used to remove data from a database.

CRUD functions are essential in developing any web application or software that deals with data management. They allow us to manage data effectively and efficiently, ensuring that users have access to the right information at the right time.

Based on our product model add the following routes to the index.js:

//Create the new product
app.post("/create", async (req, res) => {
const newProduct = new Product({
title: req.body.title,
description: req.body.description,
price: req.body.price,
discountPercentage: req.body.discountPercentage,
rating: req.body.rating,
stock: req.body.stock,
brand: req.body.brand,
category: req.body.category,
thumbnail: req.body.thumbnail,
images: req.body.images,
});

await Product.create(newProduct);
res.send("Product saved to the database!");
});
//Get the all product list
app.get("/read", async (req, res) => {
const productList = await Product.find();
res.send(JSON.stringify(productList));
});
//Update a product based on the id
app.put("/update/:id", async (req, res) => {
const product_id = req.params.id;
await Product.findByIdAndUpdate(product_id, {
title: req.body.title,
description: req.body.description,
price: req.body.price,
discountPercentage: req.body.discountPercentage,
rating: req.body.rating,
stock: req.body.stock,
brand: req.body.brand,
category: req.body.category,
thumbnail: req.body.thumbnail,
images: req.body.images,
});

res.send("Product updated successfully!");
});
//Delete a product based on the id
app.delete("/delete/:id", async (req, res) => {
const product_id = req.params.id;
await Product.findByIdAndDelete(product_id);
res.send("Product deleted!");
});

Above in the code, you can see the four basic routes for manipulating the products. For testing without the frontend we need an API testing tool. I’m going to use Postman (https://www.postman.com/) but if you are familiar with another API testing tool go for it!

Let’s test!

Using the create method we can add a new product to the database and we get back a success respond!

Add new product

Using the update method we can update the specific product.

Update a product

Using the delete method we can delete a product by id from the database.

Delete a product

Using the get method we can retrieve all products from our database.

Get the products

To perform a check, in Mongo DB Compass, simply follow these steps:

  1. Open Mongo DB Compass.
  2. Connect to the database you want to check.
  3. Select the collection you want to check.
  4. View the documents in the collection and verify that the data is correct.

By performing regular checks in Mongo DB Compass, you can ensure that your data is accurate and up-to-date. This is particularly important when working with large amounts of data, such as in an e-commerce website. So don’t forget to make regular checks to ensure the smooth functioning of your application!

Retrieving just a single product is very similar to the update function, simply you need to include the id and use the .findById() function. At the you return the product object.

I hope you take the exercise as a good challenge and you try to write alone. Give it a try and see how it goes! If things aren’t going well, don’t worry! You can always find a solution on GitHub.

Conclusion

In this article, we covered the basics of interrogating a MongoDB database with Node.js. We created and utilized fundamental CRUD functions, which we’ll delve deeper into in upcoming articles. Don’t forget to check out the code on our GitHub repository, and we’ll see you in the next part!

--

--

Tókos Bence

Hi everyone! I'm an enthusiastic full-stack developer. Please feel free to reach out to me via email (tokosbex@gmail.com) or Twitter (@tokosbex).