diff --git a/src/components/DemographicInformationInput.tsx b/src/components/DemographicInformationInput.tsx index a042cf19..ce647f4c 100644 --- a/src/components/DemographicInformationInput.tsx +++ b/src/components/DemographicInformationInput.tsx @@ -42,7 +42,7 @@ export default function DemographicInformationInput({user, mutateUser}: Props) { setIsLoading(true); axios - .patch("/api/users/update", { + .patch<{user: User}>("/api/users/update", { demographicInformation: { country, phone: `+${countryCodes.findOne("countryCode" as any, country!).countryCallingCode}${phone}`, @@ -54,7 +54,7 @@ export default function DemographicInformationInput({user, mutateUser}: Props) { }, agentInformation: user.type === "agent" ? {companyName, commercialRegistration} : undefined, }) - .then((response) => mutateUser((response.data as {user: User}).user)) + .then((response) => mutateUser(response.data.user)) .catch(() => { toast.error("Something went wrong, please try again later!", {toastId: "user-update-error"}); }) @@ -89,7 +89,15 @@ export default function DemographicInformationInput({user, mutateUser}: Props) { - setPhone(e)} value={phone} placeholder="Enter phone number" required /> + setPhone(e)} + value={phone} + placeholder="Enter phone number" + required + /> {user.type === "student" && ( , - achieved: user.levels.reading >= user.desiredLevels.reading, + achieved: user.levels?.reading || 0 >= user.desiredLevels?.reading || 9, }, { module: "listening", icon: () => , - achieved: user.levels.listening >= user.desiredLevels.listening, + achieved: user.levels?.listening || 0 >= user.desiredLevels?.listening || 9, }, { module: "writing", icon: () => , - achieved: user.levels.writing >= user.desiredLevels.writing, + achieved: user.levels?.writing || 0 >= user.desiredLevels?.writing || 9, }, { module: "speaking", icon: () => , - achieved: user.levels.speaking >= user.desiredLevels.speaking, + achieved: user.levels?.speaking || 0 >= user.desiredLevels?.speaking || 9, }, { module: "level", icon: () => , - achieved: user.levels.level >= user.desiredLevels.level, + achieved: user.levels?.level || 0 >= user.desiredLevels?.level || 9, }, ]; diff --git a/src/hooks/useUser.tsx b/src/hooks/useUser.tsx index 47b9a36e..f0ef326d 100644 --- a/src/hooks/useUser.tsx +++ b/src/hooks/useUser.tsx @@ -16,9 +16,9 @@ export default function useUser({redirectTo = "", redirectIfFound = false} = {}) if ( // If redirectIfFound is also set, redirect if the user was found - (redirectIfFound && user && user.isVerified) || + (redirectIfFound && user) || // If redirectTo is set, redirect if the user was not found. - (redirectTo && !redirectIfFound && (!user || (user && !user.isVerified))) + (redirectTo && !redirectIfFound && !user) ) { Router.push(redirectTo); } diff --git a/src/pages/api/users/update.ts b/src/pages/api/users/update.ts index 4f7ba431..aab28fa9 100644 --- a/src/pages/api/users/update.ts +++ b/src/pages/api/users/update.ts @@ -1,17 +1,17 @@ // Next.js API route support: https://nextjs.org/docs/api-routes/introduction -import type { NextApiRequest, NextApiResponse } from "next"; -import { app, storage } from "@/firebase"; -import { withIronSessionApiRoute } from "iron-session/next"; -import { sessionOptions } from "@/lib/session"; -import { Group, User } from "@/interfaces/user"; -import { getDownloadURL, getStorage, ref, uploadBytes } from "firebase/storage"; -import { getAuth, signInWithEmailAndPassword, updateEmail, updatePassword } from "firebase/auth"; -import { errorMessages } from "@/constants/errors"; +import type {NextApiRequest, NextApiResponse} from "next"; +import {app, storage} from "@/firebase"; +import {withIronSessionApiRoute} from "iron-session/next"; +import {sessionOptions} from "@/lib/session"; +import {Group, User} from "@/interfaces/user"; +import {getDownloadURL, getStorage, ref, uploadBytes} from "firebase/storage"; +import {getAuth, signInWithEmailAndPassword, updateEmail, updatePassword} from "firebase/auth"; +import {errorMessages} from "@/constants/errors"; import moment from "moment"; import ShortUniqueId from "short-unique-id"; -import { Payment } from "@/interfaces/paypal"; -import { toFixedNumber } from "@/utils/number"; -import { propagateExpiryDateChanges, propagateStatusChange } from "@/utils/propagate.user.changes"; +import {Payment} from "@/interfaces/paypal"; +import {toFixedNumber} from "@/utils/number"; +import {propagateExpiryDateChanges, propagateStatusChange} from "@/utils/propagate.user.changes"; import client from "@/lib/mongodb"; const db = client.db(process.env.MONGODB_DB); @@ -41,7 +41,7 @@ const managePaymentRecords = async (user: User, userId: string | undefined): Pro date: new Date().toISOString(), }; - const corporatePayments = await db.collection("payments").find({ corporate: userId }).toArray(); + const corporatePayments = await db.collection("payments").find({corporate: userId}).toArray(); if (corporatePayments.length === 0) { await addPaymentRecord(data); return true; @@ -71,20 +71,17 @@ const managePaymentRecords = async (user: User, userId: string | undefined): Pro async function handler(req: NextApiRequest, res: NextApiResponse) { if (!req.session.user) { - res.status(401).json({ ok: false }); + res.status(401).json({ok: false}); return; } const queryId = req.query.id as string; - let user = await db.collection("users").findOne({ id: queryId ? (queryId as string) : req.session.user.id }); - const updatedUser = req.body as User & { password?: string; newPassword?: string }; + let user = await db.collection("users").findOne({id: queryId ? (queryId as string) : req.session.user.id}); + const updatedUser = req.body as User & {password?: string; newPassword?: string}; if (!!queryId) { - await db.collection("users").updateOne( - { id: queryId }, - { $set: updatedUser } - ); + await db.collection("users").updateOne({id: queryId}, {$set: updatedUser}); await managePaymentRecords(updatedUser, updatedUser.id); if (updatedUser.status || updatedUser.type === "corporate") { @@ -93,7 +90,7 @@ async function handler(req: NextApiRequest, res: NextApiResponse) { propagateExpiryDateChanges(queryId, user?.subscriptionExpirationDate, updatedUser.subscriptionExpirationDate || null); } - res.status(200).json({ ok: true }); + res.status(200).json({ok: true}); return; } @@ -113,17 +110,17 @@ async function handler(req: NextApiRequest, res: NextApiResponse) { const credential = await signInWithEmailAndPassword(auth, req.session.user.email, updatedUser.password); await updatePassword(credential.user, updatedUser.newPassword); } catch { - res.status(400).json({ error: "E001", message: errorMessages.E001 }); + res.status(400).json({error: "E001", message: errorMessages.E001}); return; } } if (updatedUser.email !== req.session.user.email && updatedUser.password) { try { - const usersWithSameEmail = await db.collection("users").find({ email: updatedUser.email.toLowerCase() }).toArray(); + const usersWithSameEmail = await db.collection("users").find({email: updatedUser.email.toLowerCase()}).toArray(); if (usersWithSameEmail.length > 0) { - res.status(400).json({ error: "E003", message: errorMessages.E003 }); + res.status(400).json({error: "E003", message: errorMessages.E003}); return; } @@ -131,22 +128,24 @@ async function handler(req: NextApiRequest, res: NextApiResponse) { await updateEmail(credential.user, updatedUser.email); if (req.session.user.type === "student") { - const corporateAdmins = (await db.collection("users").find({ type: "corporate" }).toArray()).map((x) => x.id); + const corporateAdmins = (await db.collection("users").find({type: "corporate"}).toArray()).map((x) => x.id); - const groups = await db.collection("groups").find({ - participants: req.session.user!.id, - admin: { $in: corporateAdmins } - }).toArray(); + const groups = await db + .collection("groups") + .find({ + participants: req.session.user!.id, + admin: {$in: corporateAdmins}, + }) + .toArray(); groups.forEach(async (group) => { - await db.collection("groups").updateOne( - { id: group.id }, - { $set: { participants: group.participants.filter((x) => x !== req.session.user!.id) } } - ); + await db + .collection("groups") + .updateOne({id: group.id}, {$set: {participants: group.participants.filter((x) => x !== req.session.user!.id)}}); }); } } catch { - res.status(400).json({ error: "E002", message: errorMessages.E002 }); + res.status(400).json({error: "E002", message: errorMessages.E002}); return; } } @@ -159,22 +158,18 @@ async function handler(req: NextApiRequest, res: NextApiResponse) { delete updatedUser.password; delete updatedUser.newPassword; - await db.collection("users").updateOne( - { id: queryId }, - { $set: updatedUser } - ); - - user = await db.collection("users").findOne({ id: req.session.user.id }); + await db.collection("users").updateOne({id: queryId}, {$set: updatedUser}); if (!queryId) { - req.session.user = user ? user : null; + req.session.user = updatedUser ? {...updatedUser, id: req.session.user.id} : null; await req.session.save(); } - if (user) { - await managePaymentRecords(user, queryId); + if ({...updatedUser, id: req.session.user!.id}) { + await managePaymentRecords({...updatedUser, id: req.session.user!.id}, queryId); } - res.status(200).json({ user }); + + res.status(200).json({user: {...updatedUser, id: req.session.user!.id}}); } export const config = { diff --git a/src/pages/exam.tsx b/src/pages/exam.tsx index 779ababd..84cc0317 100644 --- a/src/pages/exam.tsx +++ b/src/pages/exam.tsx @@ -10,7 +10,7 @@ import {User} from "@/interfaces/user"; export const getServerSideProps = withIronSessionSsr(({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/exercises.tsx b/src/pages/exercises.tsx index 9a24775c..983fdfeb 100644 --- a/src/pages/exercises.tsx +++ b/src/pages/exercises.tsx @@ -10,7 +10,7 @@ import {User} from "@/interfaces/user"; export const getServerSideProps = withIronSessionSsr(({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/generation.tsx b/src/pages/generation.tsx index 8505434d..4d23a995 100644 --- a/src/pages/generation.tsx +++ b/src/pages/generation.tsx @@ -27,7 +27,7 @@ import {User} from "@/interfaces/user"; export const getServerSideProps = withIronSessionSsr(({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/groups.tsx b/src/pages/groups.tsx index 70b38f4b..12886c91 100644 --- a/src/pages/groups.tsx +++ b/src/pages/groups.tsx @@ -43,7 +43,7 @@ import {getUsers} from "@/utils/users.be"; export const getServerSideProps = withIronSessionSsr(async ({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/index.tsx b/src/pages/index.tsx index 773e829f..153bb52c 100644 --- a/src/pages/index.tsx +++ b/src/pages/index.tsx @@ -46,7 +46,7 @@ export const getServerSideProps = withIronSessionSsr(async ({req, res}) => { envVariables[x] = process.env[x]!; }); - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", @@ -78,12 +78,8 @@ export default function Home({linkedCorporate}: Props) { useEffect(() => { if (user) { - setShowDemographicInput( - !user.demographicInformation || - !user.demographicInformation.country || - !user.demographicInformation.gender || - !user.demographicInformation.phone, - ); + console.log(user.demographicInformation); + setShowDemographicInput(!user.demographicInformation || !user.demographicInformation.country || !user.demographicInformation.phone); setShowDiagnostics(user.isFirstLogin && user.type === "student"); } }, [user]); diff --git a/src/pages/list/users.tsx b/src/pages/list/users.tsx index 3a07e363..26069756 100644 --- a/src/pages/list/users.tsx +++ b/src/pages/list/users.tsx @@ -21,7 +21,7 @@ export const getServerSideProps = withIronSessionSsr(({req, res}) => { envVariables[x] = process.env[x]!; }); - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/login.tsx b/src/pages/login.tsx index 4d4b6292..fe7d37ad 100644 --- a/src/pages/login.tsx +++ b/src/pages/login.tsx @@ -28,7 +28,7 @@ export const getServerSideProps = withIronSessionSsr(({req, res}) => { envVariables[x] = process.env[x]!; }); - if (user && user.isVerified) { + if (user) { return { redirect: { destination: "/", @@ -56,7 +56,7 @@ export default function Login() { }); useEffect(() => { - if (user && user.isVerified) router.push("/"); + if (user) router.push("/"); }, [router, user]); const forgotPassword = () => { @@ -173,7 +173,7 @@ export default function Login() { )} - {user && !user.isVerified && } + {/* {user && !user.isVerified && } */} diff --git a/src/pages/payment-record.tsx b/src/pages/payment-record.tsx index 3eae246a..8d99512c 100644 --- a/src/pages/payment-record.tsx +++ b/src/pages/payment-record.tsx @@ -1,28 +1,20 @@ /* eslint-disable @next/next/no-img-element */ import Head from "next/head"; -import { withIronSessionSsr } from "iron-session/next"; -import { sessionOptions } from "@/lib/session"; +import {withIronSessionSsr} from "iron-session/next"; +import {sessionOptions} from "@/lib/session"; import useUser from "@/hooks/useUser"; -import { toast, ToastContainer } from "react-toastify"; +import {toast, ToastContainer} from "react-toastify"; import Layout from "@/components/High/Layout"; -import { shouldRedirectHome } from "@/utils/navigation.disabled"; +import {shouldRedirectHome} from "@/utils/navigation.disabled"; import usePayments from "@/hooks/usePayments"; import usePaypalPayments from "@/hooks/usePaypalPayments"; -import { Payment, PaypalPayment } from "@/interfaces/paypal"; -import { - CellContext, - createColumnHelper, - flexRender, - getCoreRowModel, - HeaderGroup, - Table, - useReactTable, -} from "@tanstack/react-table"; -import { CURRENCIES } from "@/resources/paypal"; -import { BsTrash } from "react-icons/bs"; +import {Payment, PaypalPayment} from "@/interfaces/paypal"; +import {CellContext, createColumnHelper, flexRender, getCoreRowModel, HeaderGroup, Table, useReactTable} from "@tanstack/react-table"; +import {CURRENCIES} from "@/resources/paypal"; +import {BsTrash} from "react-icons/bs"; import axios from "axios"; -import { useEffect, useState, useMemo } from "react"; -import { AgentUser, CorporateUser, User } from "@/interfaces/user"; +import {useEffect, useState, useMemo} from "react"; +import {AgentUser, CorporateUser, User} from "@/interfaces/user"; import UserCard from "@/components/UserCard"; import Modal from "@/components/Modal"; import clsx from "clsx"; @@ -34,1499 +26,1228 @@ import Input from "@/components/Low/Input"; import ReactDatePicker from "react-datepicker"; import moment from "moment"; import PaymentAssetManager from "@/components/PaymentAssetManager"; -import { toFixedNumber } from "@/utils/number"; -import { CSVLink } from "react-csv"; -import { Tab } from "@headlessui/react"; -import { useListSearch } from "@/hooks/useListSearch"; -import { checkAccess, getTypesOfUser } from "@/utils/permissions"; +import {toFixedNumber} from "@/utils/number"; +import {CSVLink} from "react-csv"; +import {Tab} from "@headlessui/react"; +import {useListSearch} from "@/hooks/useListSearch"; +import {checkAccess, getTypesOfUser} from "@/utils/permissions"; -export const getServerSideProps = withIronSessionSsr(({ req, res }) => { - const user = req.session.user; +export const getServerSideProps = withIronSessionSsr(({req, res}) => { + const user = req.session.user; - if (!user || !user.isVerified) { - return { - redirect: { - destination: "/login", - permanent: false, - }, - }; - } + if (!user) { + return { + redirect: { + destination: "/login", + permanent: false, + }, + }; + } - if ( - shouldRedirectHome(user) || - checkAccess( - user, - getTypesOfUser([ - "admin", - "developer", - "agent", - "corporate", - "mastercorporate", - ]) - ) - ) { - return { - redirect: { - destination: "/", - permanent: false, - }, - }; - } + if (shouldRedirectHome(user) || checkAccess(user, getTypesOfUser(["admin", "developer", "agent", "corporate", "mastercorporate"]))) { + return { + redirect: { + destination: "/", + permanent: false, + }, + }; + } - return { - props: { user: req.session.user }, - }; + return { + props: {user: req.session.user}, + }; }, sessionOptions); const columnHelper = createColumnHelper(); const paypalColumnHelper = createColumnHelper(); -const PaymentCreator = ({ - onClose, - reload, - showComission = false, -}: { - onClose: () => void; - reload: () => void; - showComission: boolean; -}) => { - const [corporate, setCorporate] = useState(); - const [date, setDate] = useState(new Date()); +const PaymentCreator = ({onClose, reload, showComission = false}: {onClose: () => void; reload: () => void; showComission: boolean}) => { + const [corporate, setCorporate] = useState(); + const [date, setDate] = useState(new Date()); - const { users } = useUsers(); + const {users} = useUsers(); - const price = corporate?.corporateInformation?.payment?.value || 0; - const commission = corporate?.corporateInformation?.payment?.commission || 0; - const currency = corporate?.corporateInformation?.payment?.currency || "EUR"; + const price = corporate?.corporateInformation?.payment?.value || 0; + const commission = corporate?.corporateInformation?.payment?.commission || 0; + const currency = corporate?.corporateInformation?.payment?.currency || "EUR"; - const referralAgent = useMemo(() => { - if (corporate?.corporateInformation?.referralAgent) { - return users.find( - (u) => u.id === corporate.corporateInformation.referralAgent - ); - } + const referralAgent = useMemo(() => { + if (corporate?.corporateInformation?.referralAgent) { + return users.find((u) => u.id === corporate.corporateInformation.referralAgent); + } - return undefined; - }, [corporate?.corporateInformation?.referralAgent, users]); + return undefined; + }, [corporate?.corporateInformation?.referralAgent, users]); - const submit = () => { - axios - .post(`/api/payments`, { - corporate: corporate?.id, - agent: referralAgent?.id, - agentCommission: commission, - agentValue: toFixedNumber((commission! / 100) * price!, 2), - currency, - value: price, - isPaid: false, - date: date.toISOString(), - }) - .then(() => { - toast.success("New payment has been created successfully!"); - reload(); - onClose(); - }) - .catch(() => { - toast.error("Something went wrong, please try again later!"); - }); - }; + const submit = () => { + axios + .post(`/api/payments`, { + corporate: corporate?.id, + agent: referralAgent?.id, + agentCommission: commission, + agentValue: toFixedNumber((commission! / 100) * price!, 2), + currency, + value: price, + isPaid: false, + date: date.toISOString(), + }) + .then(() => { + toast.success("New payment has been created successfully!"); + reload(); + onClose(); + }) + .catch(() => { + toast.error("Something went wrong, please try again later!"); + }); + }; - return ( -
-

New Payment

-
-
- - u.type === "corporate") as CorporateUser[]).map((user) => ({ + value: user.id, + meta: user, + label: `${user.corporateInformation?.companyInformation?.name || user.name} - ${user.email}`, + }))} + defaultValue={{value: "undefined", label: "Select an account"}} + onChange={(value) => setCorporate((value as any)?.meta ?? undefined)} + menuPortalTarget={document?.body} + styles={{ + menuPortal: (base) => ({...base, zIndex: 9999}), + control: (styles) => ({ + ...styles, + paddingLeft: "4px", + border: "none", + outline: "none", + ":focus": { + outline: "none", + }, + }), + option: (styles, state) => ({ + ...styles, + backgroundColor: state.isFocused ? "#D5D9F0" : state.isSelected ? "#7872BF" : "white", + color: state.isFocused ? "black" : styles.color, + }), + }} + /> +
-
- -
- {}} - type="number" - value={price} - defaultValue={0} - className="col-span-3" - disabled - /> - {}} - type="number" - defaultValue={0} - value={commission} - disabled - /> -
-
- - c.currency === currency)?.label - }`} - onChange={() => null} - type="text" - defaultValue={0} - disabled - /> -
-
- )} +
+ +
+ {}} type="number" value={price} defaultValue={0} className="col-span-3" disabled /> + {}} type="number" defaultValue={0} value={commission} disabled /> +
+
+ + c.currency === currency)?.label}`} + onChange={() => null} + type="text" + defaultValue={0} + disabled + /> +
+
+ )} -
-
- - setDate(date ?? new Date())} - /> -
+
+
+ + setDate(date ?? new Date())} + /> +
-
- - null} - type="text" - defaultValue={"No country manager"} - disabled - /> -
-
-
- - -
-
-
- ); +
+ + null} + type="text" + defaultValue={"No country manager"} + disabled + /> +
+
+
+ + +
+ + + ); }; const IS_PAID_OPTIONS = [ - { - value: null, - label: "All", - }, - { - value: false, - label: "Unpaid", - }, - { - value: true, - label: "Paid", - }, + { + value: null, + label: "All", + }, + { + value: false, + label: "Unpaid", + }, + { + value: true, + label: "Paid", + }, ]; const IS_FILE_SUBMITTED_OPTIONS = [ - { - value: null, - label: "All", - }, - { - value: false, - label: "Submitted", - }, - { - value: true, - label: "Not Submitted", - }, + { + value: null, + label: "All", + }, + { + value: false, + label: "Submitted", + }, + { + value: true, + label: "Not Submitted", + }, ]; -const CSV_PAYMENTS_WHITELISTED_KEYS = [ - "corporateId", - "corporate", - "date", - "amount", - "agent", - "agentCommission", - "agentValue", - "isPaid", -]; +const CSV_PAYMENTS_WHITELISTED_KEYS = ["corporateId", "corporate", "date", "amount", "agent", "agentCommission", "agentValue", "isPaid"]; -const CSV_PAYPAL_WHITELISTED_KEYS = [ - "orderId", - "status", - "name", - "email", - "value", - "createdAt", - "subscriptionExpirationDate", -]; +const CSV_PAYPAL_WHITELISTED_KEYS = ["orderId", "status", "name", "email", "value", "createdAt", "subscriptionExpirationDate"]; interface SimpleCSVColumn { - key: string; - label: string; - index: number; + key: string; + label: string; + index: number; } interface PaypalPaymentWithUserData extends PaypalPayment { - name: string; - email: string; + name: string; + email: string; } const paypalFilterRows = [["email"], ["name"], ["orderId"], ["value"]]; export default function PaymentRecord() { - const [selectedCorporateUser, setSelectedCorporateUser] = useState(); - const [selectedAgentUser, setSelectedAgentUser] = useState(); - const [isCreatingPayment, setIsCreatingPayment] = useState(false); - const [filters, setFilters] = useState< - { filter: (p: Payment) => boolean; id: string }[] - >([]); - const [displayPayments, setDisplayPayments] = useState([]); + const [selectedCorporateUser, setSelectedCorporateUser] = useState(); + const [selectedAgentUser, setSelectedAgentUser] = useState(); + const [isCreatingPayment, setIsCreatingPayment] = useState(false); + const [filters, setFilters] = useState<{filter: (p: Payment) => boolean; id: string}[]>([]); + const [displayPayments, setDisplayPayments] = useState([]); - const [corporate, setCorporate] = useState(); - const [agent, setAgent] = useState(); + const [corporate, setCorporate] = useState(); + const [agent, setAgent] = useState(); - const { user } = useUser({ redirectTo: "/login" }); - const { users, reload: reloadUsers } = useUsers(); - const { payments: originalPayments, reload: reloadPayment } = usePayments(); - const { payments: paypalPayments, reload: reloadPaypalPayment } = - usePaypalPayments(); - const [startDate, setStartDate] = useState( - moment("01/01/2023").toDate() - ); - const [endDate, setEndDate] = useState( - moment().endOf("day").toDate() - ); + const {user} = useUser({redirectTo: "/login"}); + const {users, reload: reloadUsers} = useUsers(); + const {payments: originalPayments, reload: reloadPayment} = usePayments(); + const {payments: paypalPayments, reload: reloadPaypalPayment} = usePaypalPayments(); + const [startDate, setStartDate] = useState(moment("01/01/2023").toDate()); + const [endDate, setEndDate] = useState(moment().endOf("day").toDate()); - const [startDatePaymob, setStartDatePaymob] = useState( - moment("01/01/2023").toDate() - ); - const [endDatePaymob, setEndDatePaymob] = useState( - moment().endOf("day").toDate() - ); + const [startDatePaymob, setStartDatePaymob] = useState(moment("01/01/2023").toDate()); + const [endDatePaymob, setEndDatePaymob] = useState(moment().endOf("day").toDate()); - const [paid, setPaid] = useState(IS_PAID_OPTIONS[0].value); - const [commissionTransfer, setCommissionTransfer] = useState( - IS_FILE_SUBMITTED_OPTIONS[0].value - ); - const [corporateTransfer, setCorporateTransfer] = useState( - IS_FILE_SUBMITTED_OPTIONS[0].value - ); - const reload = () => { - reloadUsers(); - reloadPayment(); - }; + const [paid, setPaid] = useState(IS_PAID_OPTIONS[0].value); + const [commissionTransfer, setCommissionTransfer] = useState(IS_FILE_SUBMITTED_OPTIONS[0].value); + const [corporateTransfer, setCorporateTransfer] = useState(IS_FILE_SUBMITTED_OPTIONS[0].value); + const reload = () => { + reloadUsers(); + reloadPayment(); + }; - const payments = useMemo(() => { - return originalPayments.filter((p: Payment) => { - const date = moment(p.date); - return date.isAfter(startDate) && date.isBefore(endDate); - }); - }, [originalPayments, startDate, endDate]); + const payments = useMemo(() => { + return originalPayments.filter((p: Payment) => { + const date = moment(p.date); + return date.isAfter(startDate) && date.isBefore(endDate); + }); + }, [originalPayments, startDate, endDate]); - const [selectedIndex, setSelectedIndex] = useState(0); + const [selectedIndex, setSelectedIndex] = useState(0); - useEffect(() => { - setDisplayPayments( - filters - .map((f) => f.filter) - .reduce((d, f) => d.filter(f), payments) - .sort((a, b) => moment(b.date).diff(moment(a.date))) - ); - }, [payments, filters]); + useEffect(() => { + setDisplayPayments( + filters + .map((f) => f.filter) + .reduce((d, f) => d.filter(f), payments) + .sort((a, b) => moment(b.date).diff(moment(a.date))), + ); + }, [payments, filters]); - useEffect(() => { - if (user && user.type === "agent") { - setAgent(user); - } - }, [user]); + useEffect(() => { + if (user && user.type === "agent") { + setAgent(user); + } + }, [user]); - useEffect(() => { - setFilters((prev) => [ - ...prev.filter((x) => x.id !== "agent-filter"), - ...(!agent - ? [] - : [ - { - id: "agent-filter", - filter: (p: Payment) => p.agent === agent.id, - }, - ]), - ]); - }, [agent]); + useEffect(() => { + setFilters((prev) => [ + ...prev.filter((x) => x.id !== "agent-filter"), + ...(!agent + ? [] + : [ + { + id: "agent-filter", + filter: (p: Payment) => p.agent === agent.id, + }, + ]), + ]); + }, [agent]); - useEffect(() => { - setFilters((prev) => [ - ...prev.filter((x) => x.id !== "corporate-filter"), - ...(!corporate - ? [] - : [ - { - id: "corporate-filter", - filter: (p: Payment) => p.corporate === corporate.id, - }, - ]), - ]); - }, [corporate]); + useEffect(() => { + setFilters((prev) => [ + ...prev.filter((x) => x.id !== "corporate-filter"), + ...(!corporate + ? [] + : [ + { + id: "corporate-filter", + filter: (p: Payment) => p.corporate === corporate.id, + }, + ]), + ]); + }, [corporate]); - useEffect(() => { - setFilters((prev) => [ - ...prev.filter((x) => x.id !== "paid"), - ...(typeof paid !== "boolean" - ? [] - : [{ id: "paid", filter: (p: Payment) => p.isPaid === paid }]), - ]); - }, [paid]); + useEffect(() => { + setFilters((prev) => [ + ...prev.filter((x) => x.id !== "paid"), + ...(typeof paid !== "boolean" ? [] : [{id: "paid", filter: (p: Payment) => p.isPaid === paid}]), + ]); + }, [paid]); - useEffect(() => { - setFilters((prev) => [ - ...prev.filter((x) => x.id !== "commissionTransfer"), - ...(typeof commissionTransfer !== "boolean" - ? [] - : [ - { - id: "commissionTransfer", - filter: (p: Payment) => - !p.commissionTransfer === commissionTransfer, - }, - ]), - ]); - }, [commissionTransfer]); + useEffect(() => { + setFilters((prev) => [ + ...prev.filter((x) => x.id !== "commissionTransfer"), + ...(typeof commissionTransfer !== "boolean" + ? [] + : [ + { + id: "commissionTransfer", + filter: (p: Payment) => !p.commissionTransfer === commissionTransfer, + }, + ]), + ]); + }, [commissionTransfer]); - useEffect(() => { - setFilters((prev) => [ - ...prev.filter((x) => x.id !== "corporateTransfer"), - ...(typeof corporateTransfer !== "boolean" - ? [] - : [ - { - id: "corporateTransfer", - filter: (p: Payment) => - !p.corporateTransfer === corporateTransfer, - }, - ]), - ]); - }, [corporateTransfer]); + useEffect(() => { + setFilters((prev) => [ + ...prev.filter((x) => x.id !== "corporateTransfer"), + ...(typeof corporateTransfer !== "boolean" + ? [] + : [ + { + id: "corporateTransfer", + filter: (p: Payment) => !p.corporateTransfer === corporateTransfer, + }, + ]), + ]); + }, [corporateTransfer]); - useEffect(() => { - if (user && user.type === "corporate") return setCorporate(user); - if (user && user.type === "agent") return setAgent(user); - }, [user]); + useEffect(() => { + if (user && user.type === "corporate") return setCorporate(user); + if (user && user.type === "agent") return setAgent(user); + }, [user]); - const updatePayment = (payment: Payment, key: string, value: any) => { - axios - .patch(`api/payments/${payment.id}`, { ...payment, [key]: value }) - .then(() => toast.success("Updated the payment")) - .finally(reload); - }; + const updatePayment = (payment: Payment, key: string, value: any) => { + axios + .patch(`api/payments/${payment.id}`, {...payment, [key]: value}) + .then(() => toast.success("Updated the payment")) + .finally(reload); + }; - const deletePayment = (id: string) => { - if (!confirm(`Are you sure you want to delete this payment?`)) return; + const deletePayment = (id: string) => { + if (!confirm(`Are you sure you want to delete this payment?`)) return; - axios - .delete(`/api/payments/${id}`) - .then(() => toast.success(`Deleted the "${id}" payment`)) - .catch((reason) => { - if (reason.response.status === 404) { - toast.error("Exam not found!"); - return; - } + axios + .delete(`/api/payments/${id}`) + .then(() => toast.success(`Deleted the "${id}" payment`)) + .catch((reason) => { + if (reason.response.status === 404) { + toast.error("Exam not found!"); + return; + } - if (reason.response.status === 403) { - toast.error( - "You do not have permission to delete an approved payment record!" - ); - return; - } + if (reason.response.status === 403) { + toast.error("You do not have permission to delete an approved payment record!"); + return; + } - toast.error("Something went wrong, please try again later."); - }) - .finally(reload); - }; + toast.error("Something went wrong, please try again later."); + }) + .finally(reload); + }; - const getFileAssetsColumns = () => { - if (user) { - const containerClassName = - "flex gap-2 text-mti-purple-light hover:text-mti-purple-dark ease-in-out duration-300 cursor-pointer"; - switch (user.type) { - case "corporate": - return [ - columnHelper.accessor("corporateTransfer", { - header: "Corporate transfer", - id: "corporateTransfer", - cell: (info) => ( -
- -
- ), - }), - ]; - case "agent": - return [ - columnHelper.accessor("commissionTransfer", { - header: "Commission transfer", - id: "commissionTransfer", - cell: (info) => ( -
- -
- ), - }), - ]; - case "admin": - return [ - columnHelper.accessor("corporateTransfer", { - header: "Corporate transfer", - id: "corporateTransfer", - cell: (info) => ( -
- -
- ), - }), - columnHelper.accessor("commissionTransfer", { - header: "Commission transfer", - id: "commissionTransfer", - cell: (info) => ( -
- -
- ), - }), - ]; - case "developer": - return [ - columnHelper.accessor("corporateTransfer", { - header: "Corporate transfer", - id: "corporateTransfer", - cell: (info) => ( -
- -
- ), - }), - columnHelper.accessor("commissionTransfer", { - header: "Commission transfer", - id: "commissionTransfer", - cell: (info) => ( -
- -
- ), - }), - ]; - default: - return []; - } - } + const getFileAssetsColumns = () => { + if (user) { + const containerClassName = "flex gap-2 text-mti-purple-light hover:text-mti-purple-dark ease-in-out duration-300 cursor-pointer"; + switch (user.type) { + case "corporate": + return [ + columnHelper.accessor("corporateTransfer", { + header: "Corporate transfer", + id: "corporateTransfer", + cell: (info) => ( +
+ +
+ ), + }), + ]; + case "agent": + return [ + columnHelper.accessor("commissionTransfer", { + header: "Commission transfer", + id: "commissionTransfer", + cell: (info) => ( +
+ +
+ ), + }), + ]; + case "admin": + return [ + columnHelper.accessor("corporateTransfer", { + header: "Corporate transfer", + id: "corporateTransfer", + cell: (info) => ( +
+ +
+ ), + }), + columnHelper.accessor("commissionTransfer", { + header: "Commission transfer", + id: "commissionTransfer", + cell: (info) => ( +
+ +
+ ), + }), + ]; + case "developer": + return [ + columnHelper.accessor("corporateTransfer", { + header: "Corporate transfer", + id: "corporateTransfer", + cell: (info) => ( +
+ +
+ ), + }), + columnHelper.accessor("commissionTransfer", { + header: "Commission transfer", + id: "commissionTransfer", + cell: (info) => ( +
+ +
+ ), + }), + ]; + default: + return []; + } + } - return []; - }; + return []; + }; - const columHelperValue = (key: string, info: any) => { - switch (key) { - case "agentCommission": { - const value = info.getValue(); - return { value: `${value}%` }; - } - case "agent": { - const user = users.find( - (x) => x.id === info.row.original.agent - ) as AgentUser; - return { - value: user?.name, - user, - }; - } - case "agentValue": - case "amount": { - const value = info.getValue(); - const numberValue = toFixedNumber(value, 2); - return { value: numberValue }; - } - case "date": { - const value = info.getValue(); - return { value: moment(value).format("DD/MM/YYYY") }; - } - case "corporate": { - const specificValue = info.row.original.corporate; - const user = users.find((x) => x.id === specificValue) as CorporateUser; - return { - user, - value: - user?.corporateInformation.companyInformation.name || user?.name, - }; - } - case "currency": { - return { - value: info.row.original.currency, - }; - } - case "isPaid": - case "corporateId": - default: { - const value = info.getValue(); - return { value }; - } - } - }; + const columHelperValue = (key: string, info: any) => { + switch (key) { + case "agentCommission": { + const value = info.getValue(); + return {value: `${value}%`}; + } + case "agent": { + const user = users.find((x) => x.id === info.row.original.agent) as AgentUser; + return { + value: user?.name, + user, + }; + } + case "agentValue": + case "amount": { + const value = info.getValue(); + const numberValue = toFixedNumber(value, 2); + return {value: numberValue}; + } + case "date": { + const value = info.getValue(); + return {value: moment(value).format("DD/MM/YYYY")}; + } + case "corporate": { + const specificValue = info.row.original.corporate; + const user = users.find((x) => x.id === specificValue) as CorporateUser; + return { + user, + value: user?.corporateInformation.companyInformation.name || user?.name, + }; + } + case "currency": { + return { + value: info.row.original.currency, + }; + } + case "isPaid": + case "corporateId": + default: { + const value = info.getValue(); + return {value}; + } + } + }; - const hiddenToCorporateColumns = () => { - if (user && user.type !== "corporate") - return [ - columnHelper.accessor("agent", { - header: "Country Manager", - id: "agent", - cell: (info) => { - const { user, value } = columHelperValue(info.column.id, info); - return ( -
setSelectedAgentUser(user)} - > - {value} -
- ); - }, - }), - columnHelper.accessor("agentCommission", { - header: "Commission", - id: "agentCommission", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return <>{value}; - }, - }), - columnHelper.accessor("agentValue", { - header: "Commission Value", - id: "agentValue", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - const finalValue = `${value} ${info.row.original.currency}`; - return {finalValue}; - }, - }), - ]; - return []; - }; + const hiddenToCorporateColumns = () => { + if (user && user.type !== "corporate") + return [ + columnHelper.accessor("agent", { + header: "Country Manager", + id: "agent", + cell: (info) => { + const {user, value} = columHelperValue(info.column.id, info); + return ( +
setSelectedAgentUser(user)}> + {value} +
+ ); + }, + }), + columnHelper.accessor("agentCommission", { + header: "Commission", + id: "agentCommission", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return <>{value}; + }, + }), + columnHelper.accessor("agentValue", { + header: "Commission Value", + id: "agentValue", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + const finalValue = `${value} ${info.row.original.currency}`; + return {finalValue}; + }, + }), + ]; + return []; + }; - const defaultColumns = [ - columnHelper.accessor("corporate", { - header: "Corporate ID", - id: "corporateId", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return value; - }, - }), - columnHelper.accessor("corporate", { - header: "Corporate", - id: "corporate", - cell: (info) => { - const { user, value } = columHelperValue(info.column.id, info); - return ( -
setSelectedCorporateUser(user)} - > - {value} -
- ); - }, - }), - columnHelper.accessor("date", { - header: "Date", - id: "date", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return {value}; - }, - }), - columnHelper.accessor("value", { - header: "Amount", - id: "amount", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - const currency = CURRENCIES.find( - (x) => x.currency === info.row.original.currency - )?.label; - const finalValue = `${value} ${currency}`; - return {finalValue}; - }, - }), - ...hiddenToCorporateColumns(), - columnHelper.accessor("isPaid", { - header: "Paid", - id: "isPaid", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); + const defaultColumns = [ + columnHelper.accessor("corporate", { + header: "Corporate ID", + id: "corporateId", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return value; + }, + }), + columnHelper.accessor("corporate", { + header: "Corporate", + id: "corporate", + cell: (info) => { + const {user, value} = columHelperValue(info.column.id, info); + return ( +
setSelectedCorporateUser(user)}> + {value} +
+ ); + }, + }), + columnHelper.accessor("date", { + header: "Date", + id: "date", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return {value}; + }, + }), + columnHelper.accessor("value", { + header: "Amount", + id: "amount", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + const currency = CURRENCIES.find((x) => x.currency === info.row.original.currency)?.label; + const finalValue = `${value} ${currency}`; + return {finalValue}; + }, + }), + ...hiddenToCorporateColumns(), + columnHelper.accessor("isPaid", { + header: "Paid", + id: "isPaid", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); - return ( - { - if (user?.type === agent || user?.type === "corporate" || value) - return null; - if ( - !info.row.original.commissionTransfer || - !info.row.original.corporateTransfer - ) - return alert( - "All files need to be uploaded to consider it paid!" - ); - if ( - !confirm(`Are you sure you want to consider this payment paid?`) - ) - return null; + return ( + { + if (user?.type === agent || user?.type === "corporate" || value) return null; + if (!info.row.original.commissionTransfer || !info.row.original.corporateTransfer) + return alert("All files need to be uploaded to consider it paid!"); + if (!confirm(`Are you sure you want to consider this payment paid?`)) return null; - return updatePayment(info.row.original, "isPaid", e); - }} - > - - - ); - }, - }), - ...getFileAssetsColumns(), - { - header: "", - id: "actions", - cell: ({ row }: { row: { original: Payment } }) => { - return ( -
- {user?.type !== "agent" && ( -
deletePayment(row.original.id)} - > - -
- )} -
- ); - }, - }, - ]; + return updatePayment(info.row.original, "isPaid", e); + }}> + +
+ ); + }, + }), + ...getFileAssetsColumns(), + { + header: "", + id: "actions", + cell: ({row}: {row: {original: Payment}}) => { + return ( +
+ {user?.type !== "agent" && ( +
deletePayment(row.original.id)}> + +
+ )} +
+ ); + }, + }, + ]; - const table = useReactTable({ - data: displayPayments, - columns: defaultColumns, - getCoreRowModel: getCoreRowModel(), - }); + const table = useReactTable({ + data: displayPayments, + columns: defaultColumns, + getCoreRowModel: getCoreRowModel(), + }); - const updatedPaypalPayments = useMemo( - () => - paypalPayments - .filter((p) => { - const date = moment(p.createdAt); - return date.isAfter(startDatePaymob) && date.isBefore(endDatePaymob); - }) - .map((p) => { - const user = users.find((x) => x.id === p.userId) as User; - return { ...p, name: user?.name, email: user?.email }; - }), - [paypalPayments, users, startDatePaymob, endDatePaymob] - ); + const updatedPaypalPayments = useMemo( + () => + paypalPayments + .filter((p) => { + const date = moment(p.createdAt); + return date.isAfter(startDatePaymob) && date.isBefore(endDatePaymob); + }) + .map((p) => { + const user = users.find((x) => x.id === p.userId) as User; + return {...p, name: user?.name, email: user?.email}; + }), + [paypalPayments, users, startDatePaymob, endDatePaymob], + ); - const paypalColumns = [ - paypalColumnHelper.accessor("orderId", { - header: "Order ID", - id: "orderId", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return {value}; - }, - }), - paypalColumnHelper.accessor("status", { - header: "Status", - id: "status", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return {value}; - }, - }), - paypalColumnHelper.accessor("name", { - header: "User Name", - id: "name", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return {value}; - }, - }), - paypalColumnHelper.accessor("email", { - header: "Email", - id: "email", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return {value}; - }, - }), - paypalColumnHelper.accessor("value", { - header: "Amount", - id: "value", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - const finalValue = `${value} ${info.row.original.currency}`; - return {finalValue}; - }, - }), - paypalColumnHelper.accessor("createdAt", { - header: "Date", - id: "createdAt", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return {moment(value).format("DD/MM/YYYY")}; - }, - }), - paypalColumnHelper.accessor("subscriptionExpirationDate", { - header: "Expiration Date", - id: "subscriptionExpirationDate", - cell: (info) => { - const { value } = columHelperValue(info.column.id, info); - return {moment(value).format("DD/MM/YYYY")}; - }, - }), - ]; + const paypalColumns = [ + paypalColumnHelper.accessor("orderId", { + header: "Order ID", + id: "orderId", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return {value}; + }, + }), + paypalColumnHelper.accessor("status", { + header: "Status", + id: "status", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return {value}; + }, + }), + paypalColumnHelper.accessor("name", { + header: "User Name", + id: "name", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return {value}; + }, + }), + paypalColumnHelper.accessor("email", { + header: "Email", + id: "email", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return {value}; + }, + }), + paypalColumnHelper.accessor("value", { + header: "Amount", + id: "value", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + const finalValue = `${value} ${info.row.original.currency}`; + return {finalValue}; + }, + }), + paypalColumnHelper.accessor("createdAt", { + header: "Date", + id: "createdAt", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return {moment(value).format("DD/MM/YYYY")}; + }, + }), + paypalColumnHelper.accessor("subscriptionExpirationDate", { + header: "Expiration Date", + id: "subscriptionExpirationDate", + cell: (info) => { + const {value} = columHelperValue(info.column.id, info); + return {moment(value).format("DD/MM/YYYY")}; + }, + }), + ]; - const { rows: filteredRows, renderSearch } = useListSearch( - paypalFilterRows, - updatedPaypalPayments - ); + const {rows: filteredRows, renderSearch} = useListSearch(paypalFilterRows, updatedPaypalPayments); - const paypalTable = useReactTable({ - data: filteredRows.sort((a, b) => - moment(b.createdAt).diff(moment(a.createdAt), "second") - ), - columns: paypalColumns, - getCoreRowModel: getCoreRowModel(), - }); + const paypalTable = useReactTable({ + data: filteredRows.sort((a, b) => moment(b.createdAt).diff(moment(a.createdAt), "second")), + columns: paypalColumns, + getCoreRowModel: getCoreRowModel(), + }); - const getUserModal = () => { - if (user) { - if (selectedCorporateUser) { - return ( - setSelectedCorporateUser(undefined)} - > - <> - {selectedCorporateUser && ( -
- { - setSelectedCorporateUser(undefined); - if (shouldReload) reload(); - }} - user={selectedCorporateUser} - disabled - disabledFields={{ countryManager: true }} - /> -
- )} - -
- ); - } + const getUserModal = () => { + if (user) { + if (selectedCorporateUser) { + return ( + setSelectedCorporateUser(undefined)}> + <> + {selectedCorporateUser && ( +
+ { + setSelectedCorporateUser(undefined); + if (shouldReload) reload(); + }} + user={selectedCorporateUser} + disabled + disabledFields={{countryManager: true}} + /> +
+ )} + +
+ ); + } - if (selectedAgentUser) { - return ( - setSelectedAgentUser(undefined)} - > - <> - {selectedAgentUser && ( -
- { - setSelectedAgentUser(undefined); - if (shouldReload) reload(); - }} - user={selectedAgentUser} - /> -
- )} - -
- ); - } - } + if (selectedAgentUser) { + return ( + setSelectedAgentUser(undefined)}> + <> + {selectedAgentUser && ( +
+ { + setSelectedAgentUser(undefined); + if (shouldReload) reload(); + }} + user={selectedAgentUser} + /> +
+ )} + +
+ ); + } + } - return null; - }; + return null; + }; - const getCSVData = () => { - const tables = [table, paypalTable]; - const whitelists = [ - CSV_PAYMENTS_WHITELISTED_KEYS, - CSV_PAYPAL_WHITELISTED_KEYS, - ]; - const currentTable = tables[selectedIndex]; - const whitelist = whitelists[selectedIndex]; - const columns = (currentTable.getHeaderGroups() as any[]).reduce( - (accm: any[], group: any) => { - const whitelistedColumns = group.headers.filter((header: any) => - whitelist.includes(header.id) - ); + const getCSVData = () => { + const tables = [table, paypalTable]; + const whitelists = [CSV_PAYMENTS_WHITELISTED_KEYS, CSV_PAYPAL_WHITELISTED_KEYS]; + const currentTable = tables[selectedIndex]; + const whitelist = whitelists[selectedIndex]; + const columns = (currentTable.getHeaderGroups() as any[]).reduce((accm: any[], group: any) => { + const whitelistedColumns = group.headers.filter((header: any) => whitelist.includes(header.id)); - const data = whitelistedColumns.map((data: any) => ({ - key: data.column.columnDef.id, - label: data.column.columnDef.header, - })) as SimpleCSVColumn[]; + const data = whitelistedColumns.map((data: any) => ({ + key: data.column.columnDef.id, + label: data.column.columnDef.header, + })) as SimpleCSVColumn[]; - return [...accm, ...data]; - }, - [] - ); + return [...accm, ...data]; + }, []); - const { rows } = currentTable.getRowModel(); + const {rows} = currentTable.getRowModel(); - const finalColumns = [ - ...columns, - { - key: "currency", - label: "Currency", - }, - ]; + const finalColumns = [ + ...columns, + { + key: "currency", + label: "Currency", + }, + ]; - return { - columns: finalColumns, - rows: rows.map((row) => { - return finalColumns.reduce((accm, { key }) => { - const { value } = columHelperValue(key, { - row, - getValue: () => row.getValue(key), - }); - return { - ...accm, - [key]: value, - }; - }, {}); - }), - }; - }; + return { + columns: finalColumns, + rows: rows.map((row) => { + return finalColumns.reduce((accm, {key}) => { + const {value} = columHelperValue(key, { + row, + getValue: () => row.getValue(key), + }); + return { + ...accm, + [key]: value, + }; + }, {}); + }), + }; + }; - const { rows: csvRows, columns: csvColumns } = getCSVData(); + const {rows: csvRows, columns: csvColumns} = getCSVData(); - const renderTable = (table: Table) => ( - - - {table.getHeaderGroups().map((headerGroup) => ( - - {headerGroup.headers.map((header) => ( - - ))} - - ))} - - - {table.getRowModel().rows.map((row) => ( - - {row.getVisibleCells().map((cell) => ( - - ))} - - ))} - -
- {header.isPlaceholder - ? null - : flexRender( - header.column.columnDef.header, - header.getContext() - )} -
- {flexRender(cell.column.columnDef.cell, cell.getContext())} -
- ); + const renderTable = (table: Table) => ( + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + ))} + + ))} + +
+ {header.isPlaceholder ? null : flexRender(header.column.columnDef.header, header.getContext())} +
+ {flexRender(cell.column.columnDef.cell, cell.getContext())} +
+ ); - return ( - <> - - Payment Record | EnCoach - - - - - - {user && ( - - {getUserModal()} - setIsCreatingPayment(false)} - > - setIsCreatingPayment(false)} - reload={reload} - showComission={checkAccess(user, ["developer", "admin"])} - /> - + return ( + <> + + Payment Record | EnCoach + + + + + + {user && ( + + {getUserModal()} + setIsCreatingPayment(false)}> + setIsCreatingPayment(false)} + reload={reload} + showComission={checkAccess(user, ["developer", "admin"])} + /> + -
-

Payment Record

-
- {checkAccess(user, [ - "developer", - "admin", - "agent", - "corporate", - "mastercorporate", - ]) && ( - - )} - {checkAccess(user, ["developer", "admin"]) && ( - - )} -
-
- - - - clsx( - "w-full rounded-lg py-2.5 text-sm font-medium leading-5 text-mti-purple-light", - "ring-white ring-opacity-60 ring-offset-2 ring-offset-mti-purple-light focus:outline-none focus:ring-2", - "transition duration-300 ease-in-out", - selected - ? "bg-white shadow" - : "text-blue-100 hover:bg-white/[0.12] hover:text-mti-purple-dark" - ) - } - > - Payments - - {checkAccess(user, ["developer", "admin"]) && ( - - clsx( - "w-full rounded-lg py-2.5 text-sm font-medium leading-5 text-mti-purple-light", - "ring-white ring-opacity-60 ring-offset-2 ring-offset-mti-purple-light focus:outline-none focus:ring-2", - "transition duration-300 ease-in-out", - selected - ? "bg-white shadow" - : "text-blue-100 hover:bg-white/[0.12] hover:text-mti-purple-dark" - ) - } - > - Paymob - - )} - - - -
-
- - u.type === "agent") as AgentUser[] - ).map((user) => ({ - value: user.id, - meta: user, - label: `${user.name} - ${user.email}`, - }))} - value={ - agent - ? { - value: agent?.id, - label: `${agent.name} - ${agent.email}`, - } - : undefined - } - onChange={(value) => - setAgent( - value !== null ? (value as any).meta : undefined - ) - } - menuPortalTarget={document?.body} - styles={{ - menuPortal: (base) => ({ ...base, zIndex: 9999 }), - control: (styles) => ({ - ...styles, - paddingLeft: "4px", - border: "none", - outline: "none", - ":focus": { - outline: "none", - }, - }), - option: (styles, state) => ({ - ...styles, - backgroundColor: state.isFocused - ? "#D5D9F0" - : state.isSelected - ? "#7872BF" - : "white", - color: state.isFocused ? "black" : styles.color, - }), - }} - /> -
- )} -
- - e.value === commissionTransfer - )} - onChange={(value) => { - if (value) return setCommissionTransfer(value.value); - setCommissionTransfer(null); - }} - menuPortalTarget={document?.body} - styles={{ - menuPortal: (base) => ({ ...base, zIndex: 9999 }), - control: (styles) => ({ - ...styles, - paddingLeft: "4px", - border: "none", - outline: "none", - ":focus": { - outline: "none", - }, - }), - option: (styles, state) => ({ - ...styles, - backgroundColor: state.isFocused - ? "#D5D9F0" - : state.isSelected - ? "#7872BF" - : "white", - color: state.isFocused ? "black" : styles.color, - }), - }} - /> -
- )} -
- - u.type === "corporate") as CorporateUser[]).map((user) => ({ + value: user.id, + meta: user, + label: `${user.corporateInformation?.companyInformation?.name || user.name} - ${user.email}`, + }))} + defaultValue={ + user.type === "corporate" + ? { + value: user.id, + meta: user, + label: `${user.corporateInformation?.companyInformation?.name || user.name} - ${ + user.email + }`, + } + : undefined + } + isDisabled={user.type === "corporate"} + onChange={(value) => setCorporate((value as any)?.meta ?? undefined)} + menuPortalTarget={document?.body} + styles={{ + menuPortal: (base) => ({...base, zIndex: 9999}), + control: (styles) => ({ + ...styles, + paddingLeft: "4px", + border: "none", + outline: "none", + ":focus": { + outline: "none", + }, + }), + option: (styles, state) => ({ + ...styles, + backgroundColor: state.isFocused ? "#D5D9F0" : state.isSelected ? "#7872BF" : "white", + color: state.isFocused ? "black" : styles.color, + }), + }} + /> +
+ {user.type !== "corporate" && ( +
+ + e.value === paid)} + onChange={(value) => { + if (value) return setPaid(value.value); + setPaid(null); + }} + menuPortalTarget={document?.body} + styles={{ + menuPortal: (base) => ({...base, zIndex: 9999}), + control: (styles) => ({ + ...styles, + paddingLeft: "4px", + border: "none", + outline: "none", + ":focus": { + outline: "none", + }, + }), + option: (styles, state) => ({ + ...styles, + backgroundColor: state.isFocused ? "#D5D9F0" : state.isSelected ? "#7872BF" : "white", + color: state.isFocused ? "black" : styles.color, + }), + }} + /> +
+
+ + moment(date).isSameOrBefore(moment(new Date()))} + onChange={([initialDate, finalDate]: [Date, Date]) => { + setStartDate(initialDate ?? moment("01/01/2023").toDate()); + if (finalDate) { + // basicly selecting a final day works as if I'm selecting the first + // minute of that day. this way it covers the whole day + setEndDate(moment(finalDate).endOf("day").toDate()); + return; + } + setEndDate(null); + }} + /> +
+ {user.type !== "corporate" && ( +
+ + e.value === corporateTransfer)} + onChange={(value) => { + if (value) return setCorporateTransfer(value.value); + setCorporateTransfer(null); + }} + menuPortalTarget={document?.body} + styles={{ + menuPortal: (base) => ({...base, zIndex: 9999}), + control: (styles) => ({ + ...styles, + paddingLeft: "4px", + border: "none", + outline: "none", + ":focus": { + outline: "none", + }, + }), + option: (styles, state) => ({ + ...styles, + backgroundColor: state.isFocused ? "#D5D9F0" : state.isSelected ? "#7872BF" : "white", + color: state.isFocused ? "black" : styles.color, + }), + }} + /> +
+
+ {renderTable(table as Table)} +
+ +
+
+ + moment(date).isSameOrBefore(moment(new Date()))} + onChange={([initialDate, finalDate]: [Date, Date]) => { + setStartDatePaymob(initialDate ?? moment("01/01/2023").toDate()); + if (finalDate) { + // basicly selecting a final day works as if I'm selecting the first + // minute of that day. this way it covers the whole day + setEndDatePaymob(moment(finalDate).endOf("day").toDate()); + return; + } + setEndDatePaymob(null); + }} + /> +
+
+ {renderSearch()} + {renderTable(paypalTable as Table)} +
+
+
+
+ )} + + ); } diff --git a/src/pages/payment.tsx b/src/pages/payment.tsx index bc2984f3..78f3b573 100644 --- a/src/pages/payment.tsx +++ b/src/pages/payment.tsx @@ -16,7 +16,7 @@ export const getServerSideProps = withIronSessionSsr(({req, res}) => { envVariables[x] = process.env[x]!; }); - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/permissions/[id].tsx b/src/pages/permissions/[id].tsx index 022ba933..6e66f109 100644 --- a/src/pages/permissions/[id].tsx +++ b/src/pages/permissions/[id].tsx @@ -32,7 +32,7 @@ export const getServerSideProps = withIronSessionSsr(async (context) => { const {req, params} = context; const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/permissions/index.tsx b/src/pages/permissions/index.tsx index 373707e7..6e116600 100644 --- a/src/pages/permissions/index.tsx +++ b/src/pages/permissions/index.tsx @@ -12,7 +12,7 @@ import PermissionList from "@/components/PermissionList"; export const getServerSideProps = withIronSessionSsr(async ({req}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/profile.tsx b/src/pages/profile.tsx index 93d0efad..d864670b 100644 --- a/src/pages/profile.tsx +++ b/src/pages/profile.tsx @@ -50,7 +50,7 @@ import {getUsers} from "@/utils/users.be"; export const getServerSideProps = withIronSessionSsr(async ({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/record.tsx b/src/pages/record.tsx index 3500fe70..c4d520d0 100644 --- a/src/pages/record.tsx +++ b/src/pages/record.tsx @@ -29,7 +29,7 @@ import useGradingSystem from "@/hooks/useGrading"; export const getServerSideProps = withIronSessionSsr(async ({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/register.tsx b/src/pages/register.tsx index 3cfda76d..b8961ae9 100644 --- a/src/pages/register.tsx +++ b/src/pages/register.tsx @@ -121,7 +121,7 @@ export default function Register({code: queryCode}: {code: string}) { )} - {user && !user.isVerified && } + {/* {user && !user.isVerified && } */} diff --git a/src/pages/settings.tsx b/src/pages/settings.tsx index b26a6a5e..e3dce976 100644 --- a/src/pages/settings.tsx +++ b/src/pages/settings.tsx @@ -31,7 +31,7 @@ import useUsers from "@/hooks/useUsers"; export const getServerSideProps = withIronSessionSsr(async ({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/stats.tsx b/src/pages/stats.tsx index b9c78c8c..4c45090f 100644 --- a/src/pages/stats.tsx +++ b/src/pages/stats.tsx @@ -34,7 +34,7 @@ const COLORS = ["#1EB3FF", "#FF790A", "#3D9F11", "#EF5DA8", "#414288"]; export const getServerSideProps = withIronSessionSsr(({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/tickets.tsx b/src/pages/tickets.tsx index d2957f79..fb6e2b47 100644 --- a/src/pages/tickets.tsx +++ b/src/pages/tickets.tsx @@ -22,7 +22,7 @@ const columnHelper = createColumnHelper(); export const getServerSideProps = withIronSessionSsr(({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/training/[id]/index.tsx b/src/pages/training/[id]/index.tsx index 2dab7719..69aab218 100644 --- a/src/pages/training/[id]/index.tsx +++ b/src/pages/training/[id]/index.tsx @@ -35,7 +35,7 @@ import {sortByModule} from "@/utils/moduleUtils"; export const getServerSideProps = withIronSessionSsr(({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", diff --git a/src/pages/training/index.tsx b/src/pages/training/index.tsx index 3c074561..461ca135 100644 --- a/src/pages/training/index.tsx +++ b/src/pages/training/index.tsx @@ -1,30 +1,30 @@ /* eslint-disable @next/next/no-img-element */ import Head from "next/head"; -import { withIronSessionSsr } from "iron-session/next"; -import { sessionOptions } from "@/lib/session"; -import { User } from "@/interfaces/user"; -import { ToastContainer } from "react-toastify"; +import {withIronSessionSsr} from "iron-session/next"; +import {sessionOptions} from "@/lib/session"; +import {User} from "@/interfaces/user"; +import {ToastContainer} from "react-toastify"; import Layout from "@/components/High/Layout"; -import { shouldRedirectHome } from "@/utils/navigation.disabled"; -import { useEffect, useState } from "react"; +import {shouldRedirectHome} from "@/utils/navigation.disabled"; +import {useEffect, useState} from "react"; import clsx from "clsx"; -import { FaPlus } from "react-icons/fa"; +import {FaPlus} from "react-icons/fa"; import useRecordStore from "@/stores/recordStore"; import router from "next/router"; import useTrainingContentStore from "@/stores/trainingContentStore"; import axios from "axios"; -import { ITrainingContent } from "@/training/TrainingInterfaces"; +import {ITrainingContent} from "@/training/TrainingInterfaces"; import moment from "moment"; -import { uuidv4 } from "@firebase/util"; +import {uuidv4} from "@firebase/util"; import TrainingScore from "@/training/TrainingScore"; import ModuleBadge from "@/components/ModuleBadge"; import RecordFilter from "@/components/Medium/RecordFilter"; import useFilterRecordsByUser from "@/hooks/useFilterRecordsByUser"; -export const getServerSideProps = withIronSessionSsr(({ req, res }) => { +export const getServerSideProps = withIronSessionSsr(({req, res}) => { const user = req.session.user; - if (!user || !user.isVerified) { + if (!user) { return { redirect: { destination: "/login", @@ -43,22 +43,23 @@ export const getServerSideProps = withIronSessionSsr(({ req, res }) => { } return { - props: { user: req.session.user }, + props: {user: req.session.user}, }; }, sessionOptions); -const Training: React.FC<{ user: User }> = ({ user }) => { - const [recordUserId, setRecordTraining] = useRecordStore((state) => [ - state.selectedUser, - state.setTraining, - ]); +const Training: React.FC<{user: User}> = ({user}) => { + const [recordUserId, setRecordTraining] = useRecordStore((state) => [state.selectedUser, state.setTraining]); const [filter, setFilter] = useState<"months" | "weeks" | "days" | "assignments">(); const [stats, setTrainingStats] = useTrainingContentStore((state) => [state.stats, state.setStats]); const [isNewContentLoading, setIsNewContentLoading] = useState(stats.length != 0); - const [groupedByTrainingContent, setGroupedByTrainingContent] = useState<{ [key: string]: ITrainingContent }>(); + const [groupedByTrainingContent, setGroupedByTrainingContent] = useState<{[key: string]: ITrainingContent}>(); - const { data: trainingContent, isLoading: areRecordsLoading } = useFilterRecordsByUser(recordUserId || user?.id, undefined, "training"); + const {data: trainingContent, isLoading: areRecordsLoading} = useFilterRecordsByUser( + recordUserId || user?.id, + undefined, + "training", + ); useEffect(() => { const handleRouteChange = (url: string) => { @@ -74,7 +75,7 @@ const Training: React.FC<{ user: User }> = ({ user }) => { useEffect(() => { const postStats = async () => { try { - const response = await axios.post<{ id: string }>(`/api/training`, { userID: user.id, stats: stats }); + const response = await axios.post<{id: string}>(`/api/training`, {userID: user.id, stats: stats}); return response.data.id; } catch (error) { setIsNewContentLoading(false); @@ -97,12 +98,12 @@ const Training: React.FC<{ user: User }> = ({ user }) => { router.push("/record"); }; - const filterTrainingContentByDate = (trainingContent: { [key: string]: ITrainingContent }) => { + const filterTrainingContentByDate = (trainingContent: {[key: string]: ITrainingContent}) => { if (filter) { const filterDate = moment() - .subtract({ [filter as string]: 1 }) + .subtract({[filter as string]: 1}) .format("x"); - const filteredTrainingContent: { [key: string]: ITrainingContent } = {}; + const filteredTrainingContent: {[key: string]: ITrainingContent} = {}; Object.keys(trainingContent).forEach((timestamp) => { if (timestamp >= filterDate) filteredTrainingContent[timestamp] = trainingContent[timestamp]; @@ -117,10 +118,10 @@ const Training: React.FC<{ user: User }> = ({ user }) => { const grouped = trainingContent.reduce((acc, content) => { acc[content.created_at] = content; return acc; - }, {} as { [key: number]: ITrainingContent }); + }, {} as {[key: number]: ITrainingContent}); setGroupedByTrainingContent(grouped); - }else { + } else { setGroupedByTrainingContent(undefined); } }, [trainingContent]); @@ -138,7 +139,7 @@ const Training: React.FC<{ user: User }> = ({ user }) => { const trainingContentContainer = (timestamp: string) => { if (!groupedByTrainingContent) return <>; - + const trainingContent: ITrainingContent = groupedByTrainingContent[timestamp]; const uniqueModules = [...new Set(trainingContent.exams.map((exam) => exam.module))]; @@ -192,7 +193,7 @@ const Training: React.FC<{ user: User }> = ({ user }) => { ) : ( <> - + {user.type === "student" && ( <>