calendar and vehicle booking rework

This commit is contained in:
Matthias Hochmeister
2026-03-25 16:09:16 +01:00
parent 7cc4facc11
commit 7dab359448
7 changed files with 25 additions and 24 deletions

View File

@@ -226,8 +226,8 @@ class BookingController {
const isOwner = booking.gebucht_von === req.user!.id;
const groups: string[] = req.user?.groups ?? [];
const isAdmin = groups.includes('dashboard_admin');
const canCancelOwn = isAdmin || permissionService.hasPermission(groups, 'kalender:manage_bookings');
const canCancelAny = isAdmin || permissionService.hasPermission(groups, 'kalender:manage_bookings');
const canCancelOwn = isAdmin || permissionService.hasPermission(groups, 'fahrzeugbuchungen:manage');
const canCancelAny = isAdmin || permissionService.hasPermission(groups, 'fahrzeugbuchungen:manage');
if (!(isOwner && canCancelOwn) && !canCancelAny) {
res.status(403).json({ success: false, message: 'Keine Berechtigung' });

View File

@@ -18,15 +18,15 @@ router.get('/calendar-token', authenticate, bookingController.getCalendarToken.b
// ── Write operations ──────────────────────────────────────────────────────────
router.post('/', authenticate, requirePermission('kalender:manage_bookings'), bookingController.create.bind(bookingController));
router.patch('/:id', authenticate, requirePermission('kalender:manage_bookings'), bookingController.update.bind(bookingController));
router.post('/', authenticate, requirePermission('fahrzeugbuchungen:create'), bookingController.create.bind(bookingController));
router.patch('/:id', authenticate, requirePermission('fahrzeugbuchungen:manage'), bookingController.update.bind(bookingController));
// Soft-cancel (sets abgesagt=TRUE) — creator or bookings:write
router.delete('/:id', authenticate, bookingController.cancel.bind(bookingController));
router.patch('/:id/cancel', authenticate, bookingController.cancel.bind(bookingController));
// Hard-delete (admin only)
router.delete('/:id/force', authenticate, requirePermission('kalender:manage_bookings'), bookingController.hardDelete.bind(bookingController));
router.delete('/:id/force', authenticate, requirePermission('fahrzeugbuchungen:manage'), bookingController.hardDelete.bind(bookingController));
// ── Single booking read — after specific routes to avoid path conflicts ───────

View File

@@ -9,7 +9,7 @@ const router = Router();
router.get(
'/',
authenticate,
requirePermission('kalender:view_bookings'),
requirePermission('fahrzeugbuchungen:view'),
buchungskategorieController.list.bind(buchungskategorieController)
);
@@ -17,7 +17,7 @@ router.get(
router.get(
'/active',
authenticate,
requirePermission('kalender:view_bookings'),
requirePermission('fahrzeugbuchungen:view'),
buchungskategorieController.listActive.bind(buchungskategorieController)
);
@@ -25,7 +25,7 @@ router.get(
router.post(
'/',
authenticate,
requirePermission('kalender:manage_bookings'),
requirePermission('fahrzeugbuchungen:manage'),
buchungskategorieController.create.bind(buchungskategorieController)
);
@@ -33,7 +33,7 @@ router.post(
router.patch(
'/:id',
authenticate,
requirePermission('kalender:manage_bookings'),
requirePermission('fahrzeugbuchungen:manage'),
buchungskategorieController.update.bind(buchungskategorieController)
);
@@ -41,7 +41,7 @@ router.patch(
router.delete(
'/:id',
authenticate,
requirePermission('kalender:manage_bookings'),
requirePermission('fahrzeugbuchungen:manage'),
buchungskategorieController.deactivate.bind(buchungskategorieController)
);
@@ -49,7 +49,7 @@ router.delete(
router.delete(
'/:id/permanent',
authenticate,
requirePermission('kalender:manage_bookings'),
requirePermission('fahrzeugbuchungen:manage'),
buchungskategorieController.remove.bind(buchungskategorieController)
);

View File

@@ -14,11 +14,11 @@ const DEFAULT_GROUP_HIERARCHY: Record<string, string[]> = {
const DEFAULT_PERMISSION_DEPS: Record<string, string[]> = {
'kalender:create': ['kalender:view'],
'kalender:view_bookings': ['kalender:view'],
'kalender:manage_bookings': ['kalender:view', 'kalender:view_bookings'],
'kalender:widget_events': ['kalender:view'],
'kalender:widget_bookings': ['kalender:view'],
'kalender:widget_quick_add': ['kalender:view', 'kalender:create'],
'fahrzeugbuchungen:create': ['fahrzeugbuchungen:view'],
'fahrzeugbuchungen:manage': ['fahrzeugbuchungen:view', 'fahrzeugbuchungen:create'],
'fahrzeugbuchungen:widget': ['fahrzeugbuchungen:view'],
'fahrzeuge:create': ['fahrzeuge:view'],
'fahrzeuge:change_status': ['fahrzeuge:view'],
'fahrzeuge:manage_maintenance': ['fahrzeuge:view'],

View File

@@ -27,6 +27,7 @@ import {
ExpandLess,
LocalShipping,
BugReport,
BookOnline,
} from '@mui/icons-material';
import { useNavigate, useLocation } from 'react-router-dom';
import { useQuery } from '@tanstack/react-query';
@@ -49,11 +50,6 @@ interface NavigationItem {
permission?: string;
}
const kalenderSubItems: SubItem[] = [
{ text: 'Veranstaltungen', path: '/kalender' },
{ text: 'Fahrzeugbuchungen', path: '/fahrzeugbuchungen' },
];
const adminSubItems: SubItem[] = [
{ text: 'Services', path: '/admin?tab=0' },
{ text: 'System', path: '/admin?tab=1' },
@@ -77,9 +73,14 @@ const baseNavigationItems: NavigationItem[] = [
text: 'Kalender',
icon: <CalendarMonth />,
path: '/kalender',
subItems: kalenderSubItems,
permission: 'kalender:view',
},
{
text: 'Fahrzeugbuchungen',
icon: <BookOnline />,
path: '/fahrzeugbuchungen',
permission: 'fahrzeugbuchungen:view',
},
{
text: 'Fahrzeuge',
icon: <DirectionsCar />,

View File

@@ -170,7 +170,7 @@ function Dashboard() {
</Fade>
)}
{hasPermission('kalender:view_bookings') && widgetVisible('vehicleBookingList') && (
{hasPermission('fahrzeugbuchungen:view') && widgetVisible('vehicleBookingList') && (
<Fade in={!dataLoading} timeout={600} style={{ transitionDelay: '520ms' }}>
<Box>
<VehicleBookingListWidget />
@@ -178,7 +178,7 @@ function Dashboard() {
</Fade>
)}
{hasPermission('kalender:manage_bookings') && widgetVisible('vehicleBooking') && (
{hasPermission('fahrzeugbuchungen:manage') && widgetVisible('vehicleBooking') && (
<Fade in={!dataLoading} timeout={600} style={{ transitionDelay: '560ms' }}>
<Box>
<VehicleBookingQuickAddWidget />

View File

@@ -98,8 +98,8 @@ function FahrzeugBuchungen() {
const navigate = useNavigate();
const queryClient = useQueryClient();
const canCreate = hasPermission('kalender:create');
const canManage = hasPermission('kalender:manage_bookings');
const canCreate = hasPermission('fahrzeugbuchungen:create');
const canManage = hasPermission('fahrzeugbuchungen:manage');
const [tabIndex, setTabIndex] = useState(0);