8 правил хорошего тона
[битрикс для начинающих]

Недавно обсуждали в сообществе для разработчиков, кому сколько доставалось хорошо сделанных проектов на битриксе. Результаты неутешительные — 1–2 в среднем ответили разработчики.

Под “хорошо” подразумевается соблюдение базовых принципов разработки веб-проектов в целом и при работе с битриксом в частности. Многие [начинающие] разработчики не знают, как делать “хорошо”.

Поэтому решил подготовить краткую заметку на эту тему.

1. Используйте компоненты

Помещайте весь php-код и шаблонизацию в компоненты.

Часто можно встретить сложный php-код прямо в индексной странице раздела или любой другой. Если редактировать такую страницу через виз. редактор, то легко можно “все сломать”, и вот основные причины:

  • виз. редактор на этапе разбора и визуализации содержимого страницы может допустить ошибки,
  • пользователь может случайно внести правки “несовместимые с жизнью” в php-код и даже не поймет этого, а все сломается.

Так быть не должно. Любой код отвечающий за бизнес-логику приложения должен быть вынесен в собственные компоненты и модули. На страницах должны располагаться только компоненты.

Такой подход позволит:

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

Материалы по теме

2. Храните данные в кеше

Результаты тяжелых вычислений и любых выборок из БД следует хранить в кеше.

Основные способы кеширования:

  • файлы,
  • memcache,
  • Redis.

Даже файлов кеш будет работать на несколько порядков быстрее, чем повторная подготовка данных. Что уж говорить про кеш в оперативной памяти.

Битрикс умеет кешировать результаты работы компонентов в файлах и в memcache. Для Redis’a можно написать свой адаптер. PHP акселераторы для этих целей не рассматриваем - пусть занимаются своей основной задачей.

В итоге место хранения кеша определяется настройками в файле .settings.php.

// Создаем объект для работы с кешем (способ кеширования задается в .settings.php)
$obCache = Bitrix\Main\Data\Cache::createInstance();

// Время жизни кеша, в секундах
$timeout = 3600;

// Уникальный ключ для кешированных данных
// на основании входных данных
$cacheKey = md5( $arParams );

// Путь относительно /bitrix/cache/
// Т.о. можно сбросить часть, а не весь кеш проекта.
// Для этого надо удалить папку /bitrix/cache/my/subdir/
$cacheDir = "/my/subdir/";


// Если кэш валиден
if( $obCache->InitCache( $timeout, $cacheKey, $cacheDir ) )
{
    // Извлекаем данные из кэша
    $result = $obCache->GetVars();
}
// Если кэш невалиден
elseif( $obCache->StartDataCache()  )
{
    // Тяжелые вычисления
    $result = hardWork();

    // Сохраняем данные в кэш
    $obCache->EndDataCache( $result );
}

// Работаем с данными ( $result )

Материалы по теме

3. Используйте модули

Выносите сложную бизнес-логику в модули.

Модуль - это модель данных и API для доступа к этим данным. Статические методы классов модуля могут вызываться в компонентах, шаблонах, других модулях.

Модуль может состоять только из файлов с классами и не иметь интерфейса в админке или публичке. Главное, что код будет логически сгруппирован и размещен согласно логике битрикса. Модули намного легче поддерживать и расширять.

Материалы по теме

4. Следите за оформлением кода

Основные требования к оформлению кода, кстати довольно простые:

Именование

Названия переменных, констант, классов и функций - должно быть осмысленным.

Выравнивание

Следите за табуляцией во вложенных блоках.

Отступы

Разделяйте логические блоки кода одной пустой строкой.

Комментарии

По большому счету код должен быть самодокументируемым. Этому способоствют семантичные названия переменных, методов и тд.

Комментарии размещайте над кодом.

/*
* Отправляем почтовые уведомления после регистрации через соц. сети,
* так как по умолчанию они не отправляются.
* В коде регистрации через соц. сети видно, что используется просто метод CUser->Add(...).
* */
\Bitrix\Main\EventManager::getInstance()->addEventHandler(
    "main",
    "OnAfterUserAdd",
    "socServdRegistrHandler"
);

или

// Отправляем почтовые уведомления после регистрации через соц. сети,
// так как по умолчанию они не отправляются.
// В коде регистрации через соц. сети видно, что используется просто метод CUser->Add(...).
\Bitrix\Main\EventManager::getInstance()->addEventHandler(
    "main",
    "OnAfterUserAdd",
    "socServdRegistrHandler"
);

Однако стоит добавлять комментарии, когда логика нетривиальна. Пожалуйста, не пишите “что здесь происходит”, а пишите “почему это происходит”. Вы пишите код для людей, которые будут работать с ним после вас, представьте себя на их месте и какие вопросы у них возникнут.

Пишите комментарии к классам - какие задачи в целом решает данный класс. Пишите комментарии к методам - в стили PhpDoc, описывайте суть метода, входные и выходные параметры и тд.

Вынесение кода в классы и функции

Следите за порядком в вашем коде с самого начала. Группируйте код. Используйте код повторно, но не копируйте его, а оформляйте его в виде отдельного метода и тд.

