+0.21
Рейтинг
1.25
Сила

Vlad

К вопросу о правильном использовании тегов H1-H6 в структуре шаблонов сайтов на LiveStreet

В свете возможного скорого выхода новой версии движка LiveStreet хотелось бы обратить внимание уважаемых разработчиков движка, разработчиков шаблонов и сообщества на вопрос о правильном использовании тегов заголовков H1-H6 в структуре шаблонов и редакторе топиков сайтов на LiveStreet.

К вопросу о правильном использовании тегов H1-H6 в структуре шаблонов сайтов на LiveStreet

Почему это важно:

Вы можете сказать, да надоели уже эти сеошники со своими  хитростями и тонкостями. Но дело в том, что за неправильное использование тегов заголовков H1-H6 (в частности) поисковые системы Яндекс и Googleнакладывают на сайт фильтр за переоптимизацию/переспам и понижают позиции сайта в поисковой выдаче, что ведет к снижению трафика на сайт из результатов поиска. В Google, в частности, этот фильтр является частью известного фильтра Panda. В Яндексе фильтр в шутку назвали «Ты спамный». Он начал работать особо активно где-то с июля 2013 года и накладывается на сайт автоматически.

Читать дальше →

Работа в различных окружениях (devel, production и т.п.)

В новой версии LS мы изменили механизм работы определения окружения и загрузки соответствующих конфигов (config.local.php и config.stable.php). Если раньше эти конфиги всегда подгружались(просто перезаписывая данные), то сейчас подключается только нужный конфиг.

Логику работы мы взяли из популярного фреймворка Laravel. Теперь у нас есть в корне сайта каталог /bootstrap/ с файлом start.php. Именно в этом файле задается механизм определения текущего окружения:
$sEnv=Engine::DetectEnvironment(array(
                                 'production' => array('your-machine-name'),
                             ));

В метод DetectEnvironment передается список окружений (ключи массива) и в качестве значений список хост-неймов серверов. Текущий хост-нейм можно посмотреть в nix командой hostname. Как альтернатива в метод DetectEnvironment вместо списка можно передать функцию и определить в ней свою логику:
$sEnv=Engine::DetectEnvironment(function(){
    // здесь ваша логика
    return 'devel';
});

В зависимости от текущего окружения будет загружен необходимый конфиг (если он существует). Например, для окружения «production» загрузится /application/config/config.production.php Этот же механизм работает и для плагинов! Будет подгружен конфиг /application/config/plugins/[plugin_name]/config.production.php

По умолчанию (если не удалось определить окружение) подключается окружение «local». Дополнительно зарезервировано окружение «testing», которое используется для юнит-тестов. Активируется оно довольно просто — достаточно перед подключением файла /bootstrap/start.php создать переменную $bUseEnvironmentTesting=true;.

Индексация от яндекс по тэгам

Я сейчас может задам тупой вопрос, но я его задам…
Сайту месяц. Яндекс проиндексировал все топики что были написаны, но при поиске, в выдаче, показывает страницы с тэгами. То есть все тэги что были написаны к топикам так или иначе в выдаче яндекса, но сами топики с ключевиками, заголовками и пр. в выдаче отсутствуют. Гугл же ищет сами топики и находит. В чем может быть причина?

Вывести количество пользователей на главную страницу

Помогите пожалуйста Вывести количество пользователей на главную страницу.
Получил статистику
/**
* Статистика кто, где и т.п.
*/
$aStat=$this->User_GetStatUsers();
/**
* Загружаем переменные в шаблон
*/
$this->Viewer_Assign('aStat',$aStat);

и поместил в ActionIndex.class.php.
Вставил переменную в шаблон {$aStat.count_all}. Не работает.
Помогите пожалуйста.

Обновление модулей кеширования и логирования

В разрабатываемой версии мы переработали модули Cache и Logger — код стал проще, меньше и более функционален.

Модуль кеширования (Cache)
Реализован новый принцип работы с разными бекендами, теперь каждый бекенд представляет из себя отдельную сущность (наследуется от ModuleCache_EntityBackend). Такой подход позволяет легко добавлять новые типы бекендов — достаточно создать сущность с нужным типом кеша, например, вот так выглядит XCache:
/**
 * Бекенд xcache
 */
