Skip to content

Commit

Permalink
Merge branch 'main' into prod
Browse files Browse the repository at this point in the history
  • Loading branch information
lucia-gomez committed Sep 16, 2024
2 parents d180c2d + 89779e9 commit 0638add
Show file tree
Hide file tree
Showing 17 changed files with 246 additions and 114 deletions.
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
import { PageContextLevel, PagePermission } from "../../../../types";
import React, { useContext, useMemo, useState } from "react";

import { Bookings } from "../../components/bookingTable/Bookings";
import { Box } from "@mui/material";
import { CenterLoading } from "../../components/Loading";
import { DatabaseContext } from "../../components/Provider";
import { PagePermission } from "../../../../types";
import Settings from "./Settings";
import Tab from "@mui/material/Tab";
import Tabs from "@mui/material/Tabs";

// This is a wrapper for google.script.run that lets us use promises.

export default function Admin() {
const [tab, setTab] = useState("bookings");
const { adminUsers, pagePermission, userEmail } = useContext(DatabaseContext);
Expand Down Expand Up @@ -40,7 +38,9 @@ export default function Admin() {
<Tab value="bookings" label="Bookings" />
<Tab value="settings" label="Settings" />
</Tabs>
{tab === "bookings" && <Bookings isAdminView={true} />}
{tab === "bookings" && (
<Bookings pageContext={PageContextLevel.ADMIN} />
)}
{tab === "settings" && <Settings />}
</div>
)}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,27 +1,26 @@
import { BookingStatusLabel, PageContextLevel } from "../../../../types";
import { IconButton, MenuItem, Select } from "@mui/material";
import React, { useContext, useMemo, useState } from "react";
import {
cancel,
checkOut,
checkin,
clientApproveBooking,
decline,
noShow,
} from "@/components/src/server/db";

import AlertToast from "../../components/AlertToast";
import { BookingStatusLabel } from "../../../../types";
import Check from "@mui/icons-material/Check";
import ConfirmDialog from "../../components/ConfirmDialog";
import { DatabaseContext } from "../../components/Provider";
import Loading from "../../components/Loading";
import useExistingBooking from "../hooks/useExistingBooking";
import { useRouter } from "next/navigation";
import {
cancel,
checkin,
checkOut,
clientApproveBooking,
decline,
noShow,
} from "@/components/src/server/db";

interface Props {
calendarEventId: string;
isAdminView: boolean;
isUserView: boolean;
pageContext: PageContextLevel;
setOptimisticStatus: (x: BookingStatusLabel) => void;
status: BookingStatusLabel;
}
Expand All @@ -48,8 +47,7 @@ type ActionDefinition = {
export default function BookingActions({
status,
calendarEventId,
isAdminView,
isUserView,
pageContext,
setOptimisticStatus,
}: Props) {
const [uiLoading, setUiLoading] = useState(false);
Expand Down Expand Up @@ -209,9 +207,14 @@ export default function BookingActions({
}, [status, paOptions]);

const options = () => {
if (isUserView) return userOptions;
if (isAdminView) return adminOptions;
return paOptions;
switch (pageContext) {
case PageContextLevel.USER:
return userOptions;
case PageContextLevel.PA:
return paOptions;
default:
return adminOptions;
}
};

if (options().length === 0) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
import { Box, IconButton } from "@mui/material";

import { BookingStatusLabel } from "../../../../types";
import { Close } from "@mui/icons-material";
import { EventContentArg } from "@fullcalendar/core";
import React from "react";
import { styled, useTheme } from "@mui/material/styles";
import { styled } from "@mui/material/styles";

export const NEW_TITLE_TAG = "Your Reservation";
export const UNKNOWN_BLOCK_TITLE = "Unavailable";

interface Props {
bgcolor: string;
Expand Down Expand Up @@ -40,9 +42,12 @@ const CloseButton = styled(IconButton)(({ theme }) => ({
}));

export default function CalendarEventBlock(eventInfo: EventContentArg) {
const match = eventInfo.event.title.match(/\[(.*?)\]/);
const title = match ? match[1] : eventInfo.event.title;
const isNew = eventInfo.event.title === NEW_TITLE_TAG;
let title = isNew ? NEW_TITLE_TAG : UNKNOWN_BLOCK_TITLE;
if (eventInfo.event.title.trim().length === 0) {
title = "";
}

const params = eventInfo.event.url
? eventInfo.event.url.split(":")
: ["0", "0"];
Expand All @@ -55,13 +60,7 @@ export default function CalendarEventBlock(eventInfo: EventContentArg) {
if (isNew) {
return null;
}
let backgroundColor = "rgba(72, 196, 77, 1)";
if (eventInfo.event.title.includes(BookingStatusLabel.REQUESTED)) {
backgroundColor = "rgba(255, 122, 26, 1)";
} else if (eventInfo.event.title.includes(BookingStatusLabel.PENDING)) {
backgroundColor = "rgba(223, 26, 255, 1)";
}
return backgroundColor;
return "rgba(72, 196, 77, 1)";
};

const hideTitle = isNew && index !== 0 && !isOneColumn;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -218,7 +218,7 @@ export default function FormInput({
description="Your N-number begins with a capital 'N' followed by eight digits."
required
pattern={{
value: /N[0-9]{8}/,
value: /N[0-9]{8}$/,
message: "Invalid N-Number",
}}
{...{ control, errors, trigger }}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
import { Booking, BookingStatusLabel } from "../../../../types";
import {
Booking,
BookingStatusLabel,
PageContextLevel,
} from "../../../../types";
import { Box, ToggleButton, ToggleButtonGroup } from "@mui/material";
import { CalendarMonth, DateRange, Today } from "@mui/icons-material";

Expand Down Expand Up @@ -45,7 +49,7 @@ export const DATE_FILTERS: Record<DateRangeFilter, (x: Booking) => boolean> = {

interface Props {
allowedStatuses: BookingStatusLabel[];
isPaView: boolean;
pageContext: PageContextLevel;
selectedStatuses: BookingStatusLabel[];
setSelectedStatuses: any;
selectedDateRange: DateRangeFilter;
Expand All @@ -54,7 +58,7 @@ interface Props {

export default function BookingTableFilters({
allowedStatuses,
isPaView,
pageContext,
selectedStatuses,
setSelectedStatuses,
selectedDateRange,
Expand Down Expand Up @@ -128,7 +132,7 @@ export default function BookingTableFilters({
)
)}
</Box>
<Box>{isPaView && dateFilters}</Box>
<Box>{pageContext >= PageContextLevel.PA && dateFilters}</Box>
</Box>
);
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
import { BookingRow, BookingStatusLabel } from "../../../../types";
import {
BookingRow,
BookingStatusLabel,
PageContextLevel,
} from "../../../../types";
import {
IconButton,
Switch,
Expand All @@ -20,22 +24,20 @@ import getBookingStatus from "../../hooks/getBookingStatus";

interface Props {
booking: BookingRow;
isAdminView: boolean;
isPaView: boolean;
isUserView: boolean;
pageContext: PageContextLevel;
setModalData: (x: BookingRow) => void;
}

export default function BookingTableRow({
booking,
isAdminView,
isPaView,
isUserView,
pageContext,
setModalData,
}: Props) {
const { bookingStatuses } = useContext(DatabaseContext);
const titleRef = useRef();

const isUserView = pageContext === PageContextLevel.USER;

const [optimisticStatus, setOptimisticStatus] =
useState<BookingStatusLabel>();

Expand Down Expand Up @@ -121,7 +123,7 @@ export default function BookingTableRow({
<BookingActions
status={optimisticStatus ?? status}
calendarEventId={booking.calendarEventId}
{...{ setOptimisticStatus, isAdminView, isUserView }}
{...{ setOptimisticStatus, pageContext }}
/>
</TableCell>
</TableRow>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,9 @@
import { Booking, BookingRow, BookingStatusLabel } from "../../../../types";
import {
Booking,
BookingRow,
BookingStatusLabel,
PageContextLevel,
} from "../../../../types";
import BookingTableFilters, {
DATE_FILTERS,
DateRangeFilter,
Expand All @@ -22,16 +27,10 @@ import MoreInfoModal from "./MoreInfoModal";
import getBookingStatus from "../../hooks/getBookingStatus";

interface BookingsProps {
isAdminView?: boolean;
isPaView?: boolean;
isUserView?: boolean;
pageContext: PageContextLevel;
}

export const Bookings: React.FC<BookingsProps> = ({
isAdminView = false,
isPaView = false,
isUserView = false,
}) => {
export const Bookings: React.FC<BookingsProps> = ({ pageContext }) => {
const {
bookings,
bookingsLoading,
Expand All @@ -49,6 +48,8 @@ export const Bookings: React.FC<BookingsProps> = ({
const [order, setOrder] = useState<"asc" | "desc">("asc");
const [currentTime, setCurrentTime] = useState(new Date());

const isUserView = pageContext === PageContextLevel.USER;

useEffect(() => {
reloadBookingStatuses();
reloadBookings();
Expand Down Expand Up @@ -79,24 +80,21 @@ export const Bookings: React.FC<BookingsProps> = ({
BookingStatusLabel.NO_SHOW,
BookingStatusLabel.WALK_IN,
];
if (isPaView) {
if (pageContext === PageContextLevel.PA) {
return paViewStatuses;
} else {
return Object.values(BookingStatusLabel);
}
}, [isUserView, isPaView]);
}, [pageContext]);

const filteredRows = useMemo(() => {
let filtered: BookingRow[] = rows;
// filter based on user view
if (isUserView) filtered = rows.filter((row) => row.email === userEmail);
else if (isPaView)
filtered = rows.filter((row) => allowedStatuses.includes(row.status));

// filter if endTime has passed and status is NO_SHOW or CHECKED_OUT
const elapsedStatues = [
BookingStatusLabel.NO_SHOW,
BookingStatusLabel.CHECKED_OUT,
BookingStatusLabel.CANCELED,
];
// checks once per minute
filtered = filtered.filter(
Expand All @@ -107,8 +105,16 @@ export const Bookings: React.FC<BookingsProps> = ({
)
);

// filter by selected PA date range
if (isPaView) {
// filter based on user view
if (pageContext === PageContextLevel.USER)
filtered = rows.filter((row) => row.email === userEmail);
else if (pageContext === PageContextLevel.PA) {
filtered = rows.filter((row) => allowedStatuses.includes(row.status));
}

if (pageContext >= PageContextLevel.PA) {
// PA and Admin
// filter by selected PA date range
filtered = filtered.filter(DATE_FILTERS[selectedDateRange]);
}

Expand All @@ -123,8 +129,7 @@ export const Bookings: React.FC<BookingsProps> = ({
}
return filtered.filter((row) => statusFilters.includes(row.status));
}, [
isUserView,
isPaView,
pageContext,
rows,
allowedStatuses,
statusFilters,
Expand All @@ -135,7 +140,7 @@ export const Bookings: React.FC<BookingsProps> = ({
]);

const topRow = useMemo(() => {
if (isUserView) {
if (pageContext === PageContextLevel.USER) {
return (
<Box
sx={{
Expand All @@ -155,13 +160,13 @@ export const Bookings: React.FC<BookingsProps> = ({
setSelectedStatuses={setStatusFilters}
{...{
allowedStatuses,
isPaView,
pageContext,
selectedDateRange,
setSelectedDateRange,
}}
/>
);
}, [isUserView, statusFilters, allowedStatuses, selectedDateRange]);
}, [pageContext, statusFilters, allowedStatuses, selectedDateRange]);

const bottomSection = useMemo(() => {
if (bookingsLoading && bookings.length === 0) {
Expand All @@ -174,13 +179,13 @@ export const Bookings: React.FC<BookingsProps> = ({
if (filteredRows.length === 0) {
return (
<TableEmpty>
{isUserView
{pageContext === PageContextLevel.USER
? "You don't have any reservations"
: "No active reservations found"}
</TableEmpty>
);
}
}, [isUserView, bookingsLoading, filteredRows]);
}, [pageContext, bookingsLoading, filteredRows]);

const createSortHandler = useCallback(
(property: keyof Booking) => (_: React.MouseEvent<unknown>) => {
Expand Down Expand Up @@ -250,8 +255,7 @@ export const Bookings: React.FC<BookingsProps> = ({
key={row.calendarEventId}
{...{
booking: row,
isAdminView,
isPaView,
pageContext,
isUserView,
setModalData,
}}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { Box, Typography } from "@mui/material";

import { Bookings } from "../components/bookingTable/Bookings";
import { PageContextLevel } from "@/components/src/types";
import React from "react";
import { styled } from "@mui/system";

Expand All @@ -15,7 +16,7 @@ export default function MyBookingsPage() {
<Center>
<Box width="65%" margin={6}>
<Typography variant="h6">Welcome</Typography>
<Bookings isUserView={true} />
<Bookings pageContext={PageContextLevel.USER} />
</Box>
</Center>
);
Expand Down
Loading

0 comments on commit 0638add

Please sign in to comment.