aboutsummaryrefslogtreecommitdiffstats
path: root/apps/dashboard/lib
diff options
context:
space:
mode:
authorRichard Steinmetz <richard@steinmetz.cloud>2023-08-17 15:09:30 +0200
committerJoas Schilling <coding@schilljs.com>2023-08-22 08:36:53 +0200
commit6982597b6a6d319dacfbe3bee2edd2a39b3d6d68 (patch)
tree9a3cfc98c5ce08542e204ef37365491fa0a0404e /apps/dashboard/lib
parent82835eaa4623180c41dad927b0ac1db1ed449362 (diff)
downloadnextcloud-server-6982597b6a6d319dacfbe3bee2edd2a39b3d6d68.tar.gz
nextcloud-server-6982597b6a6d319dacfbe3bee2edd2a39b3d6d68.zip
feat(dashboard): implement widget item api v2
This API enables the dashboard to render all widgets from the API data alone without having apps to provide their own bundles. This saves a lot of traffic and execution time as a lot less javascript has to be parsed on the frontend. Signed-off-by: Richard Steinmetz <richard@steinmetz.cloud>
Diffstat (limited to 'apps/dashboard/lib')
-rw-r--r--apps/dashboard/lib/Controller/DashboardApiController.php72
-rw-r--r--apps/dashboard/lib/ResponseDefinitions.php10
2 files changed, 72 insertions, 10 deletions
diff --git a/apps/dashboard/lib/Controller/DashboardApiController.php b/apps/dashboard/lib/Controller/DashboardApiController.php
index df1c75e4b68..8855bf71700 100644
--- a/apps/dashboard/lib/Controller/DashboardApiController.php
+++ b/apps/dashboard/lib/Controller/DashboardApiController.php
@@ -7,6 +7,7 @@ declare(strict_types=1);
*
* @author Julien Veyssier <eneiluj@posteo.net>
* @author Kate Döen <kate.doeen@nextcloud.com>
+ * @author Richard Steinmetz <richard@steinmetz.cloud>
*
* @license GNU AGPL version 3 or any later version
*
@@ -35,6 +36,7 @@ use OCP\Dashboard\IButtonWidget;
use OCP\Dashboard\IIconWidget;
use OCP\Dashboard\IOptionWidget;
use OCP\Dashboard\IManager;
+use OCP\Dashboard\IReloadableWidget;
use OCP\Dashboard\IWidget;
use OCP\Dashboard\Model\WidgetButton;
use OCP\Dashboard\Model\WidgetOptions;
@@ -42,11 +44,14 @@ use OCP\IConfig;
use OCP\IRequest;
use OCP\Dashboard\IAPIWidget;
+use OCP\Dashboard\IAPIWidgetV2;
use OCP\Dashboard\Model\WidgetItem;
+use OCP\Dashboard\Model\WidgetItems;
/**
* @psalm-import-type DashboardWidget from ResponseDefinitions
* @psalm-import-type DashboardWidgetItem from ResponseDefinitions
+ * @psalm-import-type DashboardWidgetItems from ResponseDefinitions
*/
class DashboardApiController extends OCSController {
@@ -72,6 +77,24 @@ class DashboardApiController extends OCSController {
}
/**
+ * @param string[] $widgetIds Limit widgets to given ids
+ * @return IWidget[]
+ */
+ private function getShownWidgets(array $widgetIds): array {
+ if (empty($widgetIds)) {
+ $systemDefault = $this->config->getAppValue('dashboard', 'layout', 'recommendations,spreed,mail,calendar');
+ $widgetIds = explode(',', $this->config->getUserValue($this->userId, 'dashboard', 'layout', $systemDefault));
+ }
+
+ return array_filter(
+ $this->dashboardManager->getWidgets(),
+ static function (IWidget $widget) use ($widgetIds) {
+ return in_array($widget->getId(), $widgetIds);
+ },
+ );
+ }
+
+ /**
* @NoAdminRequired
* @NoCSRFRequired
*
@@ -83,18 +106,11 @@ class DashboardApiController extends OCSController {
* @return DataResponse<Http::STATUS_OK, array<string, DashboardWidgetItem[]>, array{}>
*/
public function getWidgetItems(array $sinceIds = [], int $limit = 7, array $widgets = []): DataResponse {
- $showWidgets = $widgets;
$items = [];
-
- if (empty($showWidgets)) {
- $systemDefault = $this->config->getAppValue('dashboard', 'layout', 'recommendations,spreed,mail,calendar');
- $showWidgets = explode(',', $this->config->getUserValue($this->userId, 'dashboard', 'layout', $systemDefault));
- }
-
- $widgets = $this->dashboardManager->getWidgets();
+ $widgets = $this->getShownWidgets($widgets);
foreach ($widgets as $widget) {
- if ($widget instanceof IAPIWidget && in_array($widget->getId(), $showWidgets)) {
- $items[$widget->getId()] = array_map(function (WidgetItem $item) {
+ if ($widget instanceof IAPIWidget) {
+ $items[$widget->getId()] = array_map(static function (WidgetItem $item) {
return $item->jsonSerialize();
}, $widget->getItems($this->userId, $sinceIds[$widget->getId()] ?? null, $limit));
}
@@ -104,6 +120,31 @@ class DashboardApiController extends OCSController {
}
/**
+ * @NoAdminRequired
+ * @NoCSRFRequired
+ *
+ * Get the items for the widgets
+ *
+ * @param array<string, string> $sinceIds Array indexed by widget Ids, contains date/id from which we want the new items
+ * @param int $limit Limit number of result items per widget
+ * @param string[] $widgets Limit results to specific widgets
+ * @return DataResponse<Http::STATUS_OK, array<string, DashboardWidgetItems>, array{}>
+ */
+ public function getWidgetItemsV2(array $sinceIds = [], int $limit = 7, array $widgets = []): DataResponse {
+ $items = [];
+ $widgets = $this->getShownWidgets($widgets);
+ foreach ($widgets as $widget) {
+ if ($widget instanceof IAPIWidgetV2) {
+ $items[$widget->getId()] = $widget
+ ->getItemsV2($this->userId, $sinceIds[$widget->getId()] ?? null, $limit)
+ ->jsonSerialize();
+ }
+ }
+
+ return new DataResponse($items);
+ }
+
+ /**
* Get the widgets
*
* @NoAdminRequired
@@ -124,6 +165,8 @@ class DashboardApiController extends OCSController {
'icon_url' => ($widget instanceof IIconWidget) ? $widget->getIconUrl() : '',
'widget_url' => $widget->getUrl(),
'item_icons_round' => $options->withRoundItemIcons(),
+ 'item_api_versions' => [],
+ 'reload_interval' => 0,
];
if ($widget instanceof IButtonWidget) {
$data += [
@@ -136,6 +179,15 @@ class DashboardApiController extends OCSController {
}, $widget->getWidgetButtons($this->userId)),
];
}
+ if ($widget instanceof IReloadableWidget) {
+ $data['reload_interval'] = $widget->getReloadInterval();
+ }
+ if ($widget instanceof IAPIWidget) {
+ $data['item_api_versions'][] = 1;
+ }
+ if ($widget instanceof IAPIWidgetV2) {
+ $data['item_api_versions'][] = 2;
+ }
return $data;
}, $widgets);
diff --git a/apps/dashboard/lib/ResponseDefinitions.php b/apps/dashboard/lib/ResponseDefinitions.php
index 1c40f251f2a..b35531be2a7 100644
--- a/apps/dashboard/lib/ResponseDefinitions.php
+++ b/apps/dashboard/lib/ResponseDefinitions.php
@@ -5,6 +5,7 @@ declare(strict_types=1);
* @copyright Copyright (c) 2023 Kate Döen <kate.doeen@nextcloud.com>
*
* @author Kate Döen <kate.doeen@nextcloud.com>
+ * @author Richard Steinmetz <richard@steinmetz.cloud>
*
* @license GNU AGPL version 3 or any later version
*
@@ -34,6 +35,8 @@ namespace OCA\Dashboard;
* icon_url: string,
* widget_url: ?string,
* item_icons_round: bool,
+ * item_api_versions: int[],
+ * reload_interval: int,
* buttons?: array{
* type: string,
* text: string,
@@ -46,8 +49,15 @@ namespace OCA\Dashboard;
* title: string,
* link: string,
* iconUrl: string,
+ * overlayIconUrl: string,
* sinceId: string,
* }
+ *
+ * @psalm-type DashboardWidgetItems = array{
+ * items: DashboardWidgetItem[],
+ * emptyContentMessage: string,
+ * halfEmptyContentMessage: string,
+ * }
*/
class ResponseDefinitions {
}