Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Binary file added .DS_Store
Binary file not shown.
8 changes: 4 additions & 4 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
{
"editor.fontSize": 42,
"terminal.integrated.fontSize": 62
}
// {
// "editor.fontSize": 42,
// "terminal.integrated.fontSize": 62
// }
5 changes: 3 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
{
"name": "rap-name-api",
"version": "1.0.0",
"description": "",
"description": "npm install add DB_STRING to .env file",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
"test": "echo \"Error: no test specified\" && exit 1",
"start": "node server.js"
},
"author": "",
"license": "ISC",
Expand Down
88 changes: 44 additions & 44 deletions public/js/main.js
Original file line number Diff line number Diff line change
@@ -1,72 +1,72 @@
const deleteBtn = document.querySelectorAll('.fa-trash')
const item = document.querySelectorAll('.item span')
const itemCompleted = document.querySelectorAll('.item span.completed')
const deleteBtn = document.querySelectorAll('.fa-trash')//variable that selects all elements with the trash can class
const item = document.querySelectorAll('.item span')//variable that selects all spans with the class item
const itemCompleted = document.querySelectorAll('.item span.completed')//selects all spans with the class item and also completed

Array.from(deleteBtn).forEach((element)=>{
element.addEventListener('click', deleteItem)
Array.from(deleteBtn).forEach((element)=>{//creates an array from selection of deleteBtn and loops for each element
element.addEventListener('click', deleteItem)//ads an event listener, listens for click and runs deleteItem function
})

Array.from(item).forEach((element)=>{
element.addEventListener('click', markComplete)
Array.from(item).forEach((element)=>{//creates array from item variable and loop each elements
element.addEventListener('click', markComplete)//ads event listener, listen for click and runs markComplete function
})

Array.from(itemCompleted).forEach((element)=>{
element.addEventListener('click', markUnComplete)
Array.from(itemCompleted).forEach((element)=>{//creates arr and loop all itemsCompleted
element.addEventListener('click', markUnComplete)//ads event listener listener for click and runs function markUnComplete
})

async function deleteItem(){
const itemText = this.parentNode.childNodes[1].innerText
async function deleteItem(){//declares async function
const itemText = this.parentNode.childNodes[1].innerText//variable that holds the inner text inside the list span
try{
const response = await fetch('deleteItem', {
method: 'delete',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({
'itemFromJS': itemText
const response = await fetch('deleteItem', {//creates a response variable that waits on a fetch to get data from the result of deleteItem
method: 'delete',//sets the CRUD method for the route
headers: {'Content-Type': 'application/json'},//specify the content type to be JSON
body: JSON.stringify({//specify the content type to be stringify JSON
'itemFromJS': itemText//sets body to inner text of the list item
})
})
const data = await response.json()
console.log(data)
location.reload()
const data = await response.json()//declares variable waiting for response with JSON
console.log(data)//console log the response data
location.reload()//refresh page

}catch(err){
console.log(err)
}catch(err){//grab all errors
console.log(err)//log errors to console
}
}

async function markComplete(){
const itemText = this.parentNode.childNodes[1].innerText
async function markComplete(){//declares async function
const itemText = this.parentNode.childNodes[1].innerText//variable that holds the inner text inside the list span
try{
const response = await fetch('markComplete', {
method: 'put',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({
'itemFromJS': itemText
const response = await fetch('markComplete', {//creates a res variable that waits on a fetch to get fata from res of function markedComplete
method: 'put',//sets the CRUD method update
headers: {'Content-Type': 'application/json'},//specify the content type to be JSON
body: JSON.stringify({//specify the content type to be stringify JSON
'itemFromJS': itemText//sets body to inner text of the list item
})
})
const data = await response.json()
console.log(data)
location.reload()
const data = await response.json()//declares variable waiting for response with JSON
console.log(data)//console log the response data
location.reload()//refresh page

}catch(err){
console.log(err)
}catch(err){//grab all errors
console.log(err)//log errors to console
}
}

async function markUnComplete(){
const itemText = this.parentNode.childNodes[1].innerText
const itemText = this.parentNode.childNodes[1].innerText//variable that holds the inner text inside the list span
try{
const response = await fetch('markUnComplete', {
method: 'put',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({
'itemFromJS': itemText
const response = await fetch('markUnComplete', {//creates a res variable that waits on a fetch to get fata from res of function markedUnComplete
method: 'put',//sets the CRUD method update
headers: {'Content-Type': 'application/json'},//specify the content type to be JSON
body: JSON.stringify({//specify the content type to be stringify JSON
'itemFromJS': itemText//sets body to inner text of the list item
})
})
const data = await response.json()
console.log(data)
location.reload()
const data = await response.json()//declares variable waiting for response with JSON
console.log(data)//console log the response data
location.reload()//refresh page

}catch(err){
console.log(err)
}catch(err){//grab all errors
console.log(err)//log errors to console
}
}
108 changes: 55 additions & 53 deletions server.js
Original file line number Diff line number Diff line change
@@ -1,30 +1,32 @@
const express = require('express')
const app = express()
const MongoClient = require('mongodb').MongoClient
const PORT = 2121
require('dotenv').config()
const express = require('express') //variable to hold express being required
const app = express()//variable app to hold express
const MongoClient = require('mongodb').MongoClient //variable to say the client is mongodb
const PORT = 2121 //especifying the port for server to listen
require('dotenv').config() //tells the server .env is being used


let db,
dbConnectionStr = process.env.DB_STRING,
dbName = 'todo'
let db, //setting a global variable to hold database as db
dbConnectionStr = process.env.DB_STRING, //connection string being process using .env using the DB_STRING variable
dbName = 'todo' //setting database name to todo

MongoClient.connect(dbConnectionStr, { useUnifiedTopology: true })
.then(client => {
console.log(`Connected to ${dbName} Database`)
db = client.db(dbName)
MongoClient.connect(dbConnectionStr, { useUnifiedTopology: true }) //sets the conection string off database to connect to mongodb
.then(client => { //mongo client returns a promise after the promise is resolve we store response as client
console.log(`Connected to ${dbName} Database`) //console log connected to the name of database
db = client.db(dbName) //assigning database variable db to hold client method
})

app.set('view engine', 'ejs')
app.use(express.static('public'))
app.use(express.urlencoded({ extended: true }))
app.use(express.json())

//middleware
app.set('view engine', 'ejs') //set express to render using EJS
app.use(express.static('public')) //set static files inside public folder
app.use(express.urlencoded({ extended: true })) //tells express to use urlencoded decode and encode URLS
app.use(express.json()) //tells express to parse JSON content


app.get('/',async (request, response)=>{ //set the route to the read request as the root / and async the response
const todoItems = await db.collection('todos').find().toArray() //variable to hols array that awaits all to dos on collection
const itemsLeft = await db.collection('todos').countDocuments({completed: false}) //variable that holds all to dos not completed
response.render('index.ejs', { items: todoItems, left: itemsLeft }) //tells the response to render index.ejs with object of items not completedm

app.get('/',async (request, response)=>{
const todoItems = await db.collection('todos').find().toArray()
const itemsLeft = await db.collection('todos').countDocuments({completed: false})
response.render('index.ejs', { items: todoItems, left: itemsLeft })
// db.collection('todos').find().toArray()
// .then(data => {
// db.collection('todos').countDocuments({completed: false})
Expand All @@ -35,59 +37,59 @@ app.get('/',async (request, response)=>{
// .catch(error => console.error(error))
})

app.post('/addTodo', (request, response) => {
db.collection('todos').insertOne({thing: request.body.todoItem, completed: false})
.then(result => {
console.log('Todo Added')
response.redirect('/')
app.post('/addTodo', (request, response) => { //specify the route /addTodo to POST
db.collection('todos').insertOne({thing: request.body.todoItem, completed: false}) //tells the database to insert one document into the todos collection with the to do item as thing and completed set to false
.then(result => { //if successful
console.log('Todo Added') //log to the console todo added
response.redirect('/') //redirect to the root
})
.catch(error => console.error(error))
.catch(error => console.error(error)) //logs any errors
})

app.put('/markComplete', (request, response) => {
db.collection('todos').updateOne({thing: request.body.itemFromJS},{
app.put('/markComplete', (request, response) => { //set the put UPDATE route as /markComplete
db.collection('todos').updateOne({thing: request.body.itemFromJS},{ //we grab collection todos and update the one we click
$set: {
completed: true
completed: true //we update the completed tag to true
}
},{
sort: {_id: -1},
upsert: false
sort: {_id: -1}, //moves item to the bottom of the list
upsert: false //prevents insertion of item if item does not already exist
})
.then(result => {
console.log('Marked Complete')
response.json('Marked Complete')
.then(result => { //when we get a successful result
console.log('Marked Complete') //log to the console marked complete
response.json('Marked Complete') //sending response to sender with string marked complete
})
.catch(error => console.error(error))
.catch(error => console.error(error)) //logs any errors

})

app.put('/markUnComplete', (request, response) => {
db.collection('todos').updateOne({thing: request.body.itemFromJS},{
app.put('/markUnComplete', (request, response) => { //we specify the route to put (UPDATE) as /markUncomplete
db.collection('todos').updateOne({thing: request.body.itemFromJS},{ //grab from collection todos and update one clicked
$set: {
completed: false
completed: false //sets the completed as false
}
},{
sort: {_id: -1},
upsert: false
sort: {_id: -1}, //moves item to the bottom of the list
upsert: false //prevents insertion of item if item does not already exist
})
.then(result => {
console.log('Marked Complete')
response.json('Marked Complete')
.then(result => { //when we get a successful result
console.log('Marked unComplete') //logs marked complete
response.json('Marked unComplete') //sending response to sender with string marked unComplete
})
.catch(error => console.error(error))
.catch(error => console.error(error)) //logs any errors

})

app.delete('/deleteItem', (request, response) => {
db.collection('todos').deleteOne({thing: request.body.itemFromJS})
.then(result => {
console.log('Todo Deleted')
response.json('Todo Deleted')
app.delete('/deleteItem', (request, response) => { //set the delete route to /deleteItem
db.collection('todos').deleteOne({thing: request.body.itemFromJS}) //we go to todos collection and delete one we clicked
.then(result => { //when we get a successful result
console.log('Todo Deleted') //we log todo Deleted
response.json('Todo Deleted') //sending response to sender with string marked Todo Deleted
})
.catch(error => console.error(error))
.catch(error => console.error(error)) //logs any errors

})

app.listen(process.env.PORT || PORT, ()=>{
console.log(`Server running on port ${PORT}`)
app.listen(process.env.PORT || PORT, ()=>{ //we tell the server to listen a specific port from variable PORT or from the .env file
console.log(`Server running on port ${PORT}`) //log the server is running on what port
})
53 changes: 27 additions & 26 deletions views/index.ejs
Original file line number Diff line number Diff line change
Expand Up @@ -4,44 +4,45 @@
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.15.3/css/all.min.css">
<title>Todo List</title>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.15.3/css/all.min.css"><!--link to font awesome style sheet-->
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<!DOCTYPE html>
<!-- <!DOCTYPE html> ///This is a typo
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<h1>Todo List: </h1>
<ul class="todoItems">
<% for(let i=0; i < items.length; i++) {%>
<li class="item">
<% if(items[i].completed === true) {%>
<span class='completed'><%= items[i].thing %></span>
<% }else{ %>
<span><%= items[i].thing %></span>
<% } %>
<span class='fa fa-trash'></span>
</li>
<% } %>
</ul>
</head> /// This is a typo -->

<body> <!--main section for content displayed-->
<h1>Todo List: </h1> <!--Main heading-->
<ul class="todoItems"> <!--unordered list with class todoItems-->
<% for(let i=0; i < items.length; i++) {%> <!--for loop using EJS-->
<li class="item"> <!--create li with class item-->
<% if(items[i].completed === true) {%> <!--EJS if statement to check if item is marked completed true-->
<span class='completed'><%= items[i].thing %></span><!--creating span with class completed and adding EJS to display task-->
<% }else{ %><!--EJS for else statement-->
<span><%= items[i].thing %></span><!--adding a span with the task-->
<% } %> <!--EJS to close else statement-->
<span class='fa fa-trash'></span><!--creating a span to display tras icon from font awesome-->
</li><!--end of li item-->
<% } %><!--closing EJS for the for loop-->
</ul><!--closing unordered list-->

<h2>Left to do: <%= left %></h2>
<h2>Left to do: <%= left %></h2><!--creates a second heading and using EJS to display number of tasks left to complete-->

<h2>Add A Todo:</h2>
<h2>Add A Todo:</h2><!--second heading-->

<form action="/addTodo" method="POST">
<input type="text" placeholder="Thing To Do" name="todoItem">
<input type="submit">
</form>
<form action="/addTodo" method="POST"><!--form tag with POST(create) method that goes to the /addtodo route-->
<input type="text" placeholder="Thing To Do" name="todoItem"><!--create input box to grab our tasks named todoItem-->
<input type="submit"><!--submit button-->
</form><!--End of form-->


<script src='js/main.js'></script>
</body>
<script src='js/main.js'></script><!--link to script with our main.js file-->
</body><!--End of main section for content displayed-->
</html>