Презентация

На этой странице описаны компоненты, которые можно использовать для создания представления виджета. Представление виджета - это часть виджета, которая получает данные в соответствии со своей конфигурацией и отображает их на информационной панели в контейнере.

Представление презентации состоит из трех частей:

Действие виджета

Класс действий виджета (WidgetView) содержит методы для работы с виджетами в режиме просмотра презентации. Большинство действий виджетов используют и/или расширяют класс контроллера по умолчанию CControllerDashboardWidgetView.

Класс действия виджета должен находиться в каталоге actions и указываться в параметре actions (actions/widget.{id}.view/class) в файле manifest.json.

Пример actions/WidgetView.php (реализован в родном для Zabbix виджете Информация о системе)

class WidgetView extends CControllerDashboardWidgetView {
       
           protected function doAction(): void {
               $this->setResponse(new CControllerResponseData([
                   'name' => $this->getInput('name', $this->widget->getDefaultName()),
                   'system_info' => CSystemInfoHelper::getData(),
                   'info_type' => $this->fields_values['info_type'],
                   'user_type' => CWebUser::getType(),
                   'user' => [
                       'debug_mode' => $this->getDebugMode()
                   ]
               ]));
           }
       }

Виджет

Класс представления виджета (CWidgetView) отвечает за построение представления виджета.

Класс представления виджета должен находиться в каталоге views. Если файл, содержащий класс представления виджета, имеет имя, отличное от имени по умолчанию (widget.view.php), то его необходимо указать в файле manifest.json actions параметр (actions/widget.{id}.view/view).

пример views/widget.view.php

<?php
       
       /**
        * My custom widget view.
        *
        * @var CView $this
        * @var array $data
        */
       
       (new CWidgetView($data))
           ->addItem(
               new CTag('h1', true, $data['name'])
           )
           ->show();

JavaScript

Класс JavaScript отвечает за определение поведения виджета, например, обновление данных виджета, изменение размера виджета, отображение элементов виджета и т. д.

Все операции JavaScript используют и/или расширяют базовый класс JavaScript всех виджетов панели - CWidget. Класс CWidget содержит набор методов с реализацией по умолчанию для поведения виджета. В зависимости от сложности виджета эти методы можно использовать как есть или расширить.

Класс CWidget содержит следующие методы:

  • Методы, определяющие жизненный цикл виджета: onInitialize(), onStart(), onActivate(), onDeactivate(), onDestroy(), onEdit().
  • Методы, обрабатывающие обновление и отображение данных виджета: promiseUpdate(), getUpdateRequestData(), processUpdateResponse(response), processUpdateErrorResponse(error), setContents(response).
  • Методы, изменяющие внешний вид виджета: onResize(), hasPadding().

Класс JavaScript должен находиться в каталоге assets/js и указываться в параметре assets (assets/js) в manifest.json файл.

Методы жизненного цикла

Методы жизненного цикла виджета вызываются панелью и на разных этапах жизненного цикла виджета во время его существования на панели.

Метод _init() определяет исходное состояние и/или значения виджета без выполнения каких-либо манипуляций с HTML или данными. Этот метод вызывается при создании виджета (создается экземпляр объекта виджета), обычно путем добавления виджета на страницу панели или загрузки страницы панели.

Пример:

_init() {
           super._init();
       
           this._time_offset = 0;
           this._interval_id = null;
           this._clock_type = CWidgetClock.TYPE_ANALOG;
           this._time_zone = null;
           this._show_seconds = true;
           this._time_format = 0;
           this._tzone_format = 0;
           this._show = [];
           this._has_contents = false;
           this._is_enabled = true;
       }

Метод _registerEvents() определяет HTML-структуру виджета, не выполняя никаких манипуляций с данными. Этот метод вызывается перед первой активацией страницы панели мониторинга, то есть до того, как панель мониторинга и ее виджеты полностью отобразятся пользователю.

Пример:

_registerEvents() {
           super._registerEvents();
       
           this._events.resize = () => {
               const padding = 25;
               const header_height = this._view_mode == ZBX_WIDGET_VIEW_MODE_HIDDEN_HEADER
                   ? 0
                   : this._content_header.offsetHeight;
       
               this._target.style.setProperty(
                   '--content-height',
                   `${this._cell_height * this._pos.height - padding * 2 - header_height}px`
               );
           }
       }

Метод _doActivate() делает виджет активным и интерактивным, включая настраиваемые прослушиватели событий (для реагирования на действия пользователя) и запуская цикл обновления виджета (для поддержания актуальности его содержимого). Этот метод вызывается при активации страницы информационной панели, то есть когда она полностью отображается в пользовательском интерфейсе.

