Files
var-monorepo/apps/dispatch-server/routes/mission.ts
PxlLoewe fa10f4d7d4 dev
2025-05-21 09:21:25 -07:00

207 lines
4.8 KiB
TypeScript

import { prisma } from "@repo/db";
import { Router } from "express";
import { io } from "../index";
import { sendNtfyMission } from "modules/ntfy";
const router = Router();
// Get all missions
router.post("/", async (req, res) => {
try {
const filter = req.body?.filter || {};
const missions = await prisma.mission.findMany({
where: filter,
});
res.json(missions);
} catch (error) {
console.error(error);
res.status(500).json({ error: "Failed to fetch missions" });
}
});
// Get a single mission by ID
router.get("/:id", async (req, res) => {
const { id } = req.params;
try {
const mission = await prisma.mission.findUnique({
where: { id: Number(id) },
});
if (mission) {
res.json(mission);
} else {
res.status(404).json({ error: "Mission not found" });
}
} catch (error) {
console.error(error);
res.status(500).json({ error: "Failed to fetch mission" });
}
});
// Create a new mission
router.put("/", async (req, res) => {
try {
const startOfToday = new Date();
startOfToday.setHours(0, 0, 0, 0);
const missionsTodayCount = await prisma.mission.count({
where: {
createdAt: {
gte: startOfToday,
},
},
});
const date = new Date();
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, "0"); // Months are zero-based
const day = String(date.getDate()).padStart(2, "0");
const publicId = `__${year}${month}${day}${missionsTodayCount ? missionsTodayCount + 1 : 1}`;
const newMission = await prisma.mission.create({
data: {
...req.body,
publicId,
},
});
io.to("dispatchers").emit("new-mission", { newMission });
res.status(201).json(newMission);
} catch (error) {
res.status(500).json({ error: "Failed to create mission" });
}
});
// Update a mission by ID
router.patch("/:id", async (req, res) => {
const { id } = req.params;
try {
const updatedMission = await prisma.mission.update({
where: { id: Number(id) },
data: req.body,
});
io.to("dispatchers").emit("update-mission", updatedMission);
res.json(updatedMission);
} catch (error) {
console.error(error);
res.status(500).json({ error: "Failed to update mission" });
}
});
// Delete a mission by ID
router.delete("/:id", async (req, res) => {
const { id } = req.params;
try {
await prisma.mission.delete({
where: { id: Number(id) },
});
io.to("dispatchers").emit("delete-mission", id);
res.status(204).send();
} catch (error) {
console.error(error);
res.status(500).json({ error: "Failed to delete mission" });
}
});
// Send mission
router.post("/:id/send-alert", async (req, res) => {
const { id } = req.params;
const { stationId } = req.body as { stationId?: number };
try {
const mission = await prisma.mission.findUnique({
where: { id: Number(id) },
});
const Stations = await prisma.station.findMany({
where: {
id: {
in: mission?.missionStationIds,
},
},
});
if (!mission) {
res.status(404).json({ error: "Mission not found" });
return;
}
// connectedAircrafts the alert is sent to
const connectedAircrafts = await prisma.connectedAircraft.findMany({
where: {
stationId: stationId
? stationId
: {
in: mission.missionStationIds,
},
logoutTime: null,
},
include: {
Station: true,
},
});
for (const aircraft of connectedAircrafts) {
console.log(`Sending mission to: station:${aircraft.stationId}`);
io.to(`station:${aircraft.stationId}`).emit("mission-alert", {
...mission,
Stations,
});
const user = await prisma.user.findUnique({
where: { id: aircraft.userId },
});
if (!user) continue;
if (user.settingsNtfyRoom) {
await sendNtfyMission(
mission,
Stations,
aircraft.Station,
user.settingsNtfyRoom,
);
}
const existingMissionOnStationUser =
await prisma.missionOnStationUsers.findFirst({
where: {
missionId: mission.id,
userId: aircraft.userId,
stationId: aircraft.stationId,
},
});
if (!existingMissionOnStationUser)
await prisma.missionOnStationUsers.create({
data: {
missionId: mission.id,
userId: aircraft.userId,
stationId: aircraft.stationId,
},
});
}
// for statistics only
await prisma.missionsOnStations
.createMany({
data: mission.missionStationIds.map((stationId) => ({
missionId: mission.id,
stationId,
})),
})
.catch(() => {
// Ignore if the entry already exists
});
await prisma.mission.update({
where: { id: Number(id) },
data: {
state: "running",
},
});
res.status(200).json({
message: `Einsatz gesendet (${connectedAircrafts.length} Nutzer) `,
});
io.to("dispatchers").emit("update-mission", mission);
} catch (error) {
console.error(error);
res.status(500).json({ error: "Failed to send mission" });
}
});
export default router;