Приветствую всех на Хабре. Я Сергей Михнов, CEO компании Пуск, интегратора Битрикс24. В свое время мы выбрали особый путь – специализацию на коробочной версии Битрикс24. В коммуникациях на сайте или паблишинг площадках мы всегда пишем, что дорабатываем коробку бережно. Решил поделиться, что это значит для нас.

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

Для начала поделюсь требованием к доработкам: 

  • Ядро не модифицируется.

  • Шаблон портала / компоненты / шаблоны компонентов не копируется.

  • Все доработки находятся в папке local, с соблюдением правил описанных в разделе «Организация кода в папке local».

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

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

  • К каждой доработке есть инструкция по переносу без участия исполнителя. 

  • Запуск нужных скриптов.

  • Подробная инструкция какие изменения нужно произвести на портале. Например: создать пользовательские поля с указанием всех нужных параметров (название, тип, символьный код, и т.д.).

  • Файлы логов располагаются в папке logs или за пределами директории портала. Также предусмотрены механизмы отключения и ротация файлов.

  • События агентов логируются в «Журнале событий».

  • Ошибки в блоках БП логируются в «Журнал бизнес-процесса»

Правила оформления кода

Контроль качества кода производится при помощи платформы анализа Sonar. Проверка осуществляется посредством интеграции кода в ветку develop, а также при создании / изменении запросов на слияние. 

  • Соблюдается стандарт PSR-12. 

  • Для массивов используется сокращенная запись.

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

Для качественной и комфортной работы требуется:

  • Установить плагин SonarLint, который нужно будет подключить к порталу

  • В IDE настроить code style 

В этом случае замечания будут отображаться в среде разработки, а большая часть будет автоматически устраняться IDE.

Также в проекте устанавливается «php-cs-fixer», который правит код в соответствии с конфигурацией local/.php-cs-fixer.php.

Для запуска в директории local выполняется команда «php ./vendor/bin/php-cs-fixer fix», и только после этого следует commit. В этом случае замечания будут отображаться в среде разработки, а большая часть будет автоматически устраняться IDE.

Это правило является основополагающим.

Теперь рассмотрим детально все нюансы осуществления качественных доработок для технических специалистов. 

#NOSONAR

Отключение проверок допускается в следующих случаях:

  • Подключение файлов.

  • Название классов которые соответствуют требованиям Bitrix Framework.

  • Легаси код.

Реализация задач (Git)

Для реализации проектов наша компания использует «git-flow».
Перед выполнением задачи мы создаем ветку от develop с id задачи на портале.

Коммиты в процессе именуются по следующему шаблону:

«[P-{id}] {summary} {note }», где

{id} – id задачи на портале;

{summary} – название задачи на портале;

{note} — дополнительная информация, при необходимости.

После завершения работы создается запрос на слияние в ветку develop, с включенными опциями «Удалить исходную ветку» и  «Объединить историю коммитов». А вслед за созданием запроса на слияние автоматически запустится проверка «sonarqube-check». Если проверка завершится успешно —  проводится ревью кода. 

Если проверка имеет негативный исход —  задача не рассматривается, пока замечания не будут устранены. После их исправления в ходе ревью, код переносится на тестовый стенд по предоставленной инструкции к задаче (по умолчанию это переустановка модуля pusk.ext), и проводится проверка функционала. В случае возникновения замечаний задача возвращается на доработку. 

Перенос доработок

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

  • Исполнитель реализует доработку и делает запрос на слияние в ветку develop.

  • После прохождения автоматической проверки кода и ревью доработка переносится на Test. 

  • Происходит тестирование доработки. Если появляются замечания по описанному в задаче функционалу или ломается уже реализованный функционал, то она возвращается на доработку (возвращаемся к шагу 1). 

  • Задача завершается.

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

Организация кода в папке local

Структура каталога выглядит следующим образом:

Допускается

  • Создание дополнительных модулей

  • Подключение через автозагрузку каталога классов с соблюдением PSR-4.

Ниже подробнее разберем функционал каждой папки

Activities

Пользовательские блоки для бизнес-процессов

Components