Классы

Один класс - один файл. Больше ничего не должно быть в файле с классом. Файл должен называться так же, как и класс:

// SomeClass.php
class SomeClass {
    // some code
}

Содержимое файла init.php

Не захламляйте файл init.php тоннами строк кода.

Подключайте там только “заголовочные” файлы:

  • events.php - регистрация обработчиков событий,
  • constants.php - константы,
  • functions.php - общие функции.
// AddMessage2Log() будет записывать логи сюда и разбивать их по дням
define("LOG_FILENAME", $_SERVER["DOCUMENT_ROOT"] . "/_logs/bx/" . date("Y_m_d") . ".log");

// автозагрузчик для всех классов проекта с соблюдением стандарта PSR-4
spl_autoload_register(function ($class) {
    $class = str_replace('\\', '/', $class);

    $path = $_SERVER["DOCUMENT_ROOT"] .'/local/lib/'.$class.'.php';

    if (is_readable($path)) {
        require_once $path;
    }
});

// константы
require_once($_SERVER["DOCUMENT_ROOT"] . "/local/php_interface/constants.php");

// общие функции
require_once($_SERVER["DOCUMENT_ROOT"] . "/local/php_interface/functions.php");

// регистрация обработчиков событий
require_once($_SERVER["DOCUMENT_ROOT"] . "/local/php_interface/events.php");

Подключение классов

Когда классов в проекте мало — можно подключить их все вручную сразу или по мере необходимости.

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

В этом случае удобнее и оптимальнее использовать автозагрузку классов.

Рассмотрим два основных способа:

  • spl_autoload_register(...) — на уровне php,
  • Loader::registerAutoLoadClasses(...) — на уровне ядра битрикса.

Между ними есть принципиальная разница в том, как они подключают файлы.

registerAutoLoadClasses — требует явно прописать список всех классов, которые могут быть подключены и пути к ним.

spl_autoload_register — на основании имени класса динамически вычисляет путь где хранится файл и подключает его.

Материалы по теме

5. Следите за расположением кода

Используйте папку local. Это особенно удобно при использовании системы контроля версий. Начиная с 14 версии продукта, появилась поддержка папки /local/. В ней можно размещать весь пользовательский код проекта:

  • шаблоны сайтов и компонентов,
  • компоненты,
  • модули,
  • и прочее.

Для классов проекта используйте папку /local/lib/. В остальном по аналогии.

Материалы по теме

6. Работайте на копии проекта

Это общее правило для любых проектов.

Разработка на боевом сайте неизбежно связана с неработоспособностью сайта во время отладки, ошибками и иногда даже с падением сервера. Зачем рисковать своей репутацией и тратить нервы клиента - для него ошибка на сайте это конец света :) Так часто работают новички - они не знают как работать по-другому. И так работают лентяи и халтурщики - они думают, что так быстрее, но это не так.

Занимайтесь разработкой на локальной копии проекта - это очень удобно, весь проект, как на ладони. Особенно, если работать в IDE, а не в блокноте :)

Я работаю в PhpStorm, он идеально подходит для [локальной] разработки сайтов. Преимуществ очень много и трудно выделить несколько главных.

  • Подсветка синтаксиса
  • Подсказка и автозаполнение
  • Просмотр описания объектов – PhpDoc
  • Быстрый просмотр исходного кода функции
  • Переход к определению
  • Подсказка аргументов функции
  • Поиск использования функции
  • Поиск по всему проекту – то самое «умение быстро разбираться в чужом коде»
  • Навигация по открытым файлам и панелям
  • Работа с кодировками
  • Интеграция с Git
  • Построчная отладка PHP приложений
  • Поддержка TODO директив
  • Встроенный терминал
  • Логическая структура файла
  • Файловый менеджер
  • Встроенный FTP клиент
  • Публикация изменений на удаленный сервер
  • Синхронизация файлов с удаленным сервером
  • Работа с БД
  • Инструменты для рефакторинга
  • Быстрый переход к нужному файлу / папке по приблизительному пути
  • Навигация по истории контекста (переходы курсора)
  • Быстрый переход к классу / функции по имени
  • Поиск любых операций IDE по названию
  • Локальная история изменений
  • Навигация по изменным местам в файле (между коммитами)
  • Мощная система навигации по проекту
  • Закладки прямо в коде
  • Закладки файлов, можно именованными группами
  • Сворачивание произвольных участков кода
  • Сохранение / загрузка контекста
  • Интеграция с системами учета задач
  • Полноэкранный режим
  • Несколько проектов одновременно
  • Упрощенный режим для слабых компьютеров
  • Множество плагинов
  • Проверка синтаксиса, стиля кода и много чего еще
  • Навигация по открытым вкладкам через hot keys
  • Быстрый поиск всего (файлов/функций/классов) по всему проекту
  • Быстрая навигация по структуре документа
  • И еще множество крутых штук

7. Используйте Git

Используйте систему контроля версий (СКВ), например Git.

Много разработчиков, до сих пор, не понимают необходимость контролировать изменения в файлах с исходным кодом. А многие и вовсе не знают что такое СКВ, например Git, и как ей пользоваться.

