import React, {useEffect, useState} from "react"; import "../styles/course.css"; import "../styles/modal.css"; import "../styles/extendsurvey.css"; import "../styles/deletesurvey.css"; import "../styles/duplicatesurvey.css"; import "../styles/addsurvey.css"; import Modal from "./Modal"; import Toast from "./Toast"; import ViewResults from "./ViewResults"; import {RadioButton} from "primereact/radiobutton"; import Team from "../assets/pairingmodes/TEAM.png" import TeamSelf from "../assets/pairingmodes/TEAM+SELF.png" import TeamSelfManager from "../assets/pairingmodes/TEAM+SELF+MANAGER.png" import PM from "../assets/pairingmodes/PM.png" import SinglePairs from "../assets/pairingmodes/SinglePairs.png" // import SurveyForm from "./pages/SurveyForm" import { Link, NavLink } from "react-router-dom"; import { useNavigate } from "react-router-dom"; /** * @component * @param {Object} course * @param {String} page // What page the component is being used on. Either Home or History * @returns */ const Course = ({course, page}) => { const [surveys, setSurveys] = useState([]); /** * Perform a POST call to courseSurveysQueries */ function updateAllSurveys() { fetch(process.env.REACT_APP_API_URL + "courseSurveysQueries.php", { method: "POST", headers: { "Content-Type": "application/x-www-form-urlencoded", }, body: new URLSearchParams({ "course-id": course.id, }), }) .then((res) => res.json()) .then((result) => { console.log(result); const activeSurveys = result.active.map((survey_info) => ({ ...survey_info, expired: false, })); console.log(result); const expiredSurveys = result.expired.map((survey_info) => ({ ...survey_info, expired: true, })); const upcomingSurveys = result.upcoming.map((survey_info) => ({ ...survey_info, expired: false, })); console.log(result); setSurveys([...activeSurveys, ...expiredSurveys, ...upcomingSurveys]); }) .catch((err) => { console.log(err); }); } // MODAL CODE const [actionsButtonValue, setActionsButtonValue] = useState(""); const [currentSurveyEndDate, setCurrentSurveyEndDate] = useState(""); const [extendModal, setExtendModal] = useState(false); const [duplicateModal, setDuplicateModel] = useState(false); const [emptyOrWrongDeleteNameError, setemptyOrWrongDeleteNameError] = useState(false); const [deleteModal, setDeleteModal] = useState(false); const [modalIsOpen, setModalIsOpen] = useState(false); const [modalIsOpenError, setModalIsOpenError] = useState(false); const [errorsList, setErrorsList] = useState([]); const [modalIsOpenSurveyConfirm, setModalIsOpenSurveyConfirm] = useState(false); const [showUpdateModal, setShowUpdateModal] = useState(false); const [currentSurvey, setCurrentSurvey] = useState(""); const [showViewResultsModal, setViewResultsModal] = useState(false); const [viewingCurrentSurvey, setViewingCurrentSurvey] = useState(null); const [rosterFile, setRosterFile] = useState(null); const [updateRosterOption, setUpdateRosterOption] = useState("replace"); const [updateRosterError, setUpdateRosterError] = useState([]); const [showErrorModal, setShowErrorModal] = useState(false); const [showToast, setShowToast] = useState(false); const [rubricNames, setNames] = useState([]); const [rubricIDandDescriptions, setIDandDescriptions] = useState([]); const [pairingModesFull, setPairingModesFull] = useState([]); const [pairingModesNames, setPairingModesNames] = useState([]); const [RosterArray, setRosterArray] = useState([]); const [NonRosterArray, setNonRosterArray] = useState([]); //START:Error codes for modal frontend const [emptySurveyNameError, setEmptyNameError] = useState(false); const [emptyStartTimeError, setEmptyStartTimeError] = useState(false); const [emptyEndTimeError, setEmptyEndTimeError] = useState(false); const [emptyStartDateError, setEmptyStartDateError] = useState(false); const [emptyEndDateError, setEmptyEndDateError] = useState(false); const [emptyCSVFileError, setEmptyCSVFileError] = useState(false); const [startDateBoundError, setStartDateBoundError] = useState(false); const [startDateBound1Error, setStartDateBound1Error] = useState(false); const [endDateBoundError, setEndDateBoundError] = useState(false); const [endDateBound1Error, setEndDateBound1Error] = useState(false); const [StartAfterCurrentError, setStartAfterCurrentError] = useState(false); const [StartDateGreaterError, setStartDateGreaterError] = useState(false); const [StartTimeSameDayError, setStartTimeSameDayError] = useState(false); const [StartHourSameDayError, setStartHourSameDayError] = useState(false); const [StartHourAfterEndHourError, setStartHourAfterEndHourError] = useState(false); const [StartTimeHoursBeforeCurrent, setStartTimeHoursBeforeCurrent] = useState(false); const [StartTimeMinutesBeforeCurrent, setStartTimeMinutesBeforeCurrent] = useState(false); //END:Error codes for modal frontend const [surveyNameConfirm, setSurveyNameConfirm] = useState(); const [rubricNameConfirm, setRubricNameConfirm] = useState(); const [startDateConfirm, setStartDateConfirm] = useState(); const [endDateConfirm, setEndDateConfirm] = useState(); const updateRosterformData = new FormData(); /** * Perform a GET call to rubricsGet.php to fetch names and ID of the rubrics. */ const fetchRubrics = () => { fetch(process.env.REACT_APP_API_URL + "rubricsGet.php", { method: "GET", headers: { "Content-Type": "application/x-www-form-urlencoded", }, }) .then((res) => res.json()) .then((result) => { //this is an array of objects of example elements {rubricId: 1, rubricDesc: 'exampleDescription'} let rubricIDandDescriptions = result.rubrics.map((element) => element); //An array of just the rubricDesc let rubricNames = result.rubrics.map((element) => element.rubricDesc); setNames(rubricNames); setIDandDescriptions(rubricIDandDescriptions); }) .catch((err) => { console.log(err); }); }; /** * Perform a GET call to surveryTypesGet.php to fetch pairing modes for each surver, stored in pairingModesFull and pairingModesNames */ const fetchPairingModes = () => { fetch(process.env.REACT_APP_API_URL + "surveyTypesGet.php", { method: "GET", headers: { "Content-Type": "application/x-www-form-urlencoded", }, }) .then((res) => res.json()) .then((result) => { let allPairingModeArray = result.survey_types.mult.concat( result.survey_types.no_mult ); let pairingModeNames = allPairingModeArray.map( (element) => element.description ); let pairingModeFull1 = result.survey_types; setPairingModesFull(pairingModeFull1); setPairingModesNames(pairingModeNames); }) .catch((err) => { console.log(err); }); }; const openModal = () => { setModalIsOpen(true); fetchRubrics(); fetchPairingModes(); }; const closeModal = () => { setModalIsOpen(false); setEmptyNameError(false); setEmptyStartTimeError(false); setEmptyEndTimeError(false); setEmptyStartDateError(false); setEmptyEndDateError(false); setEmptyCSVFileError(false); setStartDateBoundError(false); setStartDateBound1Error(false); setEndDateBoundError(false); setEndDateBound1Error(false); setStartAfterCurrentError(false); setStartDateGreaterError(false); setStartTimeSameDayError(false); setStartHourSameDayError(false); setStartHourAfterEndHourError(false); setStartTimeHoursBeforeCurrent(false); setStartTimeMinutesBeforeCurrent(false); }; const closeModalError = () => { setModalIsOpenError(false); }; const closeModalSurveyConfirm = () => { setModalIsOpenSurveyConfirm(false); }; const handleErrorModalClose = () => { setRosterFile(null); // sets the file to null setShowErrorModal(false); // close the error modal setShowUpdateModal(true); // open the update modal again }; const getInitialStateRubric = () => { const value = "Select Rubric"; return value; }; const getInitialStatePairing = () => { const value = "TEAM"; return value; }; const [valueRubric, setValueRubric] = useState(getInitialStateRubric); const [valuePairing, setValuePairing] = useState(getInitialStatePairing); const [multiplierNumber, setMultiplierNumber] = useState("one"); const [validPairingModeForMultiplier, setMultiplier] = useState(false); const [pairingImage, setPairingImage] = useState(Team); const handleChangeRubric = (e) => { setValueRubric(e.target.value); }; const handleChangeMultiplierNumber = (e) => { setMultiplierNumber(e.target.value); }; const handleUpdateImage = (e) => { console.log(e.target.value); switch(e.target.value) { case 'TEAM': setPairingImage(Team); break; case 'TEAM + SELF': setPairingImage(TeamSelf); break; case 'TEAM + SELF + MANAGER': setPairingImage(TeamSelfManager); break; case 'Single Pairs': setPairingImage(SinglePairs); break; case 'PM': setPairingImage(PM); break; default: console.log('Unexpected pairing mode: ${pairingMode}'); break; } } const handleChangePairing = (e) => { var boolean = false; let multiplierCheckArray = pairingModesFull.mult.map( (element) => element.description ); if (multiplierCheckArray.includes(e.target.value)) { boolean = true; } handleUpdateImage(e); setValuePairing(e.target.value); setMultiplier(boolean); }; async function fetchRosterNonRoster() { let fetchHTTP = process.env.REACT_APP_API_URL + "confirmationForSurvey.php"; console.log(fetchHTTP); //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "GET", }); const result = await response.json(); return result; // Return the result directly } catch (err) { console.log("goes to error"); console.error(err); throw err; // Re-throw to be handled by the caller } } async function fetchAddSurveyToDatabaseComplete(data) { console.log(data); let fetchHTTP = process.env.REACT_APP_API_URL + "confirmationForSurvey.php"; //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "POST", body: data, }); const result = await response.json(); console.log(result); return result; // Return the result directly } catch (err) { throw err; // Re-throw to be handled by the caller } } async function confirmSurveyComplete() { let formData2 = new FormData(); formData2.append("save-survey", "1"); let any = await fetchAddSurveyToDatabaseComplete(formData2); updateAllSurveys(); closeModalSurveyConfirm(); return; } async function getAddSurveyResponse(formData) { console.log("this is before the addsurveyResponse function fetch call"); let fetchHTTP = process.env.REACT_APP_API_URL + "addSurveyToCourse.php?course=" + course.id; //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "POST", body: formData, }); const result = await response.json(); return result; // Return the result directly } catch (err) { console.error(err); throw err; // Re-throw to be handled by the caller } } async function duplicateSurveyBackend(formdata) { let fetchHTTP = process.env.REACT_APP_API_URL + "duplicateExistingSurvey.php?survey=" + currentSurvey.id; //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "POST", body: formdata, }); const result = await response.text(); console.log(currentSurvey); console.log(result); return result; // Return the result directly } catch (err) { console.error(err); throw err; // Re-throw to be handled by the caller } } async function verifyDuplicateSurvey() { setEmptyNameError(false); setEmptyStartTimeError(false); setEmptyEndTimeError(false); setEmptyStartDateError(false); setEmptyEndDateError(false); setEmptyCSVFileError(false); setStartDateBoundError(false); setStartDateBound1Error(false); setEndDateBoundError(false); setEndDateBound1Error(false); setStartAfterCurrentError(false); setStartDateGreaterError(false); setStartTimeSameDayError(false); setStartHourSameDayError(false); setStartHourAfterEndHourError(false); setStartTimeHoursBeforeCurrent(false); setStartTimeMinutesBeforeCurrent(false); var surveyName = document.getElementById("survey-name").value; var startTime = document.getElementById("start-time").value; var endTime = document.getElementById("end-time").value; var startDate = document.getElementById("start-date").value; var endDate = document.getElementById("end-date").value; var rubric = document.getElementById("rubric-type").value; var dictNameToInputValue = { "Survey name": surveyName, "Start time": startTime, "End time": endTime, "Start date": startDate, "End date": endDate, }; for (let k in dictNameToInputValue) { if (dictNameToInputValue[k] === "") { if (k === "Survey name") { setEmptyNameError(true); return; } if (k === "Start time") { setEmptyStartTimeError(true); return; } if (k === "End time") { setEmptyEndTimeError(true); return; } if (k === "Start date") { setEmptyStartDateError(true); return; } if (k === "End date") { setEmptyEndDateError(true); return; } } } //date and time keyboard typing bound checks. // let minDateObject = new Date("2023-08-31T00:00:00"); //first day of class // let maxDateObject = new Date("2023-12-31T00:00:00"); //last day of class let startDateObject = new Date(startDate + "T00:00:00"); //inputted start date. let endDateObject = new Date(endDate + "T00:00:00"); //inputted end date. // if (startDateObject < minDateObject) { // setStartDateBoundError(true); // return; // } // if (startDateObject > maxDateObject) { // setStartDateBound1Error(true); // return; // } // if (endDateObject < minDateObject) { // setEndDateBoundError(true); // return; // } // if (endDateObject > maxDateObject) { // setStartDateBound1Error(true); // return; // } //END:date and time keyboard typing bound checks. //special startdate case. Startdate cannot be before the current day. let timestamp = new Date(Date.now()); timestamp.setHours(0, 0, 0, 0); //set hours/minutes/seconds/etc to be 0. Just want to deal with the calendar date if (startDateObject < timestamp) { setStartAfterCurrentError(true); return; } //END:special startdate case. Startdate cannot be before the current day. //Start date cannot be greater than End date. if (startDateObject > endDateObject) { setStartDateGreaterError(true); return; } //END:Start date cannot be greater than End date. //If on the same day, start time must be before end time if (startDate === endDate) { if (startTime === endTime) { setStartTimeSameDayError(true); return; } let startHour = parseInt(startTime.split(":")[0]); let endHour = parseInt(endTime.split(":")[0]); if (startHour === endHour) { setStartHourSameDayError(true); return; } if (startHour > endHour) { setStartHourAfterEndHourError(true); return; } } //Start time must be after current time if start date is the current day. if ( startDateObject.getDate(startDateObject) === timestamp.getDate(timestamp) ) { let timestampWithHour = new Date(Date.now()); let currentHour = timestampWithHour.getHours(timestampWithHour); let currentMinutes = timestampWithHour.getMinutes(timestampWithHour); let startHourNew = parseInt(startTime.split(":")[0]); let startMinutes = parseInt(startTime.split(":")[1]); if (startHourNew < currentHour) { setStartTimeHoursBeforeCurrent(true); return; } if (startHourNew === currentHour) { if (startMinutes < currentMinutes) { setStartTimeMinutesBeforeCurrent(true); return; } } //End:Start time must be after current time } //Now it's time to send data to the backend let formData3 = new FormData(); let rubricId; let pairingId; let multiplier; for (const element of rubricIDandDescriptions) { if (element.rubricDesc === rubric) { rubricId = element.rubricId; } } formData3.append("survey-id", currentSurvey.id); formData3.append("survey-name", surveyName); formData3.append("rubric-id", rubricId); formData3.append("start-date", startDate); formData3.append("start-time", startTime); formData3.append("end-date", endDate); formData3.append("end-time", endTime); //form data is set. Call the post request let awaitedResponse = await duplicateSurveyBackend(formData3); updateAllSurveys(); closeModalDuplicate(); } async function verifySurvey() { setEmptyNameError(false); setEmptyStartTimeError(false); setEmptyEndTimeError(false); setEmptyStartDateError(false); setEmptyEndDateError(false); setEmptyCSVFileError(false); setStartDateBoundError(false); setStartDateBound1Error(false); setEndDateBoundError(false); setEndDateBound1Error(false); setStartAfterCurrentError(false); setStartDateGreaterError(false); setStartTimeSameDayError(false); setStartHourSameDayError(false); setStartHourAfterEndHourError(false); setStartTimeHoursBeforeCurrent(false); setStartTimeMinutesBeforeCurrent(false); var surveyName = document.getElementById("survey-name").value; var startTime = document.getElementById("start-time").value; var endTime = document.getElementById("end-time").value; var startDate = document.getElementById("start-date").value; var endDate = document.getElementById("end-date").value; var csvFile = document.getElementById("csv-file").value; var rubric = document.getElementById("rubric-type").value; var dictNameToInputValue = { "Survey name": surveyName, "Start time": startTime, "End time": endTime, "Start date": startDate, "End date": endDate, "Csv file": csvFile, }; for (let k in dictNameToInputValue) { if (dictNameToInputValue[k] === "") { if (k === "Survey name") { setEmptyNameError(true); return; } if (k === "Start time") { setEmptyStartTimeError(true); return; } if (k === "End time") { setEmptyEndTimeError(true); return; } if (k === "Start date") { setEmptyStartDateError(true); return; } if (k === "End date") { setEmptyEndDateError(true); return; } if (k === "Csv file") { setEmptyCSVFileError(true); return; } } } //date and time keyboard typing bound checks. // let minDateObject = new Date("2023-08-31T00:00:00"); //first day of class // let maxDateObject = new Date("2023-12-31T00:00:00"); //last day of class let startDateObject = new Date(startDate + "T00:00:00"); //inputted start date. let endDateObject = new Date(endDate + "T00:00:00"); //inputted end date. // if (startDateObject < minDateObject) { // setStartDateBoundError(true); // return; // } // if (startDateObject > maxDateObject) { // setStartDateBound1Error(true); // return; // } // if (endDateObject < minDateObject) { // setEndDateBoundError(true); // return; // } // if (endDateObject > maxDateObject) { // setStartDateBound1Error(true); // return; // } //END:date and time keyboard typing bound checks. //special startdate case. Startdate cannot be before the current day. let timestamp = new Date(Date.now()); timestamp.setHours(0, 0, 0, 0); //set hours/minutes/seconds/etc to be 0. Just want to deal with the calendar date if (startDateObject < timestamp) { setStartAfterCurrentError(true); return; } //END:special startdate case. Startdate cannot be before the current day. //Start date cannot be greater than End date. if (startDateObject > endDateObject) { setStartDateGreaterError(true); return; } //END:Start date cannot be greater than End date. //If on the same day, start time must be before end time if (startDate === endDate) { if (startTime === endTime) { setStartTimeSameDayError(true); return; } let startHour = parseInt(startTime.split(":")[0]); let endHour = parseInt(endTime.split(":")[0]); if (startHour === endHour) { setStartHourSameDayError(true); return; } if (startHour > endHour) { setStartHourAfterEndHourError(true); return; } } //Start time must be after current time if start date is the current day. if ( startDateObject.getDate(startDateObject) === timestamp.getDate(timestamp) ) { let timestampWithHour = new Date(Date.now()); let currentHour = timestampWithHour.getHours(timestampWithHour); let currentMinutes = timestampWithHour.getMinutes(timestampWithHour); let startHourNew = parseInt(startTime.split(":")[0]); let startMinutes = parseInt(startTime.split(":")[1]); if (startHourNew < currentHour) { setStartTimeHoursBeforeCurrent(true); return; } if (startHourNew === currentHour) { if (startMinutes < currentMinutes) { setStartTimeMinutesBeforeCurrent(true); return; } } //End:Start time must be after current time } //Now it's time to send data to the backend let formData = new FormData(); let rubricId; let pairingId; let multiplier; for (const element of rubricIDandDescriptions) { if (element.rubricDesc === rubric) { rubricId = element.rubricId; } } for (const element in pairingModesFull.no_mult) { if ( pairingModesFull.no_mult[element].description === document.getElementById("pairing-mode").value ) { pairingId = pairingModesFull.no_mult[element].id; console.log(pairingId); multiplier = 1; } } for (const element in pairingModesFull.mult) { if ( pairingModesFull.mult[element].description === document.getElementById("pairing-mode").value ) { pairingId = pairingModesFull.mult[element].id; multiplier = document.getElementById("multiplier-type").value; console.log("This is the multipler underneath"); console.log(multiplier); } } let file = document.getElementById("csv-file").files[0]; formData.append("survey-name", surveyName); formData.append("course-id", course.id); formData.append("rubric-id", rubricId); formData.append("pairing-mode", pairingId); formData.append("start-date", startDate); formData.append("start-time", startTime); formData.append("end-date", endDate); formData.append("end-time", endTime); formData.append("pm-mult", multiplier); formData.append("pairing-file", file); //form data is set. Call the post request let awaitedResponse = await getAddSurveyResponse(formData); //let errorsObject = errorOrSuccessResponse.errors; let errorsObject = awaitedResponse.errors; let dataObject = awaitedResponse.data; if (errorsObject.length === 0) { //succesful survey. let rosterDataAll = await fetchRosterNonRoster(); let rosterData = rosterDataAll.data; if (rosterData) { let rostersArrayHere = rosterData["roster-students"]; let nonRosterArrayHere = rosterData["non-roster-students"]; setRosterArray(rostersArrayHere); setNonRosterArray(nonRosterArrayHere); setSurveyNameConfirm(surveyName); setRubricNameConfirm(rubric); setStartDateConfirm(startDate + " at " + startTime); setEndDateConfirm(endDate + " at " + endTime); closeModal(); setModalIsOpenSurveyConfirm(true); return; } return; } if (dataObject.length === 0) { let errorKeys = Object.keys(errorsObject); let pairingFileStrings = []; let anyOtherStrings = []; let i = 0; while (i < errorKeys.length) { if (errorKeys[i] === "pairing-file") { pairingFileStrings = errorsObject["pairing-file"].split("
"); } else { let error = errorKeys[i]; anyOtherStrings.push(errorsObject[error]); } i++; } const allErrorStrings = pairingFileStrings.concat(anyOtherStrings); setErrorsList(allErrorStrings); closeModal(); setModalIsOpenError(true); return; } return; } let Navigate = useNavigate(); const handleActionButtonChange = (e, survey) => { setActionsButtonValue(e.target.value); if (e.target.value === "Duplicate") { fetchRubrics(); setCurrentSurvey(survey); setDuplicateModel(true); } if (e.target.value === "Delete") { setCurrentSurvey(survey); setDeleteModal(true); } if (e.target.value === "Extend") { setCurrentSurvey(survey); setExtendModal(true); } if (e.target.value == "View Results") { handleViewResultsModalChange(survey); } if (e.target.value == "Preview Survey") { Navigate("/SurveyPreview", {state:{survey_name: survey.name, rubric_id: survey.rubric_id, course: course.code}}); console.log(survey.name); console.log(survey.rubric_id); console.log(course.code); } setActionsButtonValue(""); }; function formatRosterError(input) { // Split the string into an array on the "Line" pattern, then filter out empty strings const lines = input .split(/(Line \d+)/) .filter((line) => line.trim() !== ""); // Combine adjacent elements so that each "Line #" and its message are in the same element const combinedLines = []; for (let i = 0; i < lines.length; i += 2) { combinedLines.push(lines[i] + (lines[i + 1] || "")); } return combinedLines } const handleUpdateRosterSubmit = (e) => { e.preventDefault(); updateRosterformData.append("roster-file", rosterFile); updateRosterformData.append("course-id", course.id); updateRosterformData.append("update-type", updateRosterOption); fetch(process.env.REACT_APP_API_URL + "rosterUpdate.php", { method: "POST", body: updateRosterformData, }) .then((res) => res.text()) .then((result) => { if (typeof result === "string" && result !== "") { try { const parsedResult = JSON.parse(result); console.log("Parsed as JSON object: ", parsedResult); if ( parsedResult.hasOwnProperty("error") && parsedResult["error"] !== "" ) { const updatedError = formatRosterError( parsedResult["error"] ); setUpdateRosterError(updatedError); setShowUpdateModal(false); // close the update modal setShowErrorModal(true); // show the error modal } } catch (e) { console.log("Failed to parse JSON: ", e); } } else { // no error // Roster is valid to update, so we can close the pop-up modal setShowUpdateModal(false); // show toast on success setShowToast(true); } }) .catch((err) => { console.log(err); }); }; //MODAL CODE useEffect(() => { fetch(process.env.REACT_APP_API_URL + "courseSurveysQueries.php", { method: "POST", headers: { "Content-Type": "application/x-www-form-urlencoded", }, body: new URLSearchParams({ "course-id": course.id, }), }) .then((res) => res.json()) .then((result) => { const activeSurveys = result.active.map((survey_info) => ({ ...survey_info, expired: false, })); const expiredSurveys = result.expired.map((survey_info) => ({ ...survey_info, expired: true, })); const upcomingSurveys = result.upcoming.map((survey_info) => ({ ...survey_info, expired: false, })); setSurveys([...activeSurveys, ...expiredSurveys, ...upcomingSurveys]); }) .catch((err) => { console.log(err); }); }, []); function closeModalDuplicate() { setDuplicateModel(false); setEmptyNameError(false); setEmptyStartTimeError(false); setEmptyEndTimeError(false); setEmptyStartDateError(false); setEmptyEndDateError(false); setEmptyCSVFileError(false); setStartDateBoundError(false); setStartDateBound1Error(false); setEndDateBoundError(false); setEndDateBound1Error(false); setStartAfterCurrentError(false); setStartDateGreaterError(false); setStartTimeSameDayError(false); setStartHourSameDayError(false); setStartHourAfterEndHourError(false); setStartTimeHoursBeforeCurrent(false); setStartTimeMinutesBeforeCurrent(false); } async function verifyDeleteBackendGet(id) { let fetchHTTP = process.env.REACT_APP_API_URL + "deleteSurvey.php?survey=" + id; //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "GET", }); const result = await response.json(); console.log(result); return result; // Return the result directly } catch (err) { throw err; // Re-throw to be handled by the caller } } async function verifyDeleteBackend(formdata, id) { let fetchHTTP = process.env.REACT_APP_API_URL + "deleteSurvey.php?survey=" + id; //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "POST", body: formdata, }); const result = await response.json(); console.log(result); return result; // Return the result directly } catch (err) { throw err; // Re-throw to be handled by the caller } } async function extendSurveyBackendGet(id) { let fetchHTTP = process.env.REACT_APP_API_URL + "extendSurvey.php?survey=" + id; //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "GET", }); const result = await response.text(); console.log(result); return result; // Return the result directly } catch (err) { throw err; // Re-throw to be handled by the caller } } async function extendSurveyBackendPost(id, formdata) { let fetchHTTP = process.env.REACT_APP_API_URL + "extendSurvey.php?survey=" + id; //let response = await fetch(fetchHTTP,{method: "POST", body: formData}); try { const response = await fetch(fetchHTTP, { method: "POST", body: formdata, }); const result = await response.json(); console.log(result); return result; // Return the result directly } catch (err) { throw err; // Re-throw to be handled by the caller } } const [extendEmptyFieldsError, setExtendEmptyFieldsError] = useState(false); const [extendStartDateGreater, setExtendStartDateGreater] = useState(false); const [extendStartHourIsGreater, setExtendStartHourIsGreater] = useState(false); const [extendMustBeAfterCurrentTime, setExtendMustBeAfterCurrentTime] = useState(false); const [extendNewEndMustComeAfterOldEnd, setExtendNewEndMustComeAfterOldEnd] = useState(false); async function verifyExtendModal() { setExtendEmptyFieldsError(false); setExtendStartDateGreater(false); setExtendStartHourIsGreater(false); setExtendMustBeAfterCurrentTime(false); setExtendNewEndMustComeAfterOldEnd(false); let newEndDate = document.getElementById("new-endDate").value; let newEndTime = document.getElementById("new-endTime").value; //empty fields check if (newEndDate === "") { setExtendEmptyFieldsError(true); return; } if (newEndTime === "") { setExtendEmptyFieldsError(true); return; } let startDate = currentSurvey.sort_start_date.split(' ')[0] let currentTime = currentSurvey.sort_start_date.split(' ')[1] currentTime = currentTime.split(':'); currentTime = currentTime[0] + ':' + currentTime[1]; let startDateTimeObject = new Date(startDate + "T00:00:00"); //inputted start date. let endDateTimeObject = new Date(newEndDate + "T00:00:00"); //inputted end date. let timestamp = new Date(Date.now()); timestamp.setHours(0, 0, 0, 0); //set hours/minutes/seconds/etc to be 0. Just want to deal with the calendar date //if the selected end date occurs in the past error if (endDateTimeObject < timestamp) { setExtendMustBeAfterCurrentTime(true); return; } //new end date must come after old end date let oldEndDate = currentSurvey.sort_expiration_date.split(' ')[0] let oldEndTimeHours = currentSurvey.sort_expiration_date.split(' ')[1] oldEndTimeHours = oldEndTimeHours.split(':'); oldEndTimeHours = oldEndTimeHours[0] + ':' + oldEndTimeHours[1]; let oldEndDateTimeObject = new Date(oldEndDate + "T00:00:00") //conditional to check if old end calendar date isnt ahead of the new one if (oldEndDateTimeObject > endDateTimeObject) { setExtendNewEndMustComeAfterOldEnd(true); return; } //conditional to check if new end time hours is greater than old if (oldEndDateTimeObject.getDate(oldEndDateTimeObject) === endDateTimeObject.getDate(endDateTimeObject)) { //same date new hours should be ahead of old if (oldEndDateTimeObject.getMonth(oldEndDateTimeObject) === endDateTimeObject.getMonth(endDateTimeObject)) { if (parseInt(oldEndTimeHours.split(':')[0]) >= parseInt(newEndTime.split(':')[0])) { console.log('goes through here') setExtendNewEndMustComeAfterOldEnd(true); return; } } } //selected end date is in the current day. Hours and minutes must be after current h/m if (endDateTimeObject.getDate(endDateTimeObject) === timestamp.getDate(timestamp)) { if (endDateTimeObject.getMonth(endDateTimeObject) === timestamp.getMonth(timestamp)) { console.log('goes through here') let timestampWithHour = new Date(Date.now()); console.log(timestampWithHour) let currentHour = timestampWithHour.getHours(timestampWithHour); console.log(currentHour) let currentMinutes = timestampWithHour.getMinutes(timestampWithHour); console.log(currentMinutes) let endHours = parseInt(newEndTime.split(":")[0]); console.log(endHours) let endMinutes = parseInt(newEndTime.split(":")[1]); console.log(endMinutes) if (endHours < currentHour) { setExtendMustBeAfterCurrentTime(true); return; } if (endHours === currentHour) { if (endMinutes <= currentMinutes) { setExtendMustBeAfterCurrentTime(true); return; } } } } //start date comes after end date error if (startDateTimeObject > endDateTimeObject) { setExtendStartDateGreater(true); return } // same date. End date hours must be ahead if (startDateTimeObject === endDateTimeObject) { console.log('goes through hour check'); console.log(currentTime); console.log(newEndTime); //hour check. Start date hour must be less than end date hour if (parseInt(currentTime.split(':')[0]) >= parseInt(newEndTime.split(':')[0])) { setExtendStartHourIsGreater(true); return; } } let surveyId = currentSurvey.id; let formData5 = new FormData(); formData5.append('survey-id', surveyId); formData5.append('end-date', newEndDate); formData5.append('end-time', newEndTime); formData5.append('rubric-id', currentSurvey.rubric_id) formData5.append('start-date', currentSurvey.sort_start_date.split(' ')[0]); formData5.append("start-time", currentTime); let pre = await extendSurveyBackendGet(surveyId); let post = await extendSurveyBackendPost(surveyId, formData5); if ( post.errors["end-date"] || post.errors["end-time"] || post.errors["start-date"] || post.errors["start-time"] ) { //there are errors let errorList = []; if (post.errors["end-date"]) { errorList.push(post.errors["end-date"]); } if (post.errors["start-date"]) { errorList.push(post.errors["start-date"]); } if (post.errors["end-time"]) { errorList.push(post.errors["end-time"]); } if (post.errors["start-time"]) { errorList.push(post.errors["start-time"]); } extendModalClose(); setErrorsList(errorList); setModalIsOpenError(true); return; } updateAllSurveys(); extendModalClose(); } async function verifyDelete() { setemptyOrWrongDeleteNameError(false); let inputtedText = document.getElementById("delete-name").value; if (inputtedText !== currentSurvey.name) { setemptyOrWrongDeleteNameError(true); } else { let form = new FormData(); form.append("agreement", 1); let surveyId = currentSurvey.id; let pre = await verifyDeleteBackendGet(surveyId); let final = await verifyDeleteBackend(form, surveyId); updateAllSurveys(); deleteModalClose(); } } function extendModalClose() { setExtendModal(false); setExtendEmptyFieldsError(false); setExtendStartDateGreater(false); setExtendStartHourIsGreater(false); setExtendMustBeAfterCurrentTime(false); setExtendNewEndMustComeAfterOldEnd(false); } function deleteModalClose() { setemptyOrWrongDeleteNameError(false); setDeleteModal(false); } const handleUpdateModalChange = () => { setShowUpdateModal((prev) => !prev); }; const handleViewResultsModalChange = (survey) => { setViewResultsModal((prev) => !prev); setViewingCurrentSurvey(survey); }; return (

Extend Survey: {currentSurvey.name}

Current Deadline

{currentSurvey.end_date}

New Deadline

{extendEmptyFieldsError ?