In this tutorial, we'll guide you through the process of building your own todo list app from scratch, empowering you to manage your tasks seamlessly.
Why Next.js and MongoDB?
Next.js, a React framework, offers a fantastic developer experience with its efficient server-side rendering and simple API routes. MongoDB, a flexible and scalable NoSQL database, provides the perfect backend solution for storing and managing our todo list data. Combining these two technologies allows us to create a dynamic and responsive application with minimal setup.Setting Up Your Environment
Before diving into the code, make sure you have Node.js and npm installed on your machine. Then, create a new Next.js project by running:npx create-next-app@latest my-todo-app cd my-todo-app
npm install mongoose
Creating the Todo Model
We'll start by defining the structure of our todo items. Create a new file called `Todo.js` in the `models` directory:// models/Todo.js import mongoose from 'mongoose'; const todoSchema = new mongoose.Schema({ title: { type: String, required: true }, completed: { type: Boolean, default: false }, createdAt: { type: Date, default: Date.now }, }); const Todo = mongoose.model('Todo', todoSchema); export default Todo;
Setting Up MongoDB
Next, let's connect our Next.js app to MongoDB. Create a new file called `db.js` in the `utils` directory:// utils/db.js import mongoose from 'mongoose'; async function connectDB() { try { await mongoose.connect(process.env.MONGODB_URI, { useNewUrlParser: true, useUnifiedTopology: true, }); console.log('Connected to MongoDB'); } catch (error) { console.error('Error connecting to MongoDB:', error); process.exit(1); } } export default connectDB;
Building the Todo API
Now, let's create our API routes for handling todo CRUD operations. Inside the `pages/api` directory, create a new file called `todos.js`:// pages/api/todos.js import connectDB from '../../utils/db'; import Todo from '../../models/Todo'; connectDB(); export default async function handler(req, res) { if (req.method === 'GET') { try { const todos = await Todo.find({}); res.status(200).json(todos); } catch (error) { res.status(500).json({ message: 'Server error' }); } } else if (req.method === 'POST') { try { const { title } = req.body; const todo = new Todo({ title }); await todo.save(); res.status(201).json(todo); } catch (error) { res.status(500).json({ message: 'Server error' }); } } }
Building the Frontend
Finally, let's create the frontend components for displaying and managing our todo list. Replace the contents of `pages/index.js` with the following code:// pages/index.js import { useState, useEffect } from 'react'; export default function Home() { const [todos, setTodos] = useState([]); const [title, setTitle] = useState(''); useEffect(() => { fetch('/api/todos') .then((res) => res.json()) .then((data) => setTodos(data)) .catch((error) => console.error('Error fetching todos:', error)); }, []); const handleSubmit = async (e) => { e.preventDefault(); try { const res = await fetch('/api/todos', { method: 'POST', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify({ title }), }); const data = await res.json(); setTodos([...todos, data]); setTitle(''); } catch (error) { console.error('Error adding todo:', error); } }; return ( <div> <h1>Todo List</h1> <form onSubmit={handleSubmit}> <input type="text" value={title} onChange={(e) => setTitle(e.target.value)} placeholder="Add a new todo" /> <button type="submit">Add Todo</button> </form> <ul> {todos.map((todo) => ( <li key={todo._id}>{todo.title}</li> ))} </ul> </div> ); }
Conclusion
Congratulations! You've successfully built a todo list app with Next.js and MongoDB. This project serves as a foundation for expanding and customizing your productivity tools. Experiment with additional features like editing and deleting todos, implementing user authentication, or styling the UI to match your preferences.The possibilities are endless! Start organizing your tasks effortlessly and boost your productivity today.