Модуль для работы с иерархией Дьюи

Материал из Course Orchestra
Перейти к: навигация, поиск
Внимание! Вы просматриваете документацию к Celesta 6.x. Документация по Celesta 7.x доступна на courseorchestra.github.io/celesta.

1. Справочник Celesta

1.1 Введение и основные понятия
1.2 Запуск и авто-обновление
1.3 Базовая настройка
1.4 Системные таблицы
1.5 CelestaSQL
1.6 CelestaDoc
1.7 Контексты сессии и вызова
1.8 Курсоры
1.9 BLOB-поля
1.10 Option-поля
1.11 Защита от потерянных обновлений
1.12 Метаданные Celesta
1.13 CelestaUnit

2. Celesta и базы данных

2.1 Особенности работы Celesta с поддерживаемыми типами СУБД
2.2 Проектирование базы данных Celesta в DBSchema

3. Создание решений с использованием Celesta для ShowCase

3.1 Программа обучения Celesta
3.2 Подготовка рабочего места для работы с Celesta
3.2.1 Для разработчиков платформы
3.2.2 Для разработчиков решений
3.3 Системные гранулы Celesta
3.3.1 common
3.3.1.1 Экспорт/импорт данных
3.3.1.2 Навигатор
3.3.1.3 Серии номеров
3.3.1.4 Иерархия Дьюи
3.3.1.5 Системные функции
3.3.1.6 Реестр настроек
3.3.1.7 Mailsender
3.3.1.8 Common.filter
3.3.2 common.api
3.3.4 security
3.3.3 lyra
3.4 Стандартные гранулы Celesta
3.4.1 dirusing
3.4.2 workflow
3.4.3 File repository
3.5 Отрисовка элементов Showcase при помощи Celesta
3.5.1 Конвертер XML-JSON
3.5.2 Навигатор (Navigator)
3.5.3 Информационная панель (Datapanel)
3.5.4 Серверное действие (Server activity)
3.5.5 Вебтекст (WebText)
3.5.6 Грид (Grid)
3.5.6.1 Панель инструментов (ToolBar)
3.5.7 XForms
3.5.7.1 Селекторы
3.5.7.2 Submission
3.5.7.3 Загрузка/Выгрузка файлов (Upload/Download)

5. Решение проблем

5.1 Проблемы с кодировкой jython-файлов

Описание

Предполагается что связь внутри иерархий в решениях на платформе КУРС будет реализована с помощью иерархии Дьюи. Модуль hierarchy разработан для удобной работы с иерархией Дьюи.

О принципах работы данной организации иерархических справочников см., напр., статью в журнале RSDN, вот цитата из неё:

 Иерархический справочник может быть основан на алгоритме записи, используемом в системе 
десятичной классификации Дьюи (Dewey Decimal Classification). 
Каждый узел содержит некоторый идентификатор, уникальный среди потомков его родителя. Каждый узел 
содержит путь от корневого элемента к данному. 
 Путь реализуется с помощью идентификаторов, разделенных символом точки.
 Например:
 1 Организация «Рога и копыта».
 1.1 Департамент «Рога».
 1.1.1 Отдел продажи рогов.
 1.1.2 Отдел покупки рогов.
 1.1.2.1 Группа оценки качества рогов.
 1.1.3 Отдел проката рогов.
 1.2. Департамент «Копыта»
 1.2.1 Отдел покупки копыт.
 1.2.2 Отдел продажи копыт.
 Как можно сразу заметить, при работе с подобным классификатором удобно использовать оператор 
LIKE. Если указывается путь, в котором начальные символы не являются маской, база данных может 
использовать индекс с операцией index scan с диапазонным поиском.


Для корректной работы с модулем в таблице с иерархией должны присутствовать два поля: поле для номера (вида 1.2.3) и сортировочное поле (вида 00100200000003). При использовании всех функций модуля предполагается, что ваша иерархия сформирована корректно и оба поля во всех записях заполнены.

Функция generateSortValue

Функция generateSortValue позволяет генерировать значение для сортировочного поля, на основе номера иерархии. на вход необходимо передать 2 аргумента

  1. Номер в иерархии
  2. Список с количеством разрядов для каждого уровня иерархии, при этом нулевой элемент этого списка указывает на количество разрядов по умолчанию. В случае если второй аргумент отсутствует или передан пустой список, для всех уровней количество разрядов равно 3.

Пример использования

from common.hierarchy import generateSortValue

...
cursor.sort = generateSortValue('1.8.5.6',[5,4,2])
...

в данном случае в поле sort вставится строка 000108000005000006 для первого уровня 4 разряда, для второго 2 разряда, для остальных 5 разрядов.

from common.hierarchy import generateSortValue

...
cursor.sortedField = generateSortValue('1.2')
...

в данном случае в поле sortedField вставится строка 001002 для всех уровней 3 разряда.

Данную функцию удобно использовать триггерах на update и insert

from common.hierarchy import generateSortValue

def refreshingSort(rec):
    rec.sort = generateSortValue(unicode(rec.number))


from . import _test_orm

_test_orm.testCursor.onPreInsert.append(refreshingSort)
_test_orm.testCursor.onPreUpdate.append(refreshingSort)

Функция moveNodeInHierarchy

Функция moveNodeInHierarchy передвигает куст в иерархии на указанную позицию соответствующего уровня, при этом уникальность нумерации не отслеживается (если Вам необходимо передвинуть куст с учетом правильной нумерации используйте функцию changeNodePositionInLevelOfHierarchy). На вход функции необходимо передать 4 аргумента

  1. context - контекст Celesta
  2. cursorInstance - курсор в который записан корень передвигаемого куста
  3. numberField - имя поля, содержащего номер иерархии
  4. position - желаемая позиция для передвижения внутри уровня
  5. isOneHierarchy - параметр указывает одна ли иерархическая структура находится в таблице курсора, по умолчанию равен False. В случае если иерархий несколько, следует быть очень внимательным с фильтрами, т.к. они должны обязательно идентифицировать изменяемую иерархию, но не более

Пример использования

from common.hierarchy import moveNodeInHierarchy
from _test_orm import testCursor
...
test=testCursor(context)
test.get(123)
...
moveNodeInHierarchy(context,test,'number',10)
...

Допустим в курсоре test находится строка с номером в иерархии 1.4.5, тогда вне зависимости от того, есть ли уже на том же уровне где и расположен курсор test элемент с номер 10 или нет - весь куст все равно переместится внутри своего уровня на 10 позицию, т.е. номера иерархии всех его потомков будут начинаться с 1.4.10

Функция deleteNodeFromHierarchy

Функция deleteNodeFromHierarchy удаляет куст из иерархии, сдвигая все нижестоящие кусты того же уровня на одну позицию вверх. На вход функции необходимо передать 4 аргумента

  1. context - контекст Celesta
  2. cursorInstance - курсор в который записан корень удаляемого куста
  3. numberField - имя поля, содержащего номер иерархии
  4. sortField - имя поля, содержащего сортировочные значения
  5. isOneHierarchy - параметр указывает одна ли иерархическая структура находится в таблице курсора, по умолчанию равен False. В случае если иерархий несколько, следует быть очень внимательным с фильтрами, т.к. они должны обязательно идентифицировать иерархию, но не более

Пример использования

from common.hierarchy import deleteNodeFromHierarchy
from _test_orm import testCursor
...
test=testCursor(context)
test.get(123)
...
deleteNodeFromHierarchy(context,test,'number','sort')
...

Допустим в курсоре test находится строка с номером в иерархии 1.4.5, тогда весь куст (текущий элемент и его потомки) будет удален, а все нижестоящие подвинутся на одну позицию вверх.

Функция changeNodePositionInLevelOfHierarchy

Функция changeNodePositionInLevelOfHierarchy передвигает куст в иерархии на указанное число позиций внутри уровня уровня, с учетом корректной нумерации. На вход функции необходимо передать 5 аргументов

  1. context - контекст Celesta
  2. cursorInstance - курсор в который записан корень передвигаемого куста
  3. numberField - имя поля, содержащего номер иерархии
  4. sortField - имя поля, содержащего сортировочные значения
  5. shift желаемое количество позиций для передвижения внутри уровня (может быть и отрицательным)
  6. isOneHierarchy - параметр указывает одна ли иерархическая структура находится в таблице курсора, по умолчанию равен False. В случае если иерархий несколько, следует быть очень внимательным с фильтрами, т.к. они должны обязательно идентифицировать иерархию, но не более

Пример использования

from common.hierarchy import changeNodePositionInLevelOfHierarchy
from _test_orm import testCursor
...
test=testCursor(context)
test.get(123)
...
changeNodePositionInLevelOfHierarchy(context,test,'number','sort',5)
...

Допустим в курсоре test находится строка с номером в иерархии 1.4.5, тогда весь куст передвинется на позицию 1.4.10 (либо на последнюю позицию уровня если она 1.4.5 и 1.4.10), кусты ранее находившиеся ниже текущего поднимутся на одну позицию вверх.

Функция leftShiftNodeInHierarchy

Функция leftShiftNodeInHierarchy передвигает куст на один уровень выше. На вход функции необходимо передать 4 аргумента

  1. context - контекст Celesta
  2. cursorInstance - курсор в который записан корень передвигаемого куста
  3. numberField - имя поля, содержащего номер иерархии
  4. sortField - имя поля, содержащего сортировочные значения
  5. isOneHierarchy - параметр указывает одна ли иерархическая структура находится в таблице курсора, по умолчанию равен False. В случае если иерархий несколько, следует быть очень внимательным с фильтрами, т.к. они должны обязательно идентифицировать иерархию, но не более

Пример использования

from common.hierarchy import leftShiftNodeInHierarchy
from _test_orm import testCursor
...
test=testCursor(context)
test.get(123)
...
leftShiftNodeInHierarchy(context,test,'number','sort')
...

Допустим в курсоре test находится строка с номером в иерархии 1.4.5, тогда после применения функции куст переместится на позицию 1.<последний номер внутри этого уровня + 1>

Функция shiftNodeToOtherLevelInHierarchy

Функция shiftNodeToOtherLevelInHierarchy передвигает куст в иерархии внутрь указанного уровня . На вход функции необходимо передать 5 аргументов

  1. context - контекст Celesta
  2. cursorInstance - курсор в который записан корень передвигаемого куста
  3. numberField - имя поля, содержащего номер иерархии
  4. sortField - имя поля, содержащего сортировочные значения
  5. parentNumber- номер элемента в иерархии Дьюи, внутрь которого необходимо передвинуть cursorInstance (этот параметр можно не указывать, в этом случае куст будет передвинут на самый верхний уровень )
  6. isOneHierarchy - параметр указывает одна ли иерархическая структура находится в таблице курсора, по умолчанию равен False. В случае если иерархий несколько, следует быть очень внимательным с фильтрами, т.к. они должны обязательно идентифицировать иерархию, но не более

Пример использования

from common.hierarchy import shiftNodeToOtherLevelInHierarchy
from _test_orm import testCursor
...
test=testCursor(context)
test.get(123)
test1=testCursor(context)
test1.get(1234)
...
shiftNodeToOtherLevelInHierarchy(context,test,'number','sort',test1.number)
...

Допустим в курсоре test находится строка с номером в иерархии 1.4.5, а в test1 находится строка с номером 2.5 , куст с корнем test будет передвинут на последнюю позицию внутри уровня 2.5.

Функция hasChildren

Функция hasChildren проверяет есть ли у указанного элемента потомки. На вход функции необходимо передать 3 аргумента

  1. context - контекст Celesta
  2. cursorInstance - курсор в который записан корень передвигаемого куста
  3. numberField - имя поля, содержащего номер иерархии
  4. isOneHierarchy - параметр указывает одна ли иерархическая структура находится в таблице курсора, по умолчанию равен False. В случае если иерархий несколько, следует быть очень внимательным с фильтрами, т.к. они должны обязательно идентифицировать иерархию, но не более

Пример использования

from common.hierarchy import hasChildren
from _test_orm import testCursor
...
test=testCursor(context)
test.get(123)
...
if hasChildren(context,test,'number'):
    pass
...

Допустим в курсоре тест находится строка с номером в иерархии 1.4.5, тогда в случае если у этого элемента есть потомки, то функция вернет True, в противном случае False

Функция getNewItemInLevelInHierarchy

Функция getNewItemInLevelInHierarchy возвращает номер для нового элемента внутри уровня. На вход функции необходимо передать 3 аргумента

  1. context - контекст Celesta
  2. cursorInstance - курсор, в который записан родительский элемент, если необходимо получить номер на верхнем уровне,то следует передавать пустой курсор
  3. numberField - имя поля, содержащего номер иерархии
  4. isOneHierarchy - параметр указывает одна ли иерархическая структура находится в таблице курсора, по умолчанию равен False. В случае если иерархий несколько, следует быть очень внимательным с фильтрами, т.к. они должны обязательно идентифицировать иерархию, но не более

Пример использования

from common.hierarchy import getNewItemInLevelInHierarchy
from _test_orm import testCursor
...
test=testCursor(context)
test.get(123)
...
newNumber = getNewItemInLevelInHierarchy(context,test,'number')
...

Допустим в курсоре тест находится строка с номером в иерархии 1.4.5, при этом этот элемент имеет 5 потомков, тогда newNumber будет равен 1.4.5.6