class ModuleCache_EntityBackendXcache extends ModuleCache_EntityBackend {
	/**
	 * Проверяет доступность использования текущего бекенда
	 *
	 * @return mixed
	 */
	public function IsAvailable() {
		if (extension_loaded('xcache')) {
			return true;
		}
		return 'The xcache extension must be loaded for using this backend!';
	}
	/**
	 * Проверяет доступность использование мульти-get запросов к кешу (указывать сразу несколько ключей)
	 *
	 * @return mixed
	 */
	public function IsAllowMultiGet() {
		return true;
	}
	/**
	 * Инициализация бекенда
	 *
	 * @param array $aParams
	 *
	 * @return mixed
	 */
	public function Init($aParams=array()) {
		require_once(LS_DKCACHE_PATH.'Cache/Backend/TagEmuWrapper.php');
		require_once(LS_DKCACHE_PATH.'Zend/Cache/Backend/Xcache.php');
		$aConfig=Config::Get('xcache');

		$oCahe = new Zend_Cache_Backend_Xcache(is_array($aConfig) ? $aConfig : array());
		if (isset($aParams['stats_callback'])) {
			$this->oCacheBackend=new Dklab_Cache_Backend_TagEmuWrapper(new Dklab_Cache_Backend_Profiler($oCahe,$aParams['stats_callback']));
		} else {
			$this->oCacheBackend=new Dklab_Cache_Backend_TagEmuWrapper($oCahe);
		}
	}
	/**
	 * Получить значение из кеша
	 *
	 * @param string $sName	Имя ключа
	 * @return mixed|bool
	 */
	public function Get($sName) {
		return $this->oCacheBackend->load($sName);
	}
	/**
	 * Записать значение в кеш
	 *
	 * @param  mixed  $mData	Данные для хранения в кеше
	 * @param  string $sName	Имя ключа
	 * @param  array  $aTags	Список тегов, для возможности удалять сразу несколько кешей по тегу
	 * @param  int|bool    $iTimeLife	Время жизни кеша в секундах
	 * @return bool
	 */
	public function Set($mData,$sName,$aTags=array(),$iTimeLife=false) {
		return $this->oCacheBackend->save($mData,$sName,$aTags,$iTimeLife);
	}
	/**
	 * Удаляет значение из кеша по ключу(имени)
	 *
	 * @param string $sName	Имя ключа
	 * @return bool
	 */
	public function Delete($sName) {
		return $this->oCacheBackend->remove($sName);
	}
	/**
	 * Чистит кеши
	 *
	 * @param string $cMode	Режим очистки кеша
	 * @param array $aTags	Список тегов, актуально для режима Zend_Cache::CLEANING_MODE_MATCHING_TAG
	 * @return bool
	 */
	public function Clean($cMode=Zend_Cache::CLEANING_MODE_ALL,$aTags=array()) {
		return $this->oCacheBackend->clean($cMode,$aTags);
	}
}

На данный момент в стандартном комплекте идет поддержка File, XCache и Memcached. Также добавлены дополнительные бекенды — FileOrm и Life. FileOrm служит для отдельного файлового кеширования схем таблиц в БД, автоматически применяется в функционале ORM. Life — это сохранение данных на время выполнения скрипта, т.е. аналог паттерна Registry. Применяется он в методах GetLife и SetLife.

Читать дальше →

Как расширить файл шаблона, если в нем не предусмотрено хуков?..

Проблема в следующем — есть файл topic_part_header, но в нем не предусмотрено хуков, которые бы позволили добавить туда что-нибудь. Но туда нужно добавить ссылку на новое действие с топиком. Подскажите, пожалуйста, как быть? Лезть в шаблон и менять не хочется, хотелось бы через плагин.

Текущая коллекция расширений от stfalcon

Доброго времени суток! Хотел бы поделиться списком текущей коллекцией плагинов.
Пользуйтесь на здоровье и пожалуйста оставляйте ваши мнения и отзывы.
 
 

Плагин «SEO Premium»

Модуль SEO Premium, расширяющий возможности модуля SEO, поднимает оптимизацию сайта для поисковых систем на новый уровень. Этот модуль дает возможность кастомизации полей для ключевых слов (keywords), описания (description) и заголовка (title) в топиках и блогах.


Читать дальше →

Дополнительные поля - использование в плагинах

В новой разрабатываемой версии LiveStreet есть функционал дополнительных (пользовательских) полей. Сейчас он задействован для топиков. Суть сводится к удобной возможности добавлять в различные объекты новые поля разных типов.

Сейчас поддерживаются следующие типы полей:
  • Целое число
  • Дробное число
  • Строка
  • Текст
  • Чекбокс
  • Дата
  • Выпадающий список
  • Теги
  • Ссылка на видео
  • Файл
  • Изображение

