dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $dashboards = []; foreach ($availableDashboards as $dashboard) { $dashboard->initializeWidgets($request); $dashboards[] = $dashboard->getTransferData(); } return new JsonResponse($dashboards); } public function addDashboard(ServerRequestInterface $request): ResponseInterface { $presetIdentifier = (string)($request->getParsedBody()['preset'] ?? ''); $dashboardPreset = $this->dashboardPresetRegistry->getDashboardPresets()[$presetIdentifier] ?? null; if (!$dashboardPreset instanceof DashboardPreset) { return new JsonResponse([ 'status' => 'error', 'message' => 'Invalid dashboard preset!', ]); } $dashboardEntity = $this->dashboardRepository->create( $dashboardPreset, (int)$this->getBackendUser()->user['uid'], (string)($request->getParsedBody()['title'] ?? '') ); $dashboardEntity->initializeWidgets($request); return new JsonResponse([ 'status' => 'ok', 'dashboard' => $dashboardEntity->getTransferData(), ]); } public function editDashboard(ServerRequestInterface $request): ResponseInterface { $dashboardIdentifier = (string)($request->getParsedBody()['identifier'] ?? ''); $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $dashboardEntity = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); if (!in_array($dashboardEntity, $availableDashboards)) { return new JsonResponse([ 'status' => 'error', 'message' => 'Dashboard is not available!', ]); } $this->dashboardRepository->updateDashboardSettings( $dashboardIdentifier, [ 'title' => (string)($request->getParsedBody()['title'] ?? ''), ] ); // Fetch updated Dashboard $dashboardEntity = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); $dashboardEntity->initializeWidgets($request); return new JsonResponse([ 'status' => 'ok', 'dashboard' => $dashboardEntity->getTransferData(), ]); } public function updateDashboard(ServerRequestInterface $request): ResponseInterface { $dashboardIdentifier = (string)($request->getParsedBody()['identifier'] ?? ''); $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $dashboardEntity = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); if (!in_array($dashboardEntity, $availableDashboards)) { return new JsonResponse([ 'status' => 'error', 'message' => 'Dashboard is not available!', ]); } $widgets = $request->getParsedBody()['widgets'] ?? []; $data = []; foreach ($widgets as $widget) { $data[$widget['identifier']] = [ 'identifier' => $widget['type'], ]; } // positions $widgetPositions = $request->getParsedBody()['widgetPositions'] ?? []; foreach ($widgetPositions as $columnCount => $widgets) { foreach ($widgets as $widget) { if (!isset($widget['identifier']) || !isset($widget['height']) || !isset($widget['width']) || !isset($widget['x']) || !isset($widget['y'])) { return new JsonResponse([ 'status' => 'error', 'message' => 'Invalid widget positions!', ]); } $identifier = $widget['identifier'] ?? ''; unset($widget['identifier']); $data[$identifier]['positions'][$columnCount] = array_map('intval', $widget); } } // settings $dashboardEntity->initializeWidgets($request); foreach ($widgets as $widget) { $dashboardWidget = $dashboardEntity->getWidget($widget['identifier']); if ($dashboardWidget) { $data[$widget['identifier']]['settings'] = $dashboardWidget->getRawConfig()['settings'] ?? []; } } $this->dashboardRepository->updateWidgetConfig($dashboardEntity, $data); // Fetch updated Dashboard $dashboardEntity = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); $dashboardEntity->initializeWidgets($request); return new JsonResponse([ 'status' => 'ok', 'dashboard' => $dashboardEntity->getTransferData(), ]); } public function deleteDashboard(ServerRequestInterface $request): ResponseInterface { $dashboardIdentifier = (string)($request->getParsedBody()['identifier'] ?? ''); $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $dashboard = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); if (!in_array($dashboard, $availableDashboards)) { return new JsonResponse([ 'status' => 'error', 'message' => 'Dashboard is not available!', ]); } $this->dashboardRepository->delete($dashboard); return new JsonResponse([ 'status' => 'ok', ]); } public function getPresets(ServerRequestInterface $request): ResponseInterface { $presets = $this->dashboardPresetRegistry->getDashboardPresets(); return new JsonResponse($presets); } public function getCategories(ServerRequestInterface $request): ResponseInterface { $widgetGroups = $this->widgetGroupInitializationService->buildWidgetGroupsConfiguration(); return new JsonResponse($widgetGroups); } public function getWidget(ServerRequestInterface $request): ResponseInterface { $widgetIdentifier = (string)($request->getQueryParams()['widget'] ?? ''); $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $widgets = []; foreach ($availableDashboards as $dashboard) { $dashboard->initializeWidgets($request); foreach ($dashboard->getWidgets() as $dashboardEntry) { $widgets[$dashboardEntry->getIdentifier()] = $dashboardEntry; } } $dashboardWidget = $widgets[$widgetIdentifier] ?? null; if ($dashboardWidget === null) { return new JsonResponse([ 'status' => 'error', 'message' => 'Widget does not exist!', ]); } return new JsonResponse([ 'status' => 'ok', 'widget' => $dashboardWidget->getTransferWidgetData()->jsonSerialize(), ]); } public function getWidgetSettings(ServerRequestInterface $request): ResponseInterface { $widgetIdentifier = (string)($request->getQueryParams()['widget'] ?? ''); $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $widgets = []; foreach ($availableDashboards as $dashboard) { $dashboard->initializeWidgets($request); foreach ($dashboard->getWidgets() as $dashboardEntry) { $widgets[$dashboardEntry->getIdentifier()] = $dashboardEntry; } } $dashboardWidget = $widgets[$widgetIdentifier] ?? null; if ($dashboardWidget === null) { return new JsonResponse([ 'status' => 'error', 'message' => 'Widget does not exist!', ]); } $categories = [ new Category( key: $dashboardWidget->getType(), label: $this->getLanguageService()->sL($dashboardWidget->getTitle()), description: $this->getLanguageService()->sL($dashboardWidget->getDescription()), icon: $dashboardWidget->getIconIdentifier(), settings: array_map( fn(SettingDefinition $definition): EditableSetting => new EditableSetting( definition: $this->resolveSettingLabels($definition), value: $dashboardWidget->getSettings()->get($definition->key), systemDefault: $definition->default, typeImplementation: $this->settingsTypeRegistry->get($definition->type)->getJavaScriptModule(), ), array_values(array_filter($dashboardWidget->getSettingsDefinitions(), fn(SettingDefinition $settingDefinition) => !$settingDefinition->readonly)) ), ), ]; return new JsonResponse([ 'status' => 'ok', 'categories' => json_encode($categories), ]); } public function updateWidgetSettings(ServerRequestInterface $request): ResponseInterface { // Check if identifier is available $widgetIdentifier = trim((string)($request->getParsedBody()['widget'] ?? '')); if ($widgetIdentifier === '') { return new JsonResponse([ 'status' => 'error', 'message' => 'Widget is not available!', ]); } // Check for widget $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $targetDashboard = null; $targetWidget = null; foreach ($availableDashboards as $dashboard) { $dashboard->initializeWidgets($request); if ($dashboard->getWidget($widgetIdentifier)) { $targetDashboard = $dashboard; $targetWidget = $dashboard->getWidget($widgetIdentifier); break; } } if ($targetWidget === null) { return new JsonResponse([ 'status' => 'error', 'message' => 'Widget does not exist!', ]); } if ($targetDashboard === null) { return new JsonResponse([ 'status' => 'error', 'message' => 'Dashboard does not exist!', ]); } $rawSettings = $request->getParsedBody()['settings'] ?? []; $widgetData = []; foreach ($targetDashboard->getWidgets() as $widget) { $widgetData[$widget->getIdentifier()] = $widget->getRawConfig(); if ($targetWidget->getIdentifier() === $widget->getIdentifier()) { $currentSettings = $widget->getRawConfig()['settings'] ?? []; $newSettings = $this->widgetSettingsFactory->createSettingsFromFormData($rawSettings, $widget->getSettingsDefinitions()); $defaultSettings = $this->widgetSettingsFactory->createSettings($widget->getType(), [], $widget->getSettingsDefinitions()); $diff = SettingsDiff::create( $currentSettings, $newSettings, $defaultSettings, ); if ($diff->changes === [] && $diff->deletions === []) { return new JsonResponse([ 'status' => 'info', 'message' => $this->getLanguageService()->sL('LLL:EXT:dashboard/Resources/Private/Language/locallang.xlf:widget.settings.unchanged'), ]); } $widgetData[$widget->getIdentifier()]['settings'] = $diff->settings; } } $this->dashboardRepository->updateWidgetConfig($targetDashboard, $widgetData); // Fetch updated Dashboard $dashboardEntity = $this->dashboardRepository->getDashboardByIdentifier($targetDashboard->getIdentifier()); $dashboardEntity->initializeWidgets($request); $returnWidget = $dashboardEntity->getWidget($targetWidget->getIdentifier()); if ($returnWidget === null) { return new JsonResponse([ 'status' => 'error', 'message' => 'Widget does not exist!', ]); } return new JsonResponse([ 'status' => 'ok', ]); } public function addWidget(ServerRequestInterface $request): ResponseInterface { $dashboardIdentifier = (string)($request->getParsedBody()['dashboard'] ?? ''); $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $dashboard = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); if (!in_array($dashboard, $availableDashboards)) { return new JsonResponse([ 'status' => 'error', 'message' => 'Dashboard is not available!', ]); } $widgetType = (string)($request->getParsedBody()['type'] ?? ''); if ($widgetType === '') { throw new \InvalidArgumentException('Argument "widget" not set.', 1714987384); } $widgets = $dashboard->getWidgetConfig(); $widgetIdentifier = sha1($widgetType . '-' . time()); $widgets[$widgetIdentifier] = ['identifier' => $widgetType]; $this->dashboardRepository->updateWidgetConfig($dashboard, $widgets); // Fetch updated Dashboard $dashboard = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); $dashboard->initializeWidgets($request); $widgets = []; foreach ($dashboard->getWidgets() as $dashboardEntry) { $widgets[$dashboardEntry->getIdentifier()] = $dashboardEntry; } $dashboardWidget = $widgets[$widgetIdentifier] ?? null; if ($dashboardWidget === null) { return new JsonResponse([ 'status' => 'error', 'message' => 'Widget is not available!', ]); } return new JsonResponse([ 'status' => 'ok', 'widget' => $dashboardWidget->getTransferWidgetData()->jsonSerialize(), ]); } public function removeWidget(ServerRequestInterface $request): ResponseInterface { $dashboardIdentifier = (string)($request->getParsedBody()['dashboard'] ?? ''); $availableDashboards = $this->dashboardRepository->getDashboardsForUser($this->getBackendUser()->getUserId()); $dashboard = $this->dashboardRepository->getDashboardByIdentifier($dashboardIdentifier); if (!in_array($dashboard, $availableDashboards)) { return new JsonResponse([ 'status' => 'error', 'message' => 'Dashboard is not available!', ]); } $widgetIdentifier = (string)($request->getParsedBody()['identifier'] ?? ''); $widgets = $dashboard->getWidgetConfig(); if ($widgetIdentifier === '' || !array_key_exists($widgetIdentifier, $widgets)) { return new JsonResponse([ 'status' => 'error', 'message' => 'Widget is not available!', ]); } unset($widgets[$widgetIdentifier]); $this->dashboardRepository->updateWidgetConfig($dashboard, $widgets); return new JsonResponse([ 'status' => 'ok', ]); } private function resolveSettingLabels(SettingDefinition $definition): SettingDefinition { $languageService = $this->getLanguageService(); return new SettingDefinition(...[ ...get_object_vars($definition), 'label' => $languageService->sL($definition->label), 'description' => $definition->description !== null ? $languageService->sL($definition->description) : null, 'enum' => array_map(static fn(string $label): string => $languageService->sL($label), $definition->enum), ]); } protected function getLanguageService(): LanguageService { return $GLOBALS['LANG']; } protected function getBackendUser(): BackendUserAuthentication { return $GLOBALS['BE_USER']; } }