Обратите внимание, что до вызова метода _doActivate() виджет находится в неактивном состоянии («WIDGET_STATE_INACTIVE»). После успешного вызова виджет переходит в активное состояние («WIDGET_STATE_ACTIVE»). В активном состоянии виджет реагирует, слушает события, периодически обновляет свое содержимое и может взаимодействовать с другими виджетами.

Пример:

_doActivate() {
           super._doActivate();
       
           if (this._has_contents) {
               this._activateContentsEvents();
           }
       }

Метод _doDeactivate() останавливает любую активность и интерактивность виджета, деактивируя пользовательские прослушиватели событий и останавливая цикл обновления виджета. Этот метод вызывается, когда страница панели деактивируется, то есть отключается или удаляется, или когда виджет удаляется со страницы панели.

Обратите внимание, что до вызова метода _doDeactivate() виджет находится в активном состоянии (WIDGET_STATE_ACTIVE). После успешного вызова виджет переходит в неактивное состояние («WIDGET_STATE_INACTIVE»).

Пример:

_doDeactivate() {
           super._doDeactivate();
       
           this._deactivateContentsEvents();
       }

Метод _doDestroy() выполняет задачи очистки перед удалением виджета с панели управления, что может включать в себя закрытие соединения с базой данных, которое было установлено во время инициализации виджета, очистка временных данных для освобождения системной памяти и предотвращения утечек ресурсов, отмена регистрации прослушивателей событий, связанных с событиями изменения размера или нажатиями кнопок, чтобы предотвратить ненужную обработку событий и утечки памяти и т. д. Этот метод вызывается при удалении виджета или страницы информационной панели, которая его содержит.

Обратите внимание, что перед вызовом метода _doDestroy() виджет в активном состоянии (WIDGET_STATE_ACTIVE) всегда деактивируется с помощью вызова метода _doDeactivate().

Пример:

_doDestroy() {
           super._doDestroy();
       
           if (this._filter_widget) {
               this._filter_widget.off(CWidgetMap.WIDGET_NAVTREE_EVENT_MARK, this._events.mark);
               this._filter_widget.off(CWidgetMap.WIDGET_NAVTREE_EVENT_SELECT, this._events.select);
           }
       }

Метод setEditMode() определяет внешний вид и поведение виджета при переходе панели управления в режим редактирования. Этот метод вызывается, когда панель мониторинга переходит в режим редактирования, обычно когда пользователь взаимодействует с кнопкой Редактировать виджета или кнопкой Редактировать панель панели мониторинга.

Пример:

setEditMode() {
           if (this._has_contents) {
               this._deactivateContentsEvents();
               this._removeTree();
           }
       
           super.setEditMode();
       
           if (this._has_contents && this._state === WIDGET_STATE_ACTIVE) {
               this._makeTree();
               this._activateTree();
               this._activateContentsEvents();
           }
       }
Методы обновления виджета

Методы процесса обновления виджета отвечают за получение обновленных данных с сервера Zabbix или любого другого источника данных и их отображение в виджете.

Метод _promiseUpdate() инициирует процесс обновления данных путем получения данных, обычно с помощью веб-запросов или вызовов API. Этот метод вызывается при отображении страницы панели и периодически после этого, пока страница панели не переключится на другую страницу панели.

Ниже приведен пример реализации по умолчанию метода _promiseUpdate(), используемого большинством родных виджетов Zabbix. В реализации по умолчанию метод _promiseUpdate() соответствует общему шаблону получения данных с сервера. Он создает новый объект Curl с соответствующим URL-адресом и параметрами запроса, отправляет запрос POST с помощью метода fetch() с объектом данных, созданным методом _getUpdateRequestData(), и обрабатывает ответ (или ответ об ошибке) с помощью _processUpdateResponse(response) или _processUpdateErrorResponse(error) соответственно. Эта реализация подходит для большинства виджетов, поскольку они обычно получают данные в формате JSON и обрабатывают их согласованным образом.

_promiseUpdate() {
           const curl = new Curl('zabbix.php');
       
           curl.setArgument('action', `widget.${this._type}.view`);
       
           return fetch(curl.getUrl(), {
               method: 'POST',
               headers: {'Content-Type': 'application/json'},
               body: JSON.stringify(this._getUpdateRequestData()),
               signal: this._update_abort_controller.signal
           })
               .then((response) => response.json())
               .then((response) => {
                   if ('error' in response) {
                       this._processUpdateErrorResponse(response.error);
       
                       return;
                   }
       
                   this._processUpdateResponse(response);
               });
       }

