CRUD Operations Using a JSON File with Express.js
đ Introduction
CRUD stands for Create, Read, Update, and Delete. These are the four fundamental operations performed on data in most web applications. While production applications typically use databases, beginners can learn CRUD concepts by storing data in a JSON file. Express.js, along with Node.js's fs module, makes it easy to read from and write to JSON files.
Information
Using a JSON file as a data store is suitable for learning, prototypes, and small applications. For production applications, use a database such as MongoDB, MySQL, or PostgreSQL.
đ Prerequisites
- Node.js installed.
- Express.js installed.
- Basic knowledge of Express routing.
- Basic understanding of JSON.
đ Project Structure
express-app
data.json
index.js
package.json
đ Creating the JSON File
Create a file named data.json to store user information.
data.json
[
{
"id": 1,
"name": "Alice",
"email": "alice@example.com"
},
{
"id": 2,
"name": "Bob",
"email": "bob@example.com"
}
]đ Setting Up the Express Server
index.js
const express = require('express');
const fs = require('fs');
const app = express();
app.use(express.json());
const FILE_PATH = './data.json';
app.listen(3000, () => {
console.log('Server running on http://localhost:3000');
});Tip
The express.json() middleware parses incoming JSON request bodies and makes them available through req.body.
đ READ Operation
Retrieve all records from the JSON file.
GET /users
app.get('/users', (req, res) => {
const data = JSON.parse(fs.readFileSync(FILE_PATH));
res.json(data);
});â CREATE Operation
Add a new user to the JSON file.
POST /users
app.post('/users', (req, res) => {
const users = JSON.parse(fs.readFileSync(FILE_PATH));
const newUser = {
id: users.length + 1,
name: req.body.name,
email: req.body.email
};
users.push(newUser);
fs.writeFileSync(FILE_PATH, JSON.stringify(users, null, 2));
res.status(201).json(newUser);
});âī¸ UPDATE Operation
Update an existing user's information using their ID.
PUT /users/:id
app.put('/users/:id', (req, res) => {
const users = JSON.parse(fs.readFileSync(FILE_PATH));
const user = users.find(
user => user.id === Number(req.params.id)
);
if (!user) {
return res.status(404).send('User not found');
}
user.name = req.body.name;
user.email = req.body.email;
fs.writeFileSync(FILE_PATH, JSON.stringify(users, null, 2));
res.json(user);
});đ DELETE Operation
Remove a user from the JSON file.
DELETE /users/:id
app.delete('/users/:id', (req, res) => {
const users = JSON.parse(fs.readFileSync(FILE_PATH));
const filteredUsers = users.filter(
user => user.id !== Number(req.params.id)
);
fs.writeFileSync(
FILE_PATH,
JSON.stringify(filteredUsers, null, 2)
);
res.send('User deleted successfully.');
});đ CRUD Workflow
Client
HTTP Request
HTTP Response
Express Server
Read JSON File
Perform CRUD Operation
Write Updated Data
đ Request Lifecycle
Client sends an HTTP request.
Express reads the JSON file.
The requested CRUD operation is performed.
Updated data is written back to the JSON file (if required).
The server sends an HTTP response.
đ CRUD Endpoints
| HTTP Method | Endpoint | Operation |
|---|---|---|
| GET | /users | Retrieve all users. |
| POST | /users | Create a new user. |
| PUT | /users/:id | Update an existing user. |
| DELETE | /users/:id | Delete a user. |
đ§Ē Example API Requests
GET
POST
PUT
DELETE
Retrieve Users
GET /usersCreate User
POST /users
Content-Type: application/json
{
"name": "Charlie",
"email": "charlie@example.com"
}Update User
PUT /users/2
Content-Type: application/json
{
"name": "Bob Smith",
"email": "bobsmith@example.com"
}Delete User
DELETE /users/2â ī¸ Limitations of Using a JSON File
| Limitation | Description |
|---|---|
| Performance | The entire file is read and written for each request. |
| Concurrency | Simultaneous writes can overwrite data. |
| Scalability | Not suitable for large datasets. |
| Data Integrity | No transactions or advanced consistency guarantees. |
đĄ Best Practices
- Use express.json() to parse JSON request bodies.
- Validate incoming request data before saving it.
- Check whether a resource exists before updating or deleting it.
- Use asynchronous file operations such as fs.promises in real-world applications to avoid blocking the event loop.
- Use unique IDs instead of relying on the array length when creating new records.
- Switch to a database as your application grows.
Best Practice
A JSON file is an excellent way to understand CRUD operations and Express.js routing. For production environments, replace file storage with a database to improve performance, scalability, and reliability.
đ Learn More
Explore the official documentation:
âĸ Express.js Official Documentation
âĸ Node.js File System (fs) Module
âĸ MDN Web Docs - JSON
đ Summary
Summary
CRUD operations using a JSON file provide a simple way to learn data management in Express.js. By combining Express routes with the Node.js fs module, you can create, read, update, and delete records stored in a JSON file. Although this approach is ideal for learning and small projects, production applications should use a dedicated database for better scalability and data integrity.