From b96fb0d0e477b754d90f5e0bccaf704fd0ddfcc5 Mon Sep 17 00:00:00 2001 From: Hymmel Date: Wed, 21 Jan 2026 11:50:23 +0100 Subject: [PATCH] womp womp --- .../ticketsystem/service/AuthService.java | 9 ++- .../components/dashboard/admin-dashboard.tsx | 3 +- Frontend/components/tickets/ticket-table.tsx | 24 ++++++- Frontend/lib/auth-context.tsx | 70 +++++++++++-------- 4 files changed, 74 insertions(+), 32 deletions(-) diff --git a/Backend/src/main/java/de/itsolutions/ticketsystem/service/AuthService.java b/Backend/src/main/java/de/itsolutions/ticketsystem/service/AuthService.java index 1b93bd2..6085a64 100644 --- a/Backend/src/main/java/de/itsolutions/ticketsystem/service/AuthService.java +++ b/Backend/src/main/java/de/itsolutions/ticketsystem/service/AuthService.java @@ -39,7 +39,14 @@ public class AuthService { user.setName(request.getFirstname() + " " + request.getLastname()); // Populate legacy/fallback fields user.setEmail(request.getEmail()); user.setPassword(passwordEncoder.encode(request.getPassword())); - user.setRole(request.getRole()); + user.setPassword(passwordEncoder.encode(request.getPassword())); + + // Auto-assign ADMIN role to the very first user + if (userRepository.count() == 0) { + user.setRole("ADMIN"); + } else { + user.setRole(request.getRole()); + } if ("RAUMBETREUER".equals(request.getRole()) && request.getRoomIds() != null) { List rooms = roomRepository.findAllById(request.getRoomIds()); diff --git a/Frontend/components/dashboard/admin-dashboard.tsx b/Frontend/components/dashboard/admin-dashboard.tsx index 3689399..8c17393 100644 --- a/Frontend/components/dashboard/admin-dashboard.tsx +++ b/Frontend/components/dashboard/admin-dashboard.tsx @@ -7,7 +7,7 @@ import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/com import { ShieldAlert, Users } from "lucide-react" export function AdminDashboard() { - const { tickets, updateTicketStatus, authHeader } = useAuth() + const { tickets, updateTicketStatus, deleteTicket, authHeader } = useAuth() const API_URL = process.env.NEXT_PUBLIC_API_URL + "/api" // Admin sees all tickets (logic handled in Backend/TicketService) @@ -62,6 +62,7 @@ export function AdminDashboard() { tickets={tickets} showStatusUpdate onStatusUpdate={updateTicketStatus} + onDeleteTicket={deleteTicket} /> diff --git a/Frontend/components/tickets/ticket-table.tsx b/Frontend/components/tickets/ticket-table.tsx index 597ba12..939742a 100644 --- a/Frontend/components/tickets/ticket-table.tsx +++ b/Frontend/components/tickets/ticket-table.tsx @@ -11,7 +11,8 @@ import { SelectTrigger, SelectValue, } from "@/components/ui/select" -import { ArrowUpDown, ArrowDown, ArrowUp, Calendar, MapPin, FileText } from "lucide-react" +import { ArrowUpDown, ArrowDown, ArrowUp, Calendar, MapPin, FileText, Trash2 } from "lucide-react" +import { Button } from "@/components/ui/button" import { Input } from "@/components/ui/input" import { Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle } from "@/components/ui/dialog" import { TicketComments } from "./ticket-comments" @@ -20,11 +21,12 @@ interface TicketTableProps { tickets: Ticket[] showStatusUpdate?: boolean onStatusUpdate?: (ticketId: number, status: TicketStatus) => void + onDeleteTicket?: (ticketId: number) => void } type SortDirection = "asc" | "desc" -export function TicketTable({ tickets, showStatusUpdate = false, onStatusUpdate }: TicketTableProps) { +export function TicketTable({ tickets, showStatusUpdate = false, onStatusUpdate, onDeleteTicket }: TicketTableProps) { const [sortConfig, setSortConfig] = useState<{ key: keyof Ticket | "room" | "owner"; direction: SortDirection }>({ key: "createdAt", direction: "desc" }) const [search, setSearch] = useState("") const [statusFilter, setStatusFilter] = useState("ALL") @@ -133,6 +135,7 @@ export function TicketTable({ tickets, showStatusUpdate = false, onStatusUpdate handleSort("status")}> Status {sortConfig.key === "status" && (sortConfig.direction === "asc" ? : )} + {onDeleteTicket && } @@ -174,6 +177,23 @@ export function TicketTable({ tickets, showStatusUpdate = false, onStatusUpdate )} + {onDeleteTicket && ( + e.stopPropagation()}> + + + )} )) )} diff --git a/Frontend/lib/auth-context.tsx b/Frontend/lib/auth-context.tsx index 7568e41..3a9275d 100644 --- a/Frontend/lib/auth-context.tsx +++ b/Frontend/lib/auth-context.tsx @@ -16,6 +16,7 @@ interface AuthContextType { logout: () => void createTicket: (ticket: { roomId: number; title: string; description: string }) => Promise updateTicketStatus: (ticketId: number, status: TicketStatus) => Promise + deleteTicket: (ticketId: number) => Promise updateRooms: (roomIds: number[]) => Promise } @@ -176,33 +177,46 @@ export function AuthProvider({ children }: { children: ReactNode }) { } } catch (e) { console.error(e) + const deleteTicket = useCallback(async (ticketId: number) => { + if (!authHeader) return + try { + const res = await fetch(`${API_URL}/tickets/${ticketId}`, { + method: "DELETE", + headers: { "Authorization": authHeader } + }) + if (res.ok) { + fetchTickets(authHeader) + } + } catch (e) { + console.error(e) + } + }, [authHeader, fetchTickets]) + + return ( + + {children} + + ) } - }, [authHeader, fetchTickets]) - return ( - - {children} - - ) -} - -export function useAuth() { - const context = useContext(AuthContext) - if (!context) { - throw new Error("useAuth must be used within an AuthProvider") - } - return context -} + export function useAuth() { + const context = useContext(AuthContext) + if (!context) { + throw new Error("useAuth must be used within an AuthProvider") + } + return context + }