Introduction
In modern web development, integrating a backend with a scalable database is essential for building dynamic applications. In this blog, we will explore how to create a RESTful API using Node.js, Express.js, and Supabase (a powerful open-source alternative to Firebase). This API will handle basic CRUD (Create, Read, Update, Delete) operations for user management.
Why Supabase?
Supabase is an open-source backend-as-a-service (BaaS) that provides features like:
- PostgreSQL database with real-time capabilities
- Authentication and authorization
- Storage for managing files
- Auto-generated APIs for database interactions
With Supabase, you get a fully managed PostgreSQL database with an easy-to-use JavaScript SDK.
Tech Stack
- Node.js: Server-side JavaScript runtime
- Express.js: Minimalist web framework for Node.js
- Supabase: PostgreSQL-based backend
- dotenv: For managing environment variables
- Swagger: API documentation tool
- CORS: Enables cross-origin resource sharing
Project Setup
1. Clone the Repository
git clone https://github.com/manthanank/nodejs-supabase.git
cd nodejs-supabase
2. Install Dependencies
npm install
3. Configure Environment Variables
Create a .env
file and add your Supabase credentials:
SUPABASE_URL=https://your-project-url.supabase.co
SUPABASE_KEY=your-anon-or-service-role-key
PORT=5000
4. Run the Application
Start the development server:
npm run dev
For production:
npm start
Your API will now be running at http://localhost:5000
.
Project Structure
nodejs-supabase
├── .env # Environment variables
├── index.js # Main application entry point
├── package.json # Project dependencies and scripts
├── README.md # Project documentation
├── config/
│ ├── supabaseClient.js # Supabase client configuration
│ └── swagger.js # Swagger configuration
├── controllers/
│ └── userController.js # User controller functions
├── routes/
│ └── userRoutes.js # API route definitions with Swagger docs
└── services/
└── userService.js # Business logic for user operations
API Endpoints
Users CRUD Operations
Method | Endpoint | Description |
---|---|---|
POST | /api/users |
Create a new user |
GET | /api/users |
Get all users |
GET | /api/users/search?query=name |
Search users by name |
GET | /api/users/:id |
Get user by ID |
GET | /api/users/email/:email |
Get user by email |
PUT | /api/users/:id |
Update user by ID |
DELETE | /api/users/:id |
Delete user by ID |
Key Implementations
Supabase Client Setup
Create config/supabaseClient.js
:
import { createClient } from "@supabase/supabase-js";
import dotenv from "dotenv";
dotenv.config();
const supabase = createClient(
process.env.SUPABASE_URL,
process.env.SUPABASE_KEY
);
export default supabase;
CRUD Operations in userService.js
Create User
export const createUser = async (userData) => {
const { data, error } = await supabase
.from("users")
.insert([userData])
.select();
if (error) throw new Error(error.message);
return data;
};
Fetch Users
export const getUsers = async () => {
const { data, error } = await supabase.from("users").select("*");
if (error) throw new Error(error.message);
return data;
};
Update User
export const updateUser = async (id, updates) => {
const { data, error } = await supabase
.from("users")
.update(updates)
.eq("id", id)
.select();
if (error) throw new Error(error.message);
return data;
};
Delete User
export const deleteUser = async (id) => {
const { error } = await supabase
.from("users")
.delete()
.eq("id", id);
if (error) throw new Error(error.message);
return { success: true, message: "User deleted successfully" };
};
API Routes in userRoutes.js
import express from "express";
import { addUser, fetchUsers, fetchUserById, fetchUserByEmail, modifyUser, removeUser } from "../controllers/userController.js";
const router = express.Router();
router.post("/users", addUser);
router.get("/users", fetchUsers);
router.get("/users/:id", fetchUserById);
router.get("/users/email/:email", fetchUserByEmail);
router.put("/users/:id", modifyUser);
router.delete("/users/:id", removeUser);
export default router;
Testing the API
Create a User
curl -X POST http://localhost:5000/api/users \
-H "Content-Type: application/json" \
-d '{"name": "John Doe", "email": "[email protected]", "age": 30}'
Search Users
curl -X GET http://localhost:5000/api/users/search?query=John
Swagger API Documentation
To enable API documentation, navigate to:
http://localhost:5000/api-docs
This provides an interactive UI for testing endpoints.
Conclusion
In this blog, we covered how to build a CRUD API using Node.js, Express.js, and Supabase. Supabase simplifies database management while offering powerful features like authentication and real-time updates. By integrating Swagger, we also ensured that our API is well-documented and easy to use.
This API can be extended with additional functionalities like authentication, role-based access control, and real-time updates.
Happy coding! 🚀
Exploring the Code
Visit the GitHub repository to explore the code in detail.