173 lines
No EOL
5.4 KiB
JavaScript
173 lines
No EOL
5.4 KiB
JavaScript
const express = require("express");
|
|
const bodyParser = require("body-parser");
|
|
const mongoose = require("mongoose");
|
|
const crypto = require("crypto");
|
|
const User = require("./models/user");
|
|
const Todo = require("./models/todo");
|
|
const app = express();
|
|
const port = 3030;
|
|
const cors = require("cors");
|
|
const jwt = require("jsonwebtoken");
|
|
const moment = require("moment")
|
|
|
|
app.use(cors());
|
|
app.use(bodyParser.urlencoded({extended: false}));
|
|
app.use(bodyParser.json());
|
|
|
|
//connect with database
|
|
mongoose.connect(process.env.MONGO_URL).then(() => {
|
|
console.log("Connectd to mongodb");
|
|
}).catch((error) => {
|
|
console.log("Error to connect with mongodb", error);
|
|
});
|
|
|
|
app.listen(port, () => {
|
|
console.log("Server is running on port 3030")
|
|
});
|
|
|
|
//login & register
|
|
const generateSecretKey = () => {
|
|
const secretKey = crypto.randomBytes(32).toString("hex")
|
|
return secretKey;
|
|
};
|
|
const secretKey = generateSecretKey();
|
|
|
|
app.post("/register", async(req, res) => {
|
|
try {
|
|
const {name, email, password} = req.body;
|
|
//check existing user
|
|
const existingUser = await User.findOne({email});
|
|
if(existingUser){
|
|
console.log("Email already registered");
|
|
}
|
|
|
|
const newUser = new User({name, email, password});
|
|
await newUser.save();
|
|
res.status(202).json({message: "Registration succeeded!"});
|
|
|
|
} catch (error) {
|
|
console.log("Fail to register an account!", error);
|
|
res.status(500).json({message: "Registration failed!"});
|
|
}
|
|
});
|
|
|
|
app.post("/login", async(req, res) => {
|
|
try {
|
|
const {email, password} = req.body;
|
|
const user = await User.findOne({email});
|
|
if(!user){
|
|
return res.status(401).json({message: "Wrong credentials: invalid username or passowrd"});
|
|
}
|
|
if(user.password !== password){
|
|
return res.status(401).json({message: "Wrong credentials: invalid username or passowrd"});
|
|
}
|
|
const token = jwt.sign({userId:user._id,}, secretKey);
|
|
res.status(200).json({token});
|
|
|
|
} catch (error) {
|
|
console.log("Fail to login!", error);
|
|
res.status(500).json({message: "Login failed!"});
|
|
}
|
|
});
|
|
//todo list
|
|
app.post("/todos/:userId", async(req, res) => {
|
|
try {
|
|
const userId = req.params.userId;
|
|
const {title, category} = req.body;
|
|
const newTodo = new Todo({
|
|
title,
|
|
category,
|
|
dueDate: moment().format("MMM Do YY")
|
|
});
|
|
await newTodo.save();
|
|
|
|
//add todo id
|
|
const user = await User.findById(userId);
|
|
if(!user){
|
|
res.status(404).json({message: "User not found!"});
|
|
}
|
|
user?.todos.push(newTodo._id);
|
|
await user.save();
|
|
|
|
res.status(200).json({message: "A list is added successfully!", todo:newTodo});
|
|
} catch (error) {
|
|
res.status(500).json({message: "Fail to add a list!"});
|
|
console.log(error)
|
|
}
|
|
});
|
|
|
|
app.get("/users/:userId/todos", async(req, res) => {
|
|
try {
|
|
const userId = req.params.userId;
|
|
const user = await User.findById(userId).populate("todos");
|
|
if(!user){
|
|
return res.status(404).json({message: "user not found"});
|
|
}
|
|
res.status(200).json({todos:user.todos});
|
|
} catch (error) {
|
|
res.status(500).json({message: "Error, something went wrong!"});
|
|
}
|
|
});
|
|
|
|
app.patch("/todos/:todoId/complete", async(req, res) => {
|
|
try {
|
|
const todoId = req.params.todoId;
|
|
const updatedTodo = await Todo.findByIdAndUpdate(todoId, {
|
|
status:"completed"
|
|
},
|
|
{new:true}
|
|
);
|
|
if(!updatedTodo){
|
|
return res.status(404).json({error:"Todo not found"});
|
|
}
|
|
res.status(200).json({message: "Mark as completed!", todo:updatedTodo});
|
|
} catch (error) {
|
|
res.status(500).json({message: "Error, something went wrong!"});
|
|
}
|
|
});
|
|
//calendar
|
|
app.get("/users/:userId/todos/completed/:date", async(req, res) => {
|
|
try {
|
|
const date = req.params.date;
|
|
const userId = req.params.userId;
|
|
const user = await User.findById(userId);
|
|
const userToDos = await user.populate('todos');
|
|
const toDos = userToDos.todos;
|
|
|
|
const completedTodos = toDos.filter(item => {
|
|
return item.status == "completed" && // status filter
|
|
item.createdAt.getTime() >= new Date(`${date}T00:00:00.000Z`) && // gte filter
|
|
item.createdAt.getTime() <= new Date(`${date}T23:59:59.999Z`) // lt filter
|
|
});
|
|
|
|
|
|
res.status(200).json({completedTodos})
|
|
} catch (error) {
|
|
res.status(500).json({message: "Error, something went wrong!"});
|
|
console.log(error)
|
|
}
|
|
});
|
|
|
|
app.get("/users/:userId/todos/count", async(req, res) => {
|
|
try {
|
|
const userId = req.params.userId;
|
|
const user = await User.findById(userId);
|
|
const userToDos = await user.populate('todos');
|
|
const toDos = userToDos.todos;
|
|
const completedTodos = toDos.filter(item => {
|
|
return item.status == "completed"
|
|
});
|
|
const pendingTodos = toDos.filter(item => {
|
|
return item.status == "pending"
|
|
});
|
|
|
|
const totalCompletedTodos = completedTodos.length;
|
|
const totalPendingTodos = pendingTodos.length;
|
|
|
|
res.status(200).json({totalCompletedTodos, totalPendingTodos});
|
|
|
|
} catch (error) {
|
|
res.status(500).json({message: "Error, something went wrong!"});
|
|
console.log(error)
|
|
}
|
|
}); |