[dev] Переопределение сортировки топиков

Статья предназначена для разработчиков плагинов и рассказывает о некоторых новых возможностях, появившихся в версии 1.1. Если быть более точным, то коммит с изменениями был залит в текущую ветку менее суток назад. Но так как это обновление решает важные застарелые проблемы, то решил написать об этом практически сразу же. Итак, известно, что прародителем Альто был движок Livestreet, и, соответственно, наш движок унаследовал, в числе прочего, множество методов для получения выборки топиков под конкретные случаи. Например:
public function GetTopicsGood($iPage, $iPerPage, $bAddAccessible = true) {
    // Список "хороших" топиков
}

public function GetTopicsDiscussed($iPage, $iPerPage, $sPeriod = null, $bAddAccessible = true) {
    // Список самых обсуждаемых топиков
}
Ну, и так далее.

Такие методы, как правило, работают по одному алгоритму: формируется фильтр, где задаются параметры отбора и порядок сортировки, а потом вызывается метод получения списка топиков через метод GetTopicsByFilter(...).

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

Как это работает сейчас.

Введено такое понятие, как «именованные фильтры». И теперь в этих узкоспециализированных методах фильтр задается через вызов метода GetNamedFilter(), куда передаются имя фильтра и дополнительные параметры. Т.е. было так:
public function GetTopicsNew($iPage, $iPerPage, $bAddAccessible = true) {
    $aFilter = array();
    // Здесь формируется фильтр ...
    return $this->GetTopicsByFilter($aFilter, $iPage, $iPerPage);
}
А теперь это так:
public function GetTopicsNew($iPage, $iPerPage, $bAddAccessible = true) {
    // Получаем именованный фильтр 'new' с доп.параметром 'accessible'
    $aFilter = $this->GetNamedFilter('new', array('accessible' => $bAddAccessible));
    return $this->GetTopicsByFilter($aFilter, $iPage, $iPerPage);
}
И теперь, если разработчик хочет изменить фильтр для метода GetTopicsNew(), он должен переопределить метод GetNamedFilter():
class PluginMine_ModuleTopic extends PluginMine_Inherits_ModuleTopic {

    public function GetNamedFilter($sFilterName, $aParams = array()) {
        // Получаем фильтр, заданный по умолчанию
        $aFilter = parent::GetNamedFilter($sFilterName, $aParams);
        if ($sFilterName == 'new') {
            $aFilter['order'] = '...'; // задаем свой порядок сортировки
        }
        return $aFilter;
    }
}
И стандартный метод GetTopicsNew() будет получать фильтр 'new', измененный плагином. Кроме того, можно задать настройки фильтра по умолчанию:
class PluginMine_ModuleTopic extends PluginMine_Inherits_ModuleTopic {

    public function Init() {
        parent::Init();
        $aFilter = array( /* новый фильтр по умолчанию */ );
        $this->SetTopicsFilter($aFilter); // задаем свой фильтр
    }
}
Разработчикам надо также иметь ввиду, что, если задаются какие-то свои специфические параметры фильтра, то, возможно, придется еще и переопределить метод buildFilter() в маппере модуля:
class PluginMine_ModuleTopic_MapperTopic extends PluginMine_Inherits_ModuleTopic_MapperTopic {

    protected function buildFilter($aFilter) {
        $sWhere = parent::buildFilter($aFilter);
        if (!empty($aFilter['...'])) {
            // здесь добавляем условия в $sWhere по своим параметрам
        }
        retuen $sWhere;
    }
}
Надеюсь, эти фичи облегчат жизнь сторонним разработчикам.

Похожие статьи

  • Alto CMS v.1.1: некторые «плюшки» для разработчиков
    Это статья для разработчиков. Поэтому буду краток: 1) Возможность установки плагинов в поддиректории 2) Человекопонятный синтаксис вызов методов модулей 3) Плагин для разработчиков
  • Работа с css- и js-файлами - дополнительные возможности для разработчиков шаблонов и плагинов
    В продолжении к статье Файлы js и css, а также прочие asset'ы – тонкости и нюансы работы с ними в Альто хочу рассказать о некоторых дополнительных возможностях по работе с css- и js-файлами, которые будут полезны ...
  • Новый функционал
    Нашел в комментариях разговор(2014 года) про расширение, написали прям в точку чего не хватает: Слишком размытый вопрос, чтоб на него можно было конкретно ответить. Возможности админа нужно расширять не для того,...
  • Как вставить блок между топиками?
    Всем привет! Столкнулся с такой проблемой: На странице есть 10 топиков, например. Мне необходимо вставить блок между 4 и 5 топиками. Как мне это сделать? Понятное дело, что необходимо будет править шаблон — это не...

3 комментария

0
На первый взгляд то что доктор прописал, нужно будет практически попробывать как это работает.
0
Такой код только добавит лишней путаницы. Есть buildFilter в нём и назначай и переназначай.
0
Этой возможности никто не отменяет. Но если нужно изменить фильтр для конкретного случая — напр., для метода GetTopicsDiscussed(), то buildFilter() мудрено будет угадать, для чего строится фильтр.
Только зарегистрированные и авторизованные пользователи могут оставлять комментарии.