Метод _getUpdateRequestData() подготавливает данные запроса сервера для обновления виджета, собирая различные свойства и соответствующие им значения (идентификаторы виджета, настройки фильтра, временные диапазоны и т. д.) из состояния и конфигурации виджета, и создание объекта данных, который представляет необходимую информацию, подлежащую отправке на сервер в запросе на обновление. Этот метод вызывается только как часть метода _promiseUpdate() по умолчанию, то есть во время процесса обновления виджета.

Реализация по умолчанию:

_getUpdateRequestData() {
           return {
               templateid: this._dashboard.templateid ?? undefined,
               dashboardid: this._dashboard.dashboardid ?? undefined,
               widgetid: this._widgetid ?? undefined,
               name: this._name !== '' ? this._name : undefined,
               fields: Object.keys(this._fields).length > 0 ? this._fields : undefined,
               view_mode: this._view_mode,
               edit_mode: this._is_edit_mode ? 1 : 0,
               dynamic_hostid: this._dashboard.templateid !== null || this.supportsDynamicHosts()
                   ? (this._dynamic_hostid ?? undefined)
                   : undefined,
               ...this._content_size
           };
       }

Метод _processUpdateResponse(response) обрабатывает ответ, полученный от сервера после запроса на обновление, и, если процесс обновления прошел успешно и без ошибок, очищает данные виджета и отображает новое содержимое с помощью метода _setContents(). Этот метод вызывается только как часть метода _promiseUpdate() по умолчанию, то есть во время процесса обновления виджета.

Реализация по умолчанию:

_processUpdateResponse(response) {
           this._setContents({
               name: response.name,
               body: response.body,
               messages: response.messages,
               info: response.info,
               debug: response.debug
           });
       }

Метод _processUpdateErrorResponse(error) обрабатывает ответ, полученный от сервера после запроса на обновление, если ответ является ошибкой, и отображает сообщения об ошибках. Этот метод вызывается только как часть метода по умолчанию _promiseUpdate(), то есть во время процесса обновления виджета.

Реализация по умолчанию:

_processUpdateErrorResponse(error) {
           this._setErrorContents({error});
       }
       
       _setErrorContents({error}) {
           const message_box = makeMessageBox('bad', error.messages, error.title)[0];
       
           this._content_body.innerHTML = '';
           this._content_body.appendChild(message_box);
       
           this._removeInfoButtons();
       }

Метод _setContents() отображает содержимое виджета, если процесс обновления виджета прошел успешно и без ошибок, что может включать в себя манипулирование элементами DOM, обновление компонентов пользовательского интерфейса, применение стилей или форматирования и т. д. Этот метод вызывается только как часть метода _processUpdateResponse(response) по умолчанию, то есть в процессе обработки ответа, полученного от сервера после запроса на обновление.

Реализация по умолчанию:

_setContents({name, body, messages, info, debug}) {
           this._setHeaderName(name);
       
           this._content_body.innerHTML = '';
       
           if (messages !== undefined) {
               const message_box = makeMessageBox('bad', messages)[0];
       
               this._content_body.appendChild(message_box);
           }
       
           if (body !== undefined) {
               this._content_body.insertAdjacentHTML('beforeend', body);
           }
       
           if (debug !== undefined) {
               this._content_body.insertAdjacentHTML('beforeend', debug);
           }
       
           this._removeInfoButtons();
       
           if (info !== undefined) {
               this._addInfoButtons(info);
           }
       }
Методы модификации представления

Методы модификации представления виджета отвечают за изменение внешнего вида виджета.

Метод resize() отвечает за настройку визуальных элементов виджета в соответствии с новым размером виджета, которые могут включать перестановку элементов, настройку размеров элементов, усечение текста, реализацию отложенной загрузки для улучшения реагирования при изменении размера и т. д. Этот метод вызывается при изменении размера виджета, например, когда пользователь вручную изменяет размер виджета или когда изменяется размер окна браузера.

Пример:

resize() {
           if (this._state === WIDGET_STATE_ACTIVE) {
               this._startUpdating();
           }
       }

Метод _hasPadding() отвечает за применение вертикального заполнения шириной 8 пикселей в нижней части виджета, когда он настроен на показ заголовка. Этот метод вызывается, когда страница информационной панели активируется, то есть когда она становится отображаемой страницей в пользовательском интерфейсе.

Реализация по умолчанию:

_hasPadding() {
           return this._view_mode !== ZBX_WIDGET_VIEW_MODE_HIDDEN_HEADER;
       }

Для некоторых виджетов необходимо использовать все доступное пространство виджетов, например, для настройки собственного цвета фона. Ниже приведен пример реализации метода _hasPadding(), используемого в родном для Zabbix виджете значение элемента данных.

_hasPadding() {
           return false;
       }