init: Init React Application

This commit is contained in:
2025-05-29 13:21:33 +03:00
parent 9444939507
commit 17de7e495f
66 changed files with 10425 additions and 0 deletions

View File

@@ -0,0 +1,206 @@
import Table from "@mui/material/Table";
import TableBody from "@mui/material/TableBody";
import TableCell from "@mui/material/TableCell";
import TableContainer from "@mui/material/TableContainer";
import TableHead from "@mui/material/TableHead";
import TableRow from "@mui/material/TableRow";
import Paper from "@mui/material/Paper";
import { Check, RotateCcw, Send, X } from "lucide-react";
import { devicesStore, Modal, snapshotStore, vehicleStore } from "@shared";
import { useEffect, useState } from "react";
import { observer } from "mobx-react-lite";
import { Button, Checkbox } from "@mui/material";
const formatDate = (dateString: string | undefined) => {
if (!dateString) return "Нет данных";
try {
const date = new Date(dateString);
return new Intl.DateTimeFormat("ru-RU", {
day: "2-digit",
month: "2-digit",
year: "numeric",
hour: "2-digit",
minute: "2-digit",
second: "2-digit",
hour12: false,
}).format(date);
} catch (error) {
console.error("Error formatting date:", error);
return "Некорректная дата";
}
};
function createData(
uuid: string,
online: boolean,
lastUpdate: string,
gps: boolean,
media: boolean,
connection: boolean
) {
return { uuid, online, lastUpdate, gps, media, connection };
}
const rows = (devices: any[], vehicles: any[]) => {
return devices.map((device) => {
const { device_status } = vehicles.find(
(v) => v?.device_status?.device_uuid === device
);
const findVehicle = vehicles.find((v) => v?.vehicle?.uuid === device);
console.log(findVehicle);
return createData(
findVehicle?.vehicle?.tail_number ?? "1243000",
device_status?.online,
device_status?.last_update,
device_status?.gps_ok,
device_status?.media_service_ok,
device_status?.is_connected
);
});
};
export const DevicesTable = observer(() => {
const {
devices,
getDevices,
uuid,
setSelectedDevice,
sendSnapshotModalOpen,
toggleSendSnapshotModal,
} = devicesStore;
const { snapshots, getSnapshots } = snapshotStore;
const { vehicles, getVehicles } = vehicleStore;
const [selectedDevices, setSelectedDevices] = useState<string[]>([]);
useEffect(() => {
const fetchData = async () => {
await getVehicles();
await getDevices();
await getSnapshots();
};
fetchData();
}, []);
const handleSendSnapshot = (uuid: string[]) => {
setSelectedDevice(uuid);
toggleSendSnapshotModal();
};
const handleReloadStatus = (uuid: string) => {
setSelectedDevice(uuid);
};
const handleSelectDevice = (event: React.ChangeEvent<HTMLInputElement>) => {
if (event.target.checked) {
setSelectedDevices([...selectedDevices, event.target.value]);
} else {
setSelectedDevices(
selectedDevices.filter((device) => device !== event.target.value)
);
}
};
return (
<>
<TableContainer component={Paper}>
<div className="flex justify-end p-3 gap-5">
<Button variant="contained" color="primary">
Выбрать все
</Button>
<Button
variant="contained"
color="primary"
disabled={selectedDevices.length === 0}
className="ml-auto"
onClick={() => handleSendSnapshot(selectedDevices)}
>
Отправить снапшот
</Button>
</div>
<Table sx={{ minWidth: 650 }} aria-label="simple table">
<TableHead>
<TableRow>
<TableCell align="center"></TableCell>
<TableCell align="center">Бортовой номер</TableCell>
<TableCell align="center">Онлайн</TableCell>
<TableCell align="center">Последнее обновление</TableCell>
<TableCell align="center">ГПС</TableCell>
<TableCell align="center">Медиа-данные</TableCell>
<TableCell align="center">Подключение</TableCell>
<TableCell align="center">Перезапросить</TableCell>
</TableRow>
</TableHead>
<TableBody>
{rows(devices, vehicles).map((row) => (
<TableRow
key={row?.uuid}
sx={{ "&:last-child td, &:last-child th": { border: 0 } }}
className="flex items-center"
>
<TableCell align="center">
<Checkbox
className="h-full"
onChange={handleSelectDevice}
value={row?.uuid}
/>
</TableCell>
<TableCell align="center" component="th" scope="row">
{row?.uuid}
</TableCell>
<TableCell align="center">
{row?.online ? (
<Check className="m-auto text-green-500" />
) : (
<X className="m-auto text-red-500" />
)}
</TableCell>
<TableCell align="center">
{formatDate(row?.lastUpdate)}
</TableCell>
<TableCell align="center">
{row?.gps ? (
<Check className="m-auto text-green-500" />
) : (
<X className="m-auto text-red-500" />
)}
</TableCell>
<TableCell align="center">
{row?.media ? (
<Check className="m-auto text-green-500" />
) : (
<X className="m-auto text-red-500" />
)}
</TableCell>
<TableCell align="center">
{row?.connection ? (
<Check className="m-auto text-green-500" />
) : (
<X className="m-auto text-red-500" />
)}
</TableCell>
<TableCell align="center" className="flex justify-center">
<button onClick={() => handleReloadStatus(row?.uuid ?? "")}>
<RotateCcw className="m-auto" />
</button>
</TableCell>
</TableRow>
))}
</TableBody>
</Table>
</TableContainer>
<Modal open={sendSnapshotModalOpen} onClose={toggleSendSnapshotModal}>
<p>Выбрать снапшот</p>
<div className="mt-5 flex flex-col gap-2 max-h-[300px] overflow-y-auto">
{snapshots &&
snapshots.map((snapshot) => (
<button className="p-2 rounded-xl bg-slate-100" key={snapshot.id}>
{snapshot.Name}
</button>
))}
</div>
</Modal>
</>
);
});