Skip to content

Commit

Permalink
Merge pull request #37 from RbAvci/RB/Video_voting_buttons
Browse files Browse the repository at this point in the history
NW6 | Rabia Avci | Full-Stack-Project | Week-3 | Video voting buttons
  • Loading branch information
zelihapala authored May 25, 2024
2 parents 8ef940b + 2079114 commit baef03d
Show file tree
Hide file tree
Showing 6 changed files with 132 additions and 51 deletions.
39 changes: 21 additions & 18 deletions client/index.html
Original file line number Diff line number Diff line change
@@ -1,21 +1,24 @@
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<link rel="icon" type="image/svg+xml" href="/icon.svg" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Video Recommendations</title>
<link rel="preconnect" href="https://fonts.googleapis.com" />
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
<link
href="https://fonts.googleapis.com/css2?family=Roboto:ital,wght@0,100;0,300;0,400;0,500;0,700;0,900;1,100;1,300;1,400;1,500;1,700;1,900&display=swap"
rel="stylesheet"
/>
<link
rel="stylesheet"
href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css"
/>
</head>

<head>
<meta charset="UTF-8" />
<link rel="icon" type="image/svg+xml" href="/icon.svg" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Video Recommendations</title>
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link
href="https://fonts.googleapis.com/css2?family=Roboto:ital,wght@0,100;0,300;0,400;0,500;0,700;0,900;1,100;1,300;1,400;1,500;1,700;1,900&display=swap"
rel="stylesheet">
</head>

<body>
<div id="root"></div>
<script type="module" src="/src/index.jsx"></script>
</body>

</html>
<body>
<div id="root"></div>
<script type="module" src="/src/index.jsx"></script>
</body>
</html>
43 changes: 43 additions & 0 deletions client/src/RatingDisplay.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
const RatingDisplay = ({ videoId, rating, onUpdate }) => {
const handleRating = (updatedRating) => {
fetch(`/api/videos/${videoId}/rating`, {
method: "PUT",
headers: {
Accept: "application/json",
"Content-Type": "application/json",
},

body: JSON.stringify({
rating: updatedRating,
}),
})
.then((response) => {
if (!response.ok) {
throw new Error("Failed to update the video rating");
}
return response.json();
})
.then((data) => {
onUpdate(videoId, data.data.rating);
})
.catch((error) => {
console.error(error);
});
};

return (
<div>
<div>{rating}</div>
<div>
<button onClick={() => handleRating(rating + 1)}>
Thumbs-up! <i className="fa fa-thumbs-up"></i>
</button>
<button onClick={() => handleRating(rating - 1)}>
Thumbs-down! <i className="fa fa-thumbs-down"></i>
</button>
</div>
</div>
);
};

export default RatingDisplay;
36 changes: 18 additions & 18 deletions client/src/VideoRecommendations.css
Original file line number Diff line number Diff line change
@@ -1,38 +1,38 @@
:root {
--primary-color: #007bff;
--container-width: 90%;
--gap-size: 20px;
--primary-color: #007bff;
--container-width: 90%;
--gap-size: 20px;
}

.video-list-container {
padding: 20px;
margin: 0 auto;
width: var(--container-width);
padding: 20px;
margin: 0 auto;
width: var(--container-width);
}

.video-list {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
gap: var(--gap-size);
display: grid;
grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
gap: var(--gap-size);
}

.video-item {
padding: 10px;
border: 1px solid #ddd;
border-radius: 5px;
background-color: #f9f9f9;
padding: 10px;
border: 1px solid #ddd;
border-radius: 5px;
background-color: #f9f9f9;
}

.video-title {
font-size: 18px;
margin-bottom: 10px;
font-family: Arial, sans-serif;
font-size: 18px;
margin-bottom: 10px;
font-family: Arial, sans-serif;
}

.video-title a {
color: var(--primary-color);
color: var(--primary-color);
}

.video-title a:hover {
text-decoration: underline;
text-decoration: underline;
}
17 changes: 14 additions & 3 deletions client/src/VideoRecommendations.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import React, { useState, useEffect } from "react";
import "./VideoRecommendations.css";
import DeleteVideoRecommendation from "./DeleteVideoRecommendation";
import NewVideoForm from "./NewVideoForm.jsx";

