Наследование значений ТВ параметров родителем.

Здравствуйте. Вопрос такого рода. Есть структура:
  • Родитель
    • ---Дочерний 1
    • ---Дочерний 2

    • ---Дочерний 3
  • Родитель 2
    • ---Дочерний 1
    • ---Дочерний 2

    • ---Дочерний 3


Дочерних документов может быть неограниченное! количество. У каждого дочернего документа есть несколько ТВ параметров с типом ввода мульти-селект(множественный выбор). Скажем одно из доп. полей называется my_tv_1. Такое же доп. поле my_tv_1 есть и у Родителя. Теперь главная суть вопроса: вот я в дочерних документах задал значения в my_tv_1 (например в ресурсе 1, значение А, в ресурсе 2 значение Б и в ресурсе 3 значение В) и нужно чтобы эти значения с трех дочерних ресурсов прописались в этом же ТВ у родителя. То есть у родителя значения тв my_tv_1 были А, Б, В.

Если короче выражаться, то в ТВ родителя должны быть все возможные значения определенного ТВ всех дочерних ресурсов (если какое-то значение уже есть, тогда не дублируем, только уникальные значения).

Я как бы с пхп совсем на Вы… Я думаю надо сделать плагин на событие onDocFormSave. При сохранении дочернего ресурса берем значение my_tv_1 текущего документа, проверяем значение my_tv_1 родительского ресурса, если такое значение есть тогда ничего не делаем, иначе добавляем это значение и обновляем родительский документ.
Логику я надеюсь понимаю, а вот написать на пхп проблемно.....(
Кто-то может помочь накидать такой плагин.
Alex
02 января 2017, 12:27
modx.pro
2
2 003
0

Комментарии: 9

Гриборий
04 января 2017, 00:04
+1
Сделал бы так(но не настоящий сварщик):

$parent = $resource->getOne('Parent');

//Из значений тв собираем массивы, чтобы можно было с ними работать.
$resource_values = explode('||',$resource->getTVValue('yourtv'));
$parent_values = explode('||',$parent->getTVValue('yourtv'));

//Объединяем
$tags = array_merge($resource_values, $parent_values);

//Оставляем только уникальные значения
$tags = array_unique($tags);

//Переводим назад в строку сразделителем '||'
$tags = implode('||', $tags);

$parent->setTVValue('yourtv', $tags);
    Гриборий
    04 января 2017, 00:06
    0
    Ну, конечно, проверку бы еще нужно, по шаблону, например.
      Alex
      07 января 2017, 09:19
      0
      Привет. Спасибо за ответ. Я использовал вот такой код:
      <?php
      $template = $resource->get('template');
      if($template != 5 ) return ''; // ID шаблона товара
      $myTV = $resource->getTVValue('tip'); //получаем TV
      $par_id = $resource->get('parent'); //получаем ID родителя
      if(empty($par_id)) return '';
      
      $tvr = $modx->getObject('modTemplateVarResource', array(
        'tmplvarid' => 6, //тут ID TV
        'contentid' => $par_id
      ));
      if ($tvr) {
        $parTV = $tvr->get('value');
      }
      $pos = strpos($parTV, $myTV); //находим вхождение TV товара в строке TV родителя
      if ($pos === false){ //если не найдено...
          $newTV = $parTV.'||'.$myTV; //...добавляем значение
          $parent = $modx->getObject('modResource', $par_id); //получаем объект родителя
          $parent->setTVValue('tip', $newTV); //и пишем в TV родителя
      }
      Вроде бы вполне нормально работает, ваш вариант не пробовал, но все равно спасибо за ответ.
        Гриборий
        07 января 2017, 13:05
        0
        Вроде бы вполне нормально работает
        Похоже, пока в мультиселекте дочерних ресурсов указано только одно значение.
          Alex
          01 февраля 2017, 23:22
          0
          Все таки оказалось опция нескольких значений в одном мультиселекте нужна и тут возникла проблема. Как мой вариант плагина, который мне подсказали на модекс.ру так и ваш работал некорректно. То есть, если в одном мультиселекте товара задавать например 3 значения вот так: ТВ «Назначение» = В кухню||В прихожую||В гостиную, то в ТВ «Назначение» родительской категории эти значения склеивались вот так В кухнюВ прихожуюВ гостиную в одно значение. Это конечно кардинально не подходило. Подправил чуток плагин, тоже не сварщик, но вроде работает как надо.
          $res = $modx->getObject('modResource', $resource->get('id')); //получаем ID текущего ресурса
          $template = $res->get('template'); //делаем проверку по шаблону товара
          if($template != 5 ) return '';
          
          $tvs = $res->getMany('TemplateVarResources', array('tmplvarid' => 6)); //получаем необработанный массив заданнаго ТВ-параметра
          foreach ($tvs as $k =>$tv) { // выводим массив
              $tvs = $tv->toArray();
          }
          
          $tvs = array_splice($tvs, 3); // вырезаем первые три пары [ключ]=>значение, оставляем только значения ТВ
          $tvs = implode('||',$tvs); // переводим массив в строку с разделителем ||
          
          $par_id = $res->get('parent'); //получаем ID родителя
          if(empty($par_id)) return '';
          
          $tvr = $modx->getObject('modTemplateVarResource', array( //получаем необработанные значения ТВ родителя
            'tmplvarid' => 6, //тут ID нужного TV
            'contentid' => $par_id
          ));
          
          if ($tvr) {
            $parTV = $tvr->get('value');
          }
          $pos = strpos($parTV, $tvs); // сравниваем строковые значения ТВ родителя и ТВ текущего документа, оставляем только уникальные
          
          if ($pos === false){ //если не найдено...
              $newTV = $parTV.'||'.$tvs; //...добавляем значение
              $parent = $modx->getObject('modResource', $par_id); //получаем объект родителя
              $parent->setTVValue('tip', $newTV); //пишем в тв родителя
          }
          Игорь
          11 июля 2021, 12:14
          0
          А как сделать наоборот у простых ресурсов. Есть родитель и ТВ у него. Это же ТВ присвоено дочерним. Как прописать значение родителя в это же тв дочерних?
          Был бы очень признателен.
      Виктор
      19 августа 2017, 19:02
      0
      Подскажите, пожалуйста, как можно сделать наоборот — что бы значение TV родителя назначалось дочерним ресурсам?

      Я так понимаю, код будет похожий, но что-то не разберусь, как именно нужно написать.
        Alex
        29 сентября 2017, 18:05
        0
        Еще актуально? Могу написать код.
          Виктор
          11 июля 2021, 12:33
          0
          да, буду благодарен!
        Авторизуйтесь или зарегистрируйтесь, чтобы оставлять комментарии.
        9