import ErrorDisplay from "@/ui/error-display"; import { useApi } from "@/util/api"; import { AircraftFormSchema, AircraftSchema } from "@/util/types"; import { ActionIcon, Button, Card, Center, Container, Group, Loader, Modal, NumberInput, ScrollArea, Select, Stack, Text, TextInput, Title, Tooltip, } from "@mantine/core"; import { useForm } from "@mantine/form"; import { randomId, useDisclosure } from "@mantine/hooks"; import { IconPencil, IconPlus, IconTrash, IconX } from "@tabler/icons-react"; import { UseQueryResult, useMutation, useQuery, useQueryClient, } from "@tanstack/react-query"; import { AxiosError } from "axios"; import { useState } from "react"; function useAircraft() { const client = useApi(); const aircraft = useQuery({ queryKey: ["aircraft-list"], queryFn: async () => await client.get(`/aircraft`).then((res) => res.data), }); return aircraft; } function AircraftCard({ aircraft }: { aircraft: AircraftSchema }) { const [deleteOpened, { open: openDelete, close: closeDelete }] = useDisclosure(false); const client = useApi(); const queryClient = useQueryClient(); const deleteAircraft = useMutation({ mutationFn: async () => await client.delete(`/aircraft/${aircraft.id}`).then((res) => res.data), onSuccess: () => { queryClient.invalidateQueries({ queryKey: ["aircraft-list"] }); }, }); return ( <> Are you sure you want to delete this aircraft? This action cannot be undone. {deleteAircraft.isError ? ( {deleteAircraft.error.message} ) : null} {aircraft.tail_no} {aircraft.make} {aircraft.model} {aircraft.aircraft_category} / {aircraft.aircraft_class} {aircraft.hobbs ? Hobbs: {aircraft.hobbs} : null} ); } function NewAircraftModal({ opened, close, }: { opened: boolean; close: () => void; }) { const newForm = useForm({ initialValues: { tail_no: "", make: "", model: "", aircraft_category: "", aircraft_class: "", hobbs: 0.0, }, validate: { tail_no: (value) => value === null || value.trim() === "" ? "Please enter a tail number" : null, make: (value) => value === null || value.trim() === "" ? "Please enter a make" : null, model: (value) => value === null || value.trim() === "" ? "Please enter a model" : null, aircraft_category: (value) => value === null || value.trim() === "" ? "Please select a category" : null, aircraft_class: (value) => value === null || value.trim() === "" ? "Please select a class" : null, }, }); const client = useApi(); const queryClient = useQueryClient(); const categories = useQuery({ queryKey: ["categories"], queryFn: async () => await client.get(`/aircraft/categories`).then((res) => res.data), }); const [category, setCategory] = useState(""); const [classSelection, setClassSelection] = useState(""); const classes = useQuery({ queryKey: ["classes", category], queryFn: async () => await client .get(`/aircraft/class?category=${category}`) .then((res) => res.data), enabled: !!category, }); const addAircraft = useMutation({ mutationFn: async (values: AircraftFormSchema) => { const newAircraft = values; if (newAircraft) { const res = await client.post("/aircraft", newAircraft); return res.data; } throw new Error("Aircraft creation failed"); }, onSuccess: async () => { await queryClient.invalidateQueries({ queryKey: ["aircraft-list"] }); close(); }, }); return (
addAircraft.mutate(values))}> {addAircraft.isError ? ( {(addAircraft.error as AxiosError)?.response?.data?.detail ?? "Error adding aircraft"} ) : addAircraft.isPending ? ( Adding aircraft... ) : null}
); } export default function Aircraft() { const aircraft: UseQueryResult = useAircraft(); const [newOpened, { open: openNew, close: closeNew }] = useDisclosure(false); return ( <> Aircraft {aircraft.isLoading ? (
) : aircraft.isError ? (
) : aircraft.data && aircraft.data.length === 0 ? (
No Aircraft
) : ( {aircraft.data?.map((item) => ( ))} )}
); }