import RatingDisplay from "./RatingDisplay.jsx";
const VideoList = () => {
const [videos, setVideos] = useState([]);

Expand All @@ -15,8 +15,7 @@ const VideoList = () => {
})
.then((response) => response.json())
.then((data) => {
console.log(JSON.stringify(data));
setVideos(data);
setVideos(data.sort((a, b) => a.id - b.id));
})
.catch((error) => {
console.error(error);
Expand All @@ -31,6 +30,13 @@ const VideoList = () => {
setVideos(videos.filter((video) => video.id !== videoId));
};

const handleRatingUpdate = (videoId, rating) => {
const updatedVideos = videos.map((video) =>
video.id === videoId ? { ...video, rating: rating } : video
);
setVideos(updatedVideos);
};

return (
<div className="video-list-container">
<div className="video-list">
Expand All @@ -43,6 +49,11 @@ const VideoList = () => {
videoId={videoData.id}
onDelete={handleDelete}
/>
<RatingDisplay
videoId={videoData.id}
rating={videoData.rating}
onUpdate={handleRatingUpdate}
/>
</div>
))}
</div>
Expand Down
23 changes: 12 additions & 11 deletions db/initdb.sql
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,18 @@ DROP TABLE IF EXISTS videos CASCADE;
CREATE TABLE videos (
id SERIAL PRIMARY KEY,
title VARCHAR,
src VARCHAR
src VARCHAR,
rating INTEGER

);

INSERT INTO videos (title,src) VALUES ('Never Gonna Give You Up','https://www.youtube.com/watch?v=dQw4w9WgXcQ');
INSERT INTO videos (title,src) VALUES ('The Coding Train','https://www.youtube.com/watch?v=HerCR8bw_GE');
INSERT INTO videos (title,src) VALUES ('Mac & Cheese | Basics with Babish','https://www.youtube.com/watch?v=FUeyrEN14Rk');
INSERT INTO videos (title,src) VALUES ('Videos for Cats to Watch - 8 Hour Bird Bonanza','https://www.youtube.com/watch?v=xbs7FT7dXYc');
INSERT INTO videos (title,src) VALUES ('The Complete London 2012 Opening Ceremony | London 2012 Olympic Games','https://www.youtube.com/watch?v=4As0e4de-rI');
INSERT INTO videos (title,src) VALUES ('Learn Unity - Beginner''s Game Development Course','https://www.youtube.com/watch?v=gB1F9G0JXOo');
INSERT INTO videos (title,src) VALUES ('Cracking Enigma in 2021 - Computerphile','https://www.youtube.com/watch?v=RzWB5jL5RX0');
INSERT INTO videos (title,src) VALUES ('Coding Adventure: Chess AI','https://www.youtube.com/watch?v=U4ogK0MIzqk');
INSERT INTO videos (title,src) VALUES ('Coding Adventure: Ant and Slime Simulations','https://www.youtube.com/watch?v=X-iSQQgOd1A');
INSERT INTO videos (title,src) VALUES ('Why the Tour de France is so brutal','https://www.youtube.com/watch?v=ZacOS8NBK6U');
INSERT INTO videos (title,src,rating) VALUES ('Never Gonna Give You Up','https://www.youtube.com/watch?v=dQw4w9WgXcQ', 5);
INSERT INTO videos (title,src,rating) VALUES ('The Coding Train','https://www.youtube.com/watch?v=HerCR8bw_GE', 5);
INSERT INTO videos (title,src,rating) VALUES ('Mac & Cheese | Basics with Babish','https://www.youtube.com/watch?v=FUeyrEN14Rk', 5);
INSERT INTO videos (title,src,rating) VALUES ('Videos for Cats to Watch - 8 Hour Bird Bonanza','https://www.youtube.com/watch?v=xbs7FT7dXYc', 5);
INSERT INTO videos (title,src,rating) VALUES ('The Complete London 2012 Opening Ceremony | London 2012 Olympic Games','https://www.youtube.com/watch?v=4As0e4de-rI', 5);
INSERT INTO videos (title,src,rating) VALUES ('Learn Unity - Beginner''s Game Development Course','https://www.youtube.com/watch?v=gB1F9G0JXOo', 5);
INSERT INTO videos (title,src,rating) VALUES ('Cracking Enigma in 2021 - Computerphile','https://www.youtube.com/watch?v=RzWB5jL5RX0', 5);
INSERT INTO videos (title,src,rating) VALUES ('Coding Adventure: Chess AI','https://www.youtube.com/watch?v=U4ogK0MIzqk', 5);
INSERT INTO videos (title,src,rating) VALUES ('Coding Adventure: Ant and Slime Simulations','https://www.youtube.com/watch?v=X-iSQQgOd1A', 5);
INSERT INTO videos (title,src,rating) VALUES ('Why the Tour de France is so brutal','https://www.youtube.com/watch?v=ZacOS8NBK6U', 5);
25 changes: 24 additions & 1 deletion server/api.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ router.post("/videos", async (req, res) => {
return res.status(422).json({ message: "src field is required" });
}
const result = await db.query(
`INSERT INTO videos (title,src) VALUES ('${req.body.title}','${req.body.src}') RETURNING id`
`INSERT INTO videos (title,src,rating) VALUES ('${req.body.title}','${req.body.src}', 0) RETURNING id`
);
const newVideoId = result.rows[0].id;
res.status(200).json({ success: true, data: { id: newVideoId } });
Expand All @@ -42,4 +42,27 @@ router.delete("/videos/:id", async (req, res) => {
}
});

router.put("/videos/:id/rating", async (req, res) => {
const videoId = req.params.id;
const { rating } = req.body;

try {
const result = await db.query(`SELECT * FROM videos WHERE id=${videoId}`);
let video = result.rows[0];
if (!video) {
return res.status(404).json({ error: "Video not found" });
}

await db.query(`UPDATE videos SET rating=${rating} WHERE id=${videoId}`);

res.status(200).json({
success: true,
message: "Video updated successfully",
data: { rating: rating },
});
} catch (error) {
res.status(500).json({ success: false, error: "Internal server error" });
}
});

export default router;

0 comments on commit baef03d

Please sign in to comment.