К сожалению, СКВ решает задачу только применительно к файлам. Изменения в базе данных с помощью СКВ не отследить. На текущий момент СКВ для БД — это почти утопия.

Сейчас мы рассмотрим только основные причины для использования СКВ и настройку исключений.

Почему нужно использовать систему контроля версий:

  • одновременная работа нескольких человек над проектом
  • возможность быстро обнаружить и откатить, все не зафиксированные изменения
  • возможность быстро откатить ошибочные, уже зафиксированные, изменения
  • история всех изменений в проекте, с указанием даты и авторов
  • возможность изучить процесс развития проекта

Однако не все файлы следует держать под контролем, например:

  • ядро битрикса,
  • файлы IDE,
  • временные файлы,
  • файлы не относящиеся к проекту.

Чтобы скрыть какие-либо файлы из под бдительного ока СКВ, существует служебный файл .gitignore, в котором содержаться правила исключения.

Предлагаю вам свой образец файла .gitignore при работе с битриксом:

# --- files ---
.DS_Store
Thumbs.db
/nbproject/
/.idea/
/*.sublime-project
/*.sublime-workspace

# --- core ---
/bitrix/*
!/bitrix/components
/bitrix/components/bitrix
!/bitrix/modules
/bitrix/modules/*
!/bitrix/templates
!/bitrix/php_interface
/bitrix/php_interface/after_connect.php
/bitrix/php_interface/after_connect_d7.php
/bitrix/php_interface/dbconn.php
!/bitrix/admin/
/bitrix/admin/*

# --- project modules ---
!/bitrix/modules/project*

# --- project admin scripts ---
# any project pages
!/bitrix/admin/project*
# 1c exchange custom script
!/bitrix/admin/1c_exchange_custom.php

# --- media files ---
/upload
/video
/files
/i

# --- log files ---
/_logs/
*.log
log.txt

# --- archives ---
*.tar*
*.zip*
*.rar*

# --- mysql files ---
/*.sql

# --- other ---
*.tmp
/_*
/test/
/t.php
test.php
robots.txt
sitemap*.xml
/*.txt
web.config
.htaccess.restore
*old*
*/*cache*/

cgi-bin/
google*.html
mywot*.html
wmail*.html
yandex*.html
php.ini

restore.php
bitrix_server_test.php
bitrixsetup.php

phpMyAdmin
pma
adminer.php
adminer.css

bx_1c_import.php
bx_1c_import_lite.php
/webstat

# allows fast hide any files or folders from under git's eyes
*_gitignore_*
    

Материалы по теме

8. Завершайте проект

Завершайте работу над проектом грамотно.

Чтобы избежать случайных ошибок и проблем:

Настройка логов

Имея под рукой логи проще разобраться с возникшими проблемами и выяснить, когда и почему они начались.

Речь о логах функции AddMessage2Log(...) и секции exception_handling из файла .settings.php.

Чтобы в логах было удобнее ориентироваться — можно группировать их по датам. Формат даты "Y_m_d" — позволит файлам автоматически сортироваться в хронологическом порядке.

Все логи удобно держать в одном месте, например в папке /_logs/bx/.

В целях защиты следует закрыть доступ к папке с логами по http — настраивается в .htacces, и/или добавить к названию файла уникальный для проекта постфикс.

Папку для логов надо предварительно создать и убедиться, что битрикс (веб-сервер) имеет права на запись в нее.

define("LOG_FILENAME", $_SERVER["DOCUMENT_ROOT"] . "/_logs/bx/" . date("Y_m_d") . "_PROJECT_UNIQUE_POSTFIX.log");
'exception_handling' => array (
  'value' => array (
      'debug' => false, // disables error output to screen
       // ошибки для вывода в лог
      'handled_errors_types' => E_ALL & ~E_NOTICE & ~E_STRICT & ~E_WARNING,
      'exception_errors_types' => E_ALL & ~E_NOTICE & ~E_WARNING & ~E_STRICT & ~E_COMPILE_WARNING,
      'ignore_silence' => true,
      'assertion_throws_exception' => true,
      'assertion_error_type' => 256,
      'log' => array (
          'settings' => array (
              'file' => "_logs/bx_error/" . date("Y_m_d") . "_PROJECT_UNIQUE_POSTFIX.log",
              'log_size' => 1000000, // ~ 1Mb per file
          ),
      ),
  ),
  'readonly' => true,
),

Материалы по теме

Дополнительные материалы

Подведем итоги

Я постарался собрать основные правила хорошего тона, о которых следует знать начинающим разработчикам, и не забывать опытным. Я уверен, что соблюдение этих правил поднимет качество, как при повседневной работе проекта, так и при его модернизации.

Надеюсь теперь сайтов на битриксе, которые будут сделаны “хорошо”, будут работать быстро и легко поддерживаться станет больше.

Присоединяйтесь к нам в Telegram чат для битрикс-разработчиков и участвуйте в обсуждениях.

Комментарии

Форма для связи

Контакты
Telegram:

по запросу

Skype:

по запросу

Телефон:

по запросу

Город:

Санкт-Петербург