Папка с компонентами. На первом уровне пространство имен должно соответствовать id нашего модуля с которым связан компонент. Они реализуются только на классах (через component.php  категорически запрещено). 

Js

Содержит расширения (extensions). Используется во всех случаях когда нужен js код, который будет использоваться в нескольких компонентах или для подключения на событиях.

Modules / pusk.ext

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

Agent

Содержит агенты, реализованные в модуле.

Cli

Содержит все консольные скрипты, реализованные на базе пакета symfony/console. 

Handler

Содержит обработчики событий. На первом уровне мы создаём папку с id модуля к которому относится событие. 

Infrastructure

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

Orm

Содержит классы, которые описывают структуру таблиц в базе данных.

ResultModifier

Содержит классы, которые используются при кастомизации компонентов через шаблон. (См. раздел «templates»).

ServiceLocator

Содержит классы для подмены через сервис локатор.

Php_interface

Данный каталог должен содержать исключительно подключение файлов или конфигурирование объектов. Реализация логики в нем категорически запрещена. 

В файле init.php подключаются нужные файлы или модули.

При потребности подмены классов через сервис локатор необходимо использовать файл local/php_interface/include/crm_services.php. В нем реализуется только регистрация классов, вся логика реализуется в пространстве имен Pusk\Ext\ServiceLocator модуля. 

Templates

В файле components.php описана логика встройки в компонент перед выводом шаблона. Для мы создаем в папке templates/.default/components/bitrix аналогичную структуру целевого компонента. Для комплексных компонентов вместо файла template.php указывается соответствующий файл. 

template.php — содержит только проверку на подключение из ядра (B_PROLOG_INCLUDED). Он нужен для идентификации шаблона и не будет подключаться при его обработке.

result_modifier.php в этом файле реализуется необходимая логика. Если число строк кода более 5 — она выносится в Pusk\Ext\ResultModifier

Tests

Содержит тесты. Структура соответствует пространству имен тестируемых классов.


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

Комментарии (2)


  1. rpsv
    07.06.2023 05:25
    +1

    В целом вроде все хорошо, но вот как бы не забыть про безопасность: в данной конфигурации у вас торчат наружу тесты, композер, cli.php.
    Любой может спокойной зайти и подчерпнуть нужную для себя информацию.

    Нехорошо как-то :/


  1. rpsv
    07.06.2023 05:25
    +1

    Они реализуются только на классах (через component.php категорически запрещено).

    Что за категоричность? А если мне нужно только подключить шаблон?

    Infrastructure
    Содержит все классы, которые используются при установке/удалении модуля или относятся к базовым функциям модуля.

    Название директории не совсем соответствует содержимому. Инфраструктура это все же про другое. Ну и как минимум интересно: а какие классы там используются?

    Php_interface
    В файле init.php подключаются нужные файлы или модули.

    А зачем для каждого хита подключать модули?

    При потребности подмены классов через сервис локатор необходимо использовать файл local/php_interface/include/crm_services.php. В нем реализуется только регистрация классов, вся логика реализуется в пространстве имен Pusk\Ext\ServiceLocator модуля.

    Ну в данном файле видимо сервисы CRM переопределяются, и тоже непонятно зачем делать это на каждом хите.
    Правильней было бы подвязаться на include.php в своем модуле и заменять сервисы на те, которые нужны вам. Неважно подключен модуль уже или нет, сервисы не перезаписываются.

    Templates
    В файле components.php описана логика встройки в компонент перед выводом шаблона

    В файле или директории? :)

    ResultModifier

    Содержит классы, которые используются при кастомизации компонентов через шаблон. (См. раздел «templates»).

    Не самое лучшее решение. У вас класс должен решать конкретную задачу, а не быть прибитым к конкретному компоненту. А как быть если такая же логика мне нужна в соседнем компоненте? Использовать класс-модифайер из другого компонента, или копи-пастить? Получается вопрос из разряда какой стул выбрать :)

    result_modifier.php  в этом файле реализуется необходимая логика. Если число строк кода более 5 — она выносится в Pusk\Ext\ResultModifier

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