Постепенно мы наращиваем функционал и количество типов.
За весь функционал по полям отвечает модуль Property. Рассмотрим пример подключения функционала дополнительных полей к плагину «Статьи» на базе ORM.

Читать дальше →

Хлебные крошки

Приветствую, подскажите пожалуйста как правильно сделать хлебные крошки? Код ниже не хочет работать, если его вставить в верх страницы. то ничего не отображается ниже него.

<a href="{cfg name='path.root.web'}">Главная</a> -> <a href="{$oBlog->getUrlFull()}" class="topic-blog">{$oBlog->getTitle()|escape:'html'}</a> -> <a href="{$oTopic->getUrl()}">{$oTopic->getTitle()|escape:'html'}</a>

Мультизагрузка изображений

Простой (самый простой) способ реализовать мультизагрузку картинок.

В шаблоне правим window_load_img.tpl, делаем массив img_file[] и дописываем multiple
<input type="file" name="img_file[]" id="img_file" value="" class="input-text input-width-full" multiple />


И ActionAjax.class.php, вот функция EventUploadImage() целиком
	/**
	 * Загрузка изображения
	 *
	 */
	protected function EventUploadImage() {
		/**
		 * Т.к. используется обработка отправки формы, то устанавливаем тип ответа 'jsonIframe' (тот же JSON только обернутый в textarea)
		 * Это позволяет избежать ошибок в некоторых браузерах, например, Opera
		 */
		$this->Viewer_SetResponseAjax('jsonIframe',false);
		/**
		 * Пользователь авторизован?
		 */
		if (!$this->oUserCurrent) {
			$this->Message_AddErrorSingle($this->Lang_Get('need_authorization'),$this->Lang_Get('error'));
			return;
		}
		$sFile=null;
                
                
                if (isPost('img_url') && $_REQUEST['img_url']!='' && $_REQUEST['img_url']!='http://') {
                        /**
                         * Загрузка файла по URl
                         */
                        $sFile=$this->Topic_UploadTopicImageUrl($_REQUEST['img_url'],$this->oUserCurrent);
                        switch (true) {
                                case is_string($sFile):

                                        break;

                                case ($sFile==ModuleImage::UPLOAD_IMAGE_ERROR_READ):
                                        $this->Message_AddErrorSingle($this->Lang_Get('uploadimg_url_error_read'),$this->Lang_Get('error'));
                                        return;

                                case ($sFile==ModuleImage::UPLOAD_IMAGE_ERROR_SIZE):
                                        $this->Message_AddErrorSingle($this->Lang_Get('uploadimg_url_error_size'),$this->Lang_Get('error'));
                                        return;

                                case ($sFile==ModuleImage::UPLOAD_IMAGE_ERROR_TYPE):
                                        $this->Message_AddErrorSingle($this->Lang_Get('uploadimg_url_error_type'),$this->Lang_Get('error'));
                                        return;

                                default:
                                case ($sFile==ModuleImage::UPLOAD_IMAGE_ERROR):
                                        $this->Message_AddErrorSingle($this->Lang_Get('uploadimg_url_error'),$this->Lang_Get('error'));
                                        return;
                        }

                        if ($sFile) {                        
                                $sText=$this->Image_BuildHTML($sFile, $_REQUEST);
                        }

                } else {

                        foreach ($_FILES['img_file'] as $k=>$v){
                           if(is_array($v)){
                               foreach ($v as $sk=>$sv){ 
                                        $arr[$sk][$k]=$sv;
                                }
                               }
                            }

                        $sText = "";

                        foreach ($arr as $_FILES['img_file']) {

                                /**
                                 * Был выбран файл с компьютера и он успешно зугрузился?
                                 */
                                if (is_uploaded_file($_FILES['img_file']['tmp_name'])) {

                                        if(!$sFile=$this->Topic_UploadTopicImageFile($_FILES['img_file'],$this->oUserCurrent)) {
                                                $this->Message_AddErrorSingle($this->Lang_Get('uploadimg_file_error'),$this->Lang_Get('error'));
                                                return;
                                        }
                                        /**
                                         * Если файл успешно загружен, формируем HTML вставки и возвращаем в ajax ответе
                                         */
                                        if ($sFile) {
                                                $sText.=$this->Image_BuildHTML($sFile, $_REQUEST);
                                        }

                                }	

                        } //foreach

                }

		$this->Viewer_AssignAjax('sText',$sText);		
		
	}


такие дела