Skip to content
This repository was archived by the owner on Oct 1, 2022. It is now read-only.
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
66 changes: 53 additions & 13 deletions controllers/bookings.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
const Booking = require("../models/Booking");
const validateBookingInput = require("../validation/booking");
const { bookingConfirmationEmail } = require("../utils/notification");
const Booking = require('../models/Booking');
const validateBookingInput = require('../validation/booking');
const {
bookingConfirmationEmail,
adminSendEmailToClassVolunteers,
} = require('../utils/notification');
const Class = require('../models/Class');
const dayjs = require('dayjs');
exports.getBookings = async (req, res) => {
try {
const bookings = await Booking.find();
Expand All @@ -12,7 +17,7 @@ exports.getBookings = async (req, res) => {
} catch (err) {
return res.status(500).json({
success: false,
error: "Server Error",
error: 'Server Error',
});
}
};
Expand All @@ -24,7 +29,7 @@ exports.getClassBookings = async (req, res) => {
if (!booking) {
return res.status(404).json({
success: false,
error: "No booking found",
error: 'No booking found',
});
}
return res.status(200).json({
Expand All @@ -35,7 +40,7 @@ exports.getClassBookings = async (req, res) => {
} catch (err) {
return res.status(400).json({
success: false,
error: "Could not get class bookings",
error: 'Could not get class bookings',
});
}
};
Expand All @@ -55,12 +60,12 @@ exports.createBooking = async (req, res) => {
return res.status(400).json({
success: false,
message:
"Email already exists, You have already booked for this class, thanks!",
'Email already exists, You have already booked for this class, thanks!',
});
} else if (err) {
return res.status(500).json({
success: false,
error: "Server Error",
error: 'Server Error',
});
} else {
const allBooking = await Booking.find({ classId: req.body.classId });
Expand All @@ -73,6 +78,10 @@ exports.createBooking = async (req, res) => {
}

const newBooking = await Booking.create(req.body);
const classInfo = await Class.findById(req.body.classId);
newBooking.classDate = dayjs(classInfo.date).format('DD/MM/YYYY');
newBooking.classStartTime = classInfo.startTime;
newBooking.classEndTime = classInfo.endTime;
await bookingConfirmationEmail(newBooking);
return res.status(201).json({
success: true,
Expand All @@ -84,7 +93,7 @@ exports.createBooking = async (req, res) => {
} catch (err) {
return res.status(500).json({
success: false,
error: "Server Error",
error: 'Server Error',
});
}
};
Expand All @@ -98,7 +107,7 @@ exports.deleteBooking = async (req, res) => {
if (!booking) {
return res.status(404).json({
success: false,
error: "No booking found",
error: 'No booking found',
});
}

Expand All @@ -111,7 +120,7 @@ exports.deleteBooking = async (req, res) => {
} catch (err) {
return res.status(500).json({
success: false,
error: "Server Error, could not delete booking",
error: 'Server Error, could not delete booking',
});
}
};
Expand All @@ -129,7 +138,7 @@ exports.updateBooking = async (req, res) => {
if (!booking) {
return res.status(400).json({
success: false,
error: "booking not found!",
error: 'booking not found!',
});
}
return res.status(200).json({
Expand All @@ -139,7 +148,38 @@ exports.updateBooking = async (req, res) => {
} catch (err) {
return res.status(400).json({
success: false,
error: "Could not update booking",
error: 'Could not update booking',
});
}
};

exports.sendEmailToAllVolunteers = async (req, res) => {
try {
const emailData = req.body;
if (emailData.subject === '' || emailData.emailText === '') {
return res.status(400).json("'Subject or email can not be empty.'");
}
const classId = emailData.classId;
const classBookings = await Booking.find({ classId });
if (classBookings && !classBookings.length > 0) {
return res.status(400).json({
success: false,
message:
'Sorry, there are no volunteers signed up for this class, thanks!',
});
}
const emails = [];
classBookings.forEach((booking) => emails.push(booking.email));
emailData.emails = emails;
await adminSendEmailToClassVolunteers(emailData);
return res.status(200).json({
success: true,
message: 'An email notification is sent to all volunteers, thanks!',
});
} catch (err) {
return res.status(400).json({
success: false,
error: 'Could not Send Emails',
});
}
};
80 changes: 80 additions & 0 deletions frontend/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
"react": "^16.14.0",
"react-dom": "^16.14.0",
"react-hook-form": "^6.10.1",
"react-quill": "^1.3.5",
"react-redux": "^7.2.2",
"react-router-dom": "^5.2.0",
"react-scripts": "^3.4.4",
Expand Down
24 changes: 23 additions & 1 deletion frontend/src/components/ClassCard/ClassCard.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { MonthNames } from "../../utils/MonthNames";
import { Link } from "react-router-dom";
import NewBookingForm from "../NewBookingForm/NewBookingForm.jsx";
import ClassVolunteersList from "../ClassVolunteersList/ClassVolunteersList.jsx";
import EmailToAll from "./EmailToAll.jsx";
import axios from "axios";
import Alert from "../Alert/Alarm.jsx";
import Loading from "../Loading/Loading.jsx";
Expand All @@ -17,11 +18,16 @@ const ClassCard = ({ user, city, component, id, Class, WeekNumber }) => {
const [alertStatus, setAlertStatus] = useState(false);
const [alertType, setAlertType] = useState("");
const [alertMessage, setAlertMessage] = useState("message");
const [sendEmail, setSendEmail] = useState(false);

const closeConfirmationAlert = () => {
setCancelStatus(false);
};

const emailClose = () => {
setSendEmail(false);
};

const showAlert = (type, message) => {
setAlertStatus(true);
setAlertType(type);
Expand Down Expand Up @@ -180,6 +186,19 @@ const ClassCard = ({ user, city, component, id, Class, WeekNumber }) => {
<div>
{user === users[0].id && (
<React.Fragment>
{component === "attendingvolunteers" && (
<button
onClick={() => {
setSendEmail(true);
}}
className="classcard-email-bottom"
>
<span className="classcard-text-ctl">
Send Email
</span>
<i className="far fa-paper-plane classcard-icon-ctl"></i>
</button>
)}
<button
onClick={() => {
setCancelStatus(true);
Expand Down Expand Up @@ -234,6 +253,9 @@ const ClassCard = ({ user, city, component, id, Class, WeekNumber }) => {
</div>
)}
</div>
{sendEmail && (
<EmailToAll Class={Class} emailClose={emailClose} />
)}
{!["upcomingclass", "coursecalendar", "overview"].includes(
component
) && <hr className="classcard-separator"></hr>}
Expand Down Expand Up @@ -263,4 +285,4 @@ const ClassCard = ({ user, city, component, id, Class, WeekNumber }) => {
);
};

export default ClassCard;
export default ClassCard;
Loading