Перейти к основному содержанию
`Ctrl`+`K`

# MDA-таблица

## Основные положения

`MDA-таблица` (Multi-Dimension Analysis) - средство, позволяющее реализовать список, управляемый пользователем с возможностью анализа данных и их группировки.

Основной особенностью `MDA-таблиц` является работа с данными вне базы данных. При первом запросе данных, будет выполнен запрос к базе данных, далее, если не изменялся порядок сортировки данных, то запросы к базе не выполняются.

Для проектирования `MDA-таблицы` разработчик определяет запрос данных и описывает колонки этого запроса, часть колонок могут быть `измерениями`, другие колонки - `показатели`.

- `Измерения` - колонки, по которым данные группируются;

- `Показатели` - колонки, к которым применяются функции агрегации.

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

Построение и отображение данных делится на две части:

- `Модель запроса` - описывает правила получения данных из `БД`, `измерения` и `показатели`.

- `Представление данных` - описывает правила сортировки, агрегации и порядок вывода данных на экран.

## Модель запроса

Описывает правила получения данных, `измерения` и `показатели`.

Класс `ru.bitec.app.btk.sel.mda.model.MdaModel`.

Для построения модели создан `класс-builder` `ru.bitec.app.btk.sel.mda.model.MdaModelBuilder`

### Текст запроса

`Текст запроса` - строка, в которой содержится текст `sql-запроса`. Этот запрос будет получать исходные данные из базы данных.

Для использования `связанных переменных` используется синтаксис `AnormSql`. Пример связанной переменной:

    select ...
        from ...
    where t.id = {id}

Для указания значений связанных переменных используется метод `on` класса `ru.bitec.app.btk.sel.mda.model.MdaModelBuilder`.

Полный пример использования запроса со `связанными переменными`:

    val model = MdaModelBuilder()
        .setQuery( () =>
        s"""
            select ...
                from ...
            where t.id = {id}
            """
        )
        .on(() => Seq(
        "id" -> 100.nl
        ))
        .build()

### Измерения

Определяют поля по которым доступна группировка и сортировка.

Класс `ru.bitec.app.btk.sel.mda.model.Dimension`.

#### Значимое измерение

Измерение, представляющее собой единичную колонку запроса.

Пример создания:

    val model = MdaModelBuilder()
        .addDimension(NumberColumn("nNum"), "Число")
        .addDimension(StringColumn("sString"), "Строка")
        .addDimension(DateColumn("dDate"), "Дата")

Первым параметром передается объект `колонка`, который описывает тип данных и имя колонки в запросе данных.

#### Ссылочное измерение

Измерение, представляющее из себя 2 колонки запроса, одна из которых содержит `id` объекта, а вторая - `headline`.

Используется, если в качестве измерения используется какой- либо объект с прямой ссылочностью.

В отображаемых данных колонка с `id` будет невидима.

Примечание

Для ссылочных полей важно создавать такие измерения, т.к. они позволят фильтроваться в универсальном фильтре по такому измерению как по ссылочному.

Пример создания:

    val model = MdaModelBuilder()
      .addRefDimension("idRefObject", "idRefObjectHl", "Ссылочный объект", "Some_RefClassName")

Параметры в порядке следования:

- имя колонки с идентификатором;

- имя колонки с отображаемым значением;

- отображаемое имя;

- имя класса, на который ссылается измерение.

#### Измерение переменной ссылочности

Измерение, представляющее из себя 2 колонки запроса, одна из которых содержит `gid` объекта, а вторая - `headline`.

Используется, если в качестве измерения используется какой- либо объект, на который ссылочность организована через `gid`.

В отображаемых данных колонка с `gid` будет невидима.

Примечание

Для ссылочных полей важно создавать такие измерения, т.к. они позволят фильтроваться в универсальном фильтре по такому измерению как по ссылочному.

Пример создания:

    val model = MdaModelBuilder()
      .addAnyRefDimension("gidRefObject", "gidRefObjectHl", "Ссылочный объект", List("Some_RefClassName1", "Some_RefClassName2"))

Параметры в порядке следования:

- имя колонки с идентификатором;

- имя колонки с отображаемым значением;

- отображаемое имя;

- список классов, на который ссылается измерение.

### Показатели

Определяют поля по которым доступна агрегация значений.

Класс `ru.bitec.app.btk.sel.mda.model.Dimension`.

#### Простой показатель

Показатель, представляющий собой единичную колонку запроса.

Пример создания:

    val model = MdaModelBuilder()
        .addMeasure(NumberColumn("nSum"), "Сумма")

Первым параметром передается объект `колонка`, который описывает тип данных и имя колонки в запросе данных.

#### Составной показатель

Так же как и `простой показатель` представляет собой единичную колонку запроса, но имеет дополнительное `измерение`, в разрезе которого должна производиться агрегация. Например, сумма в договоре, где дополнительным измерением является валюта.

Пример создания:

    val model = MdaModelBuilder()
      .addCompositeMeasure(
        NumberColumn("nSum"),
        Dimension(StringColumn("sMsr"), "Валюта"),
        "Сумма"
      )

Параметры в порядке следования:

- `колонка`, которая описывает тип данных и имя колонки в запросе данных;

- `измерение` - дополнительное измерение, в рамках которого требуется агрегация;

- отображаемое имя.

### Колонки

Модель обладает перечнем колонок, которые были использованы при создании `измерений` и `значений`.

Класс `ru.bitec.app.btk.sel.mda.model.Column`

Колонки определяют:

- тип данных;

- имя колонки в запросе данных;

- тип редактора.

Типы колонок:

- `NumberColumn` - числовая колонка;

- `BooleanColumn` - булева колонка. Наследник от числовой, с типом редактора `чекбокс`;

- `MoneyColumn` - денежная колонка. Наследник от числовой, с типом редактора `Денежный редактор`;

- `LongColumn` - целочисленная колонка;

- `StringColumn` - строковая колонка;

- `DateColumn` - колонка с типом `дата`, с типом редактора `редактор даты` ;

- `DateTimeColumn` - колонка с типом `дата и время`. Наследник от `DateColumn`, с типом редактора `Редактор даты и времени`.

Стандартный тип редактора может быть переопределен, используя метод `setEditorType`, который принимает строку, имеющую формат настройки `динамического типа редактора`.

Пример:

    NumberColumn("nNum").setEditorType("EditorType=etEdit")

## Представление данных

Отвечает за настройки отображения данных в `MDA-таблице`:

- порядок сортировки;

- вывод промежуточных итогов;

- агрегация значений показателей;

- порядок вывода колонок на экран;

- пользовательское переопределение наименования колонки;

- изменение стилей строк итогов и промежуточных итогов;

- размеры, видимость колонок;

- параметры настройки.

Класс `ru.bitec.app.btk.sel.mda.view.MdaView`.

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

### Измерения

Определяет настройки сортировки, группировки и вывода промежуточных итогов.

### Показатели

Определяет показатели, по которым будет выполнена агрегация.

### Атрибуты

Определяет порядок вывода колонок на экран и их наименование.

### Описание формируемых атрибутов выборки

На каждый подобранный `атрибут представления` в выборке формируются следующие атрибуты:

- `idValue[<имя колонки>]` - невидимый атрибут, будет содержать `id` для `ссылочных измерений` или `gid` для `измерений переменной ссылочности`.

- `value[<имя колонки>]` - видимый атрибут, в котором будет отображаться значение, видимое пользователя. Для `ссылочных измерений` или `измерений переменной ссылочности` в этот атрибут выводится значение колонки, объявленной как `headline`.

- `sEditor[<имя колонки>]` - невидимый атрибут, управляющий типом редактора.

- `sStyle[<имя колонки>]` - невидимый атрибут, управляющий стилем раскраски ячейки.

## Подключение MDA-таблицы к прикладной выборке

### Реализация отображения сгруппированных данных

Для подключения к прикладной выборке сервиса `MDA-таблиц` необходимо:

1. Унаследовать выборку от `ru.bitec.app.btk.sel.mda.Btk_MdaAbsAvi`.

2. Создать отображение, если требуется.

3. Унаследовать нужное отображение от отображения `Grid`.

4. Определить модель запроса данных, переопределив метод `buildModel`, используя строителя модели `ru.bitec.app.btk.sel.mda.model.MdaModelBuilder`.

5. Переопределить метод `getSourceDataRep`, который будет определять выборку для открытия исходных данных.

### Реализация отображения исходных данных

Для реализации выборки, которая будет отображать `исходные данные` (данные которые вернул запрос из базы данных), необходимо:

1. Унаследовать выборку от `ru.bitec.app.btk.sel.mda.Btk_MdaAbsAvi`.

2. Создать отображение, если требуется.

3. Унаследовать нужное отображение от отображения `SourceDataGrid`.

### Управление типом редактора

Тип редактора для колонки определяется в момент описания `модели запроса данных`. Каждый тип колонки имеет свой тип редактора по умолчанию, для его переопределения можно воспользоваться методом `setEditorType`.

### Интеграция с универсальным фильтром

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

Правила формирования доступных для фильтрации атрибутов:

- для `ссылочных измерений` создается ссылочный атрибут фильтрации;

- для `измерений переменной ссылочности` создается атрибут фильтрации переменой ссылочности;

- для всех остальных `измерений` и `показателей` создаются значимые атрибуты фильтрации в соответствие с типом данных.

### Создание стандартного фильтра

Стандартный фильтр создается по тем же правилам, что и для обычной выборки.

### Использование макросов

Для использования макроса выборки в тексте запроса необходимо получить его текст, используя метод `selection.getMacro`, и добавить его в нужное место запроса.

Пример:

    val model = MdaModelBuilder()
        .setQuery(() =>
        s"""
            select ...
                from ...
            where ${selection.getMacro("SomeMacrosName")}
            """
        )

### Описание основных методов

- `extendDynMeta` - позволяет добавить в перечень атрибутов выборки свои атрибуты.

- `extendDynRow` - позволяет установить дополнительные значения в формируемую строку выборки.

- `buildModel` - метод, который должен переопределить разработчик, для описания `модели данных`.

- `mdaModel` - возвращает `модель данных`.

- `mdaView` - возвращает `представление данных`.

- `needGenChooseCheckBox` - признак, что требуется формировать чекбоксы для выбора строк.

- `forSelectedRows` - позволяет обойти выбранные через чекбоксы строки.

- `getSourceDataRep` - метод, который должен переопределить разработчик, для указания выборки, которая будет открыта из операции `Открыть исходные данные`.

- `filterRow` - позволяет отфильтровать записи.

- `refreshBySql` - метод, который принудительно делает перезапрос данных из базы данных, и обновляет выборку.

### Описание основных операций

- `openSourceData` - открывает выборку, указанную в методе `getSourceDataRep`, в которой будут отображены исходные данные для выбранных строк.

- `chooseAll` - для всех записей проставляет чекбокс выбора.

- `clearAllChosen` - Для всех записей снимет чекбокс выбора.

- `chooseSelected` - Для всех выделенных записей проставляет чекбокс выбора.

- `clearSelected` - Для всех выделенных записей снимет чекбокс выбора.

## Описание настройки атрибутов

Настройка происходит через выборку `ru.bitec.app.btk.sel.mda.Btk_MdaViewEditorAvi#attrEditor`. Выборка ожидает в качестве параметра `mdaModel` в формате JSON и опционально прошлый `mdaView` для формирования нового `mdaView`. Возвращает JSON отредактированного `mdaView`.

Для работы с созданием/сохранением/загрузки настроек выборка ожидает названия выборки и репрезентации и опционально id прошлой настройки.

На вкладке `Настройка сортировки и агрегации` можно настроить:

- порядок и тип сортировки;

- вывод промежуточных итогов;

- тип агрегация значений показателей;

- стили промежуточных итогов.

На вкладке `Настройка выводимых столбцов` можно настроить:

- порядок вывода колонок на экран;

- пользовательское переопределение наименования колонки;

- размеры, видимость колонок.

На вкладке `Характеристики настройки` можно настроить:

- изменение параметров настройки;

- стили итогов.