Хак: Ограничение доступа к части топика по рейтингу

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

<rating min="2">Виден пользователям с рейтингом большим или равным 2.</rating>

Для последующих ссылок я использую чистую версию LiveStreet 0.3.1. Далее по пунктам:

I. Разрешаем системе использовать наш тег. Открываем файл \classes\modules\sys_text\Text.class.php:

1. Разрешаем в редакторе наш тег rating. Находим 51 строку:
$this->oJevix->cfgAllowTags(array('cut','a', 'img', 'i', 'b', 'u', 's', 'video', 'em',  'strong', 'nobr', 'li', 'ol', 'ul', 'sup', 'abbr', 'sub', 'acronym', 'h4', 'h5', 'h6', 'br', 'hr', 'pre', 'code', 'object', 'param', 'embed', 'blockquote'));
и добавляем в конец строки:
$this->oJevix->cfgAllowTags(array('cut','a', 'img', 'i', 'b', 'u', 's', 'video', 'em',  'strong', 'nobr', 'li', 'ol', 'ul', 'sup', 'abbr', 'sub', 'acronym', 'h4', 'h5', 'h6', 'br', 'hr', 'pre', 'code', 'object', 'param', 'embed', 'blockquote', 'rating'));

2. Разрешаем для нашего тега параметр min (числового типа). После 62 строки:
$this->oJevix->cfgAllowTagParams('embed', array('src' => '#image', 'type' => '#text','allowscriptaccess' => '#text', 'allowfullscreen' => '#text','width' => '#int', 'height' => '#int', 'flashvars'=> '#text', 'wmode'=> '#text'));
добавляем строку:
$this->oJevix->cfgAllowTagParams('rating', array('min' => '#int'));

3. Делаем наш параметр min обязательным. После 65 строки:
$this->oJevix->cfgSetTagParamsRequired('a', 'href');
добавляем строку:
$this->oJevix->cfgSetTagParamsRequired('rating', 'min');


На данном этапе при добавлении новости, наш тег rating не будет обрезаться, если был правильно оформлен он сам и обязательный параметр min.

II. Делаем проверку и редактирование блоков с рейтингом перед отправкой данных топика в шаблонизатор. Делает поиск вхождений тега в тексте топика, если находит, то меняет в зависимости от рейтинга на нужный нам блок. Отредактируйте в коде под свои нужды html код и текст. Открываем файл \classes\actions\ActionBlog.class.php:

1. В методе EventShowTopicPersonal() после строк 718-723:
/**
* Выставляем SEO данные
*/
$sTextSeo=preg_replace("/<.*>/Ui",' ',$oTopic->getText());
$this->Viewer_SetHtmlDescription(func_text_words($sTextSeo,20));
$this->Viewer_SetHtmlKeywords($oTopic->getTags());
вставляем следующие строки:
/**
* Проверяем доступ к контенту по рейтингу
*/
$sText = $oTopic->getText();		
preg_match_all("/<rating min=\"([0-9]*)\">(.*)<\/rating>/Ui",$sText,$aMatch,PREG_SET_ORDER);
foreach ($aMatch as $key => $value){
	if ($this->oUserCurrent and intval($aMatch[$key][1]) <= $this->oUserCurrent->getRating())
		$sText = str_replace($aMatch[$key][0], "<span class=\"rating_enable\">".$aMatch[$key][2]."</span>", $sText);
	else
		$sText = str_replace($aMatch[$key][0], "<span class=\"rating_disable\">Чтобы увидеть этот текст, необходимо иметь рейтинг более ".$aMatch[$key][1].".</span>", $sText);
}
$oTopic->setText($sText);

2. Тот же самый код, только теперь в методе EventShowTopic() после блока:
/**
* Выставляем SEO данные
*/
$sTextSeo=preg_replace("/<.*>/Ui",' ',$oTopic->getText());
$this->Viewer_SetHtmlDescription(func_text_words($sTextSeo,20));
$this->Viewer_SetHtmlKeywords($oTopic->getTags());
вставляем наш код:
/**
* Проверяем доступ к контенту по рейтингу
*/
$sText = $oTopic->getText();		
preg_match_all("/<rating min=\"([0-9]*)\">(.*)<\/rating>/Ui",$sText,$aMatch,PREG_SET_ORDER);
foreach ($aMatch as $key => $value){
	if ($this->oUserCurrent and intval($aMatch[$key][1]) <= $this->oUserCurrent->getRating())
		$sText = str_replace($aMatch[$key][0], "<span class=\"rating_enable\">".$aMatch[$key][2]."</span>", $sText);
	else
		$sText = str_replace($aMatch[$key][0], "<span class=\"rating_disable\">Чтобы увидеть этот текст, необходимо иметь рейтинг более ".$aMatch[$key][1].".</span>", $sText);
}
$oTopic->setText($sText);


В зависимости от того, хватает рейтинга для просмотра или нет, тег rating заменяется тегом span с предупреждением, либо самим контентом. Не забудьте добавить стили css. Можете подредактировать код для вывода других тегов, либо другого содержания.

На данный момент все. Позже постараюсь добавить еще пункт, в котором рассказывается, как добавить наш тег в саму панельку редактора рядом с остальными. Возможны некоторые апдейты топика, будем совершенствовать вместе.

Пример не совсем «по фен-шую». Фактически нарушаются принципы MVC модели, используемой в LS. Поэтому с удовольствием выслушаю ваши советы и предложения. Хотелось бы доработать данный хак, чтобы как можно лучше соответствовать самой LiveStreet.

12 комментариев

avatar
Круто, спасибо, не надо будет самому голову крутить =)
avatar
Подчистил код в 1 и 2 пункте раздела II. Дело было ночью, спешил…
  • Shem
  • 0
avatar
Вопрос: стоит ли парсинг текста перед отдачей в smarty реализовать не в ActionBlog.class.php, а с помощью хуков например в Text.class.php.
Правильнее ли будет такой вариант? Или может есть идеи лучше?
  • Shem
  • 0
avatar
есть парочку «но». Он пропускает ссылку если смотреть топики в ленте хороших, плохих, новых постов и т.д. )
  • mrak
  • 0
avatar
Потому-что изменяли класс блога, а не топиков.
avatar
Это «подкатная» версия. Работает только при просмотре полной новости. Попробую посмотреть, чтобы сделать и в кратких новостях подобное.
avatar
на 0.4.2 нету?(
avatar
тоже недо
avatar
livestreetcms.com/addons/view/23/
в платном плагине есть
avatar
слишком много лишнего, имхо
avatar
livestreetcms.com/addons/view/23/
в платном плагине есть
avatar
а как сделать так, чтобы пользователь не мог читать топики из блога у которого стоит ограничение по рейтингу?
Только зарегистрированные и авторизованные пользователи могут оставлять комментарии.