Схема функционирования OLAP куба в Pentaho
В документации [1] удалось найти нормальную схему функционирования сервера, создающего кубы и работающего с MDX запросами. В качестве основной литературы предлагаю почитать «Mondrian 3.0.4 Technical Guide». Схема, приведенная ниже, взята из руководства.
Для организации кубов нужна схема (в виде XML) представления куба. В схеме описывается, к какой таблице происходит построение куба, производится описание измерений, меры, расчет дополнительных полей.
Начнем разбираться, для чего нужны измерения, иерархии, меры. Сначала зададим вопрос: как хранится многомерный куб и вообще, что это такое? Многомерный куб - многомерный массив, в котором хранятся меры. Для доступа к мерам нужны уникальные индексы.
Иерархия - это всего лишь множества для обращения к уникальным индексам и больше ничего. На роль уникальных индексов предпочтительно использовать суррогатные ключи, которые выполняют следующие функции:
- Служат для доступа к мерам. Ключ не зависит от информации, которая хранится в БД (OLTP) (обычно является целым числом).
- Основное предназначение WH (Ware House) - это сохранение информации и неизменяемость уже попавших данных, а это свойство обеспечивает суррогатный ключ.
- Снижение размеров (занимаемого пространства на диске) WH (прирост таблицы фактов будет идти только по размеру внешних ключей и самим мерам).
Теперь становится понятно, какие поля требуется задавать для организации взаимодействия кубов.
Для примера разработаем куб Sales (похож из руководства [1], но есть и отличия). Этот куб больше подходит для рассмотрения, чем SteelWheels - из стандартной установки.
Для большего понимания приведем фрагмент ER диаграммы Foodmart. (Это только схема и в ней есть несоответствие типов данных. Нас интересует только отношение между таблицами. Кстати, рисовалась схема данных в программе SQL Power Architect. Ссылка приведена в конце статьи).
Приведем схему для первого куба на Pentaho.
<Schema name="first_olap_cube" description="my first cube"> <Dimension name="Time"> <Hierarchy hasAll="false" primaryKey="time_id"> <Table name="time_by_day" /> <Level name="Year" column="the_year" type="Numeric" uniqueMembers="true" /> <Level name="Quarter" column="quarter" uniqueMembers="false" /> <Level name="Month" column="month_of_year" type="Numeric" uniqueMembers="false" /> </Hierarchy> </Dimension> <Cube name="Sales"> <Table name="sales_fact_1997" /> <Dimension name="Gender" foreignKey="customer_id"> <Hierarchy hasAll="true" allMemberName="All Genders" primaryKey="customer_id"> <Table name="customer" /> <Level name="Gender" column="gender" uniqueMembers="true" /> </Hierarchy> </Dimension> <DimensionUsage name="Time" source="Time" foreignKey="time_id"/> <Measure name="Unit Sales" column="unit_sales" aggregator="sum" formatString="#,###" /> <Measure name="Store Sales" column="store_sales" aggregator="sum" formatString="#,###.##" /> <Measure name="Store Cost" column="store_cost" aggregator="sum" formatString="#,###.00" /> <CalculatedMember name="Profit" dimension="Measures" formula="[Measures]. [Store Sales]-[Measures].[Store Cost]"> <CalculatedMemberProperty name="FORMAT_STRING" value="$#,##0.00" /> </CalculatedMember> </Cube> </Schema>
Итак, поехали разбираться.
Схема
<Schema name="first_olap_cube" description="my first cube">
<Schema> - тег, необходимый для описания схемы функционирования OLAP куба на сервере Pentaho. В схеме могут быть описаны права пользователей, меры, кубы, виртуальные кубы и т.д. Можно глянуть одним глазом на схему SteelWheels и увидеть, как происходит описание (прав, схем разделения информации и т.д).
name="first_olap_cube" - название схемы.
description="my first cube" - описание схемы.
Описание куба
<Cube name="Sales"> <Table name="sales_fact_1997" /> - <Dimension name="Gender" foreignKey="customer_id"> - <Hierarchy hasAll="true" allMemberName="All Genders" primaryKey="customer_id"> <Table name="customer" /> <Level name="Gender" column="gender" uniqueMembers="true" /> </Hierarchy> </Dimension> <DimensionUsage name="Time" source="Time" foreignKey="time_id"/> <Measure name="Unit Sales" column="unit_sales" aggregator="sum" formatString="#,###" /> <Measure name="Store Sales" column="store_sales" aggregator="sum" formatString="#,###.##" /> <Measure name="Store Cost" column="store_cost" aggregator="sum" formatString="#,###.00" /> - <CalculatedMember name="Profit" dimension="Measures" formula="[Measures]. [Store Sales]-[Measures].[Store Cost]"> <CalculatedMemberProperty name="FORMAT_STRING" value="$#,##0.00" /> </CalculatedMember> </Cube>
<Cube> - тег, в котором происходит описание куба.
<Table name="sales_fact_1997" /> это таблица фактов, по которой происходит построение куба.
Измерения
<Dimension> тег измерений. В измерении указывается информация, по какому полю будет задаваться соответствие с таблицей фактов.
Выделим два вида измерений: внутренние и внешние. Действие их аналогично действию глобальной переменной (внешние) и локальной переменной (внутренние).
Внутренние измерения задаются между тегами <cube> </cube>. Однако это не всегда удобно. Внешние измерения для кубов делают, если в схеме будет более одного куба.
Внешние измерения описываются точно так же, как и внутренние, только располагаются между тегами <Schema>...</Schema>. Для использования внешнего измерения в кубе нужно сделать на него ссылку. Ссылка делается между тегами куба <cube> </cube> тегом <DimensionUsage name="Store Type" source="Store Type" foreignKey="store_id"/>
name="Store Type" - название внешнего измерения.
source="Store Type" - название измерения, которое добавляется в куб.
foreignKey="store_id" - внешний ключ таблицы фактов.
Внутреннее измерение
<Dimension name="Gender" foreignKey="customer_id"> - <Hierarchy hasAll="true" allMemberName="All Genders" primaryKey="customer_id"> <Table name="customer" /> <Level name="Gender" column="gender" uniqueMembers="true" /> </Hierarchy> </Dimension>
<Dimension name="Gender" foreignKey="customer_id">
foreignKey="customer_id" - это внешний ключ из таблицы фактов.
<Hierarchy> Тег описывает иерархию, которая находится в таблице. Для описания требуется задать первичный ключ таблицы измерений.
Иерархия
Далее начинаем разбираться с иерархией.
<Hierarchy hasAll="true" allMemberName="All Genders" primaryKey="customer_id">
<Hierarchy> тег иерархии.
hasAll="true" - отображает все уровни иерархии.
allMemberName="All Genders" - показывает, как будет отображаться иерархия.
primaryKey="customer_id" - первичный ключ таблицы измерений.
<Table name="customer"> - сама таблица измерений.
Уровень иерархии
<Level name="Gender" column="gender" uniqueMembers="true" />
<Level> уровень иерархии.
name="Gender" - название иерархии.
column="gender" - столбец, по которому строится иерархия.
uniqueMembers="true" - все уникальные значения.
Внешнее измерение
Далее разберем внешнее измерение.
<Dimension name="Time"> <Hierarchy hasAll="false" primaryKey="time_id"> <Table name="time_by_day" /> … </Hierarchy> </Dimension>
Из тега <Dimension name="Time" > исчезает свойство foreignKey. Это свойство перекочевывает в тег <DimensionUsage name="Store Type" source="Store Type" foreignKey="store_id"/>. В целом, структура описания соответствует внутренней иерархии.
Кстати, если возникнет ошибка “This page cannot be accessed directly. It must be linked to from other pages”, то один из вариантов ошибки - присутствие foreignKey в теге <Dimension name="Time" >, чего не должно быть во внешних измерениях.
Многоуровневая иерархия
Теперь разберем многоуровневую иерархию.
<Dimension name="Time"> <Hierarchy hasAll="false" primaryKey="time_id"> <Table name="time_by_day" /> <Level name="Year" column="the_year" type="Numeric" uniqueMembers="true" /> <Level name="Quarter" column="quarter" uniqueMembers="false" /> <Level name="Month" column="month_of_year" type="Numeric" uniqueMembers="false" /> </Hierarchy> </Dimension>
Происходит добавление трех уровней иерархии.
<Hierarchy hasAll="false" primaryKey="time_id">
hasAll="false" - нельзя перетаскивать все значения.
<Level name="Year" column="the_year" type="Numeric" uniqueMembers="true" />
<Level name="Quarter" column="quarter" uniqueMembers="false" />
На втором уровне происходит построение второго множества уникальных ключей. Для третьего - аналогично.
Меры
Меры - это наши данные. К данным могут применяться операции, допустимые на множестве мер. (Предположим, по выручке допустимая операция будет суммирование).
Обычные меры
<Measure name="Unit Sales" column="unit_sales" aggregator="sum" formatString="#,###" />
<Measure> тег, который описывает меру.
name="Unit Sales" - название меры.
column="unit_sales" - название столбца в таблице фактов.
aggregator="sum" - операции агрегации на множестве. Не всегда могут применяться операции суммирования.
formatString="#,###" - формат выводимых значений при анализе. Можно отметить, что “saiku” не поддерживает отображение форматов.
Вычисляемые меры
<CalculatedMember name="Profit" dimension="Measures" formula="[Measures]. [Store Sales]-[Measures].[Store Cost]"> <CalculatedMemberProperty name="FORMAT_STRING" value="$#,##0.00" /> </CalculatedMember>
<CalculatedMember> - вычисляемое поле.
name="Profit" - название поля.
dimension="Measures" - поле относится к измерениям.
formula="[Measures]. [Store Sales]-[Measures].[Store Cost]" - формула для расчета измерения, заданная на языке MDX. Существуют и другие способы вычисления полей. Более подробно можно ознакомиться в руководстве [1].
<CalculatedMemberProperty> - свойства вычисляемого поля.
name="FORMAT_STRING" - название свойства вычисляемого поля.
value="$#,##0.00" задает формат отображения поля.
Ну, вот и весь разбор куба. Теперь понятно, что и куда писать в schema-workbench для кубика.
При работе с Pentaho Data Source мы не сможем использовать схему снежинка, если в одной таблице измерений есть два или более значимых поля (например, время, год, квартал и т.д.), так как Pentaho Data Source не может задать иерархию самостоятельно.
Ссылки и литература:
- «Mondrian 3.0.4 Technical Guide».
- Pentaho schema workbench утилита для составления схем кубов.
- Утилита для разработки ER диаграмм и моделирования кубов. (Пока меня устраивает) http://www.sqlpower.ca/page/architect_download_os
- Первичный ключ - составной или суррогатный? http://www.interface.ru/home.asp?artId=23781
- Подробности
- Опубликовано: 24 Октябрь 2013
- Просмотров: 8633