Доктрина 1.2. Свойства NestedSet и наследование отношений от предков - PullRequest
0 голосов
/ 12 мая 2011

У меня есть проект Doctrine 1.2, который я реорганизую, чтобы иметь древовидную структуру для таблицы, использующей поведение доктрины NestedSet с несколькими корнями.

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

Позвольте мне объяснить на примере:

Category:
  actAs:
    NestedSet:
      hasManyRoots: true
      rootColumnName: root_id
  columns:
    name: string(50)
    another_property: string(50)
    active: boolean
Tag:
  columns:
    value: string(50)
CategoryTag:
  columns:
    category_id: integer
    tag_id: integer

Что я хочу выполнить:

  • получить, если категорияактивный, это означает, что проверка, все ли предки активны
  • , если в данной категории отсутствует another_property, наследует его от ближайшего предка, в котором присутствует
  • , извлекает теги для данной категории;если метки отсутствуют, извлеките их у ближайшего предка

Что бы вы предложили в качестве наилучшего подхода для максимизации скорости и гибкости?

1 Ответ

0 голосов
/ 12 мая 2011

Ну, это очень просто.Просто получите дерево с нужными вам отношениями следующим образом:

    class ModelTable extends Doctrine_Table
    {
      /**
       * Gets tree element in one query
       */
      public function getModelTree()
      {

        $q = $this->createQuery('g')
          ->leftJoin('g.Tags t')
          ->orderBy('g.root_id')
          ->addOrderBy('g.lft')
          ->where('g.root_id NOT NULL')
;
        return $q->execute(array(),  Doctrine_Core::HYDRATE_ARRAY_HIERARCHY);
      }
    }

Затем вы можете отобразить его следующим образом:

<?php function echoNode($tree, $parent=null) { ?>
  <ul>
  <?php foreach ($tree as $node): ?>
    <li data-property='<?php echo false != $node['property'] ? $node['property'] : $parent['property']  ?>'>
      <?php echo $node['name'] ?>
      <?php if (count($node['__children']) > 0): ?>
        <?php echo echoNode($node['__children'], $node) ?>
      <?php endif; ?>
    </li>
  <?php endforeach; ?>       
  </ul>
<?php } ?>

<?php echo echoNode($tree) ?>

Обратите внимание, как вы можете получить «свойство» у родителя.узел, если он отсутствует.Другой способ решения этой проблемы - использовать Doctrine_Core :: HYDRATE_RECORD_HIERARCHY.Это позволяет использовать для вызова методов на $ узлах при цикле.Вы можете создать метод Model :: getClosestProperty (), например, чтобы получить свойство от ближайшего родителя.Но это не так эффективно, как увлажнение массива.

...