Непрерывная интеграция для PHP-проектов с помощью PHP Censor

· 978 words · 5 minute read

В настоящий момент получила широкое распространение практика Continuous integration (CI) (а так же практики Continuous Deployment и Continuous Delivery, которые ей сопутствуют), которая позволяет запускать различные проверки кода и тесты автоматически. Тем самым гарантируется непрерывный контроль качества и работоспособности кода, в отличии от избирательных ручных запусков тестов и проверок.

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

Существует множество различных Continuous integration решений на разных языках, каждое из которых обладает собственными особенностями, а так же областью применения. К ним относятся такие решения, как: Travis CI, Jenkins, TeamCity, PHPCI и другие.

В данной статье я бы хотел рассказать про еще один CI-сервер, - PHP Censor. Это приложение является форком PHPCI, который уже довольно давно активно не развивается.

PHP Censor, так же как и его прародитель, является CI-сервером с открытым исходным кодом написанным на PHP для максимального облегчения сборки PHP-проектов. В частности, можно собрать проект, который вообще не имеет конфигурационного файла, в таком случае будет использован базовый набор плагинов, которые можно запустить с базовой конфигурацией (проверки на дубликаты в коде, проверки стиля кода, тесты и т.д.).

PHP Censor является self-hosted решением, то есть должно быть установлено самостоятельно на свой собственный сервер.

Системные требования 🔗

Для того, чтобы развернуть свой инстанс PHP Censor необходим сервер (виртуальная машина или контейнер), соответствующий следущим требованиям:

  • Unix-подобная операционная система (Windows не поддерживается);
  • Доступен PHP 5.6+ (С поддержкой OpenSSL и включенными функциями: exec(), shell_exec() and proc_open());
  • Доступен веб-сервер (Nginx, Apache или любой другой);
  • Доступна база данных MySQL или PostgreSQL;
  • Доступна очередь Beanstalkd (Очередь необходима только, если вы запускаете сервер в режиме демона, запуск по крону не требует очереди);

Возможности 🔗

Ниже приведен краткий список возможностей PHP Censor-а:

  • Может получать исходные коды проектов из: Github, Bitbucket, Gitlab, Git, Mercurial, SVN или локальной директории;
  • Может запускать сборки по push-у/commit-у в репозиторий;
  • Может устанавливать и очищать тестовые БД для PostgreSQL, MySQL и SQLite;
  • Может устанавливать зависимости для проекта c помощью Composer-а;
  • Может запускать тесты для PHPUnit, Atoum, Behat, Codeception и PHPSpec;
  • Может проверять ваши исходные коды с помощью Lint, PHPParallelLint, Pdepend, PHPCodeSniffer, PHPCpd, PHPCsFixer, PHPDocblockChecker, PHPLoc, PHPMessDetect, PHPTalLint и TechnicalDept;
  • Может запускать другие доступные плагины, включая: Campfire, CleanBuild, CopyBuild, Deployer, Env, Git, Grunt, Gulp, PackageBuild, Phar, Phing, Shell и Wipe;
  • Может отправлять оповещения о сборке по различным каналам связи, включая: Email, XMPP, Slack, IRC, Flowdock, HipChat and Telegram;
  • Может авторизовывать пользователей через внешний LDAP-сервер;

Установка 🔗

Самый простой способ установить приложение, - это развернуть его в docker-контейнерах, используя репозиторий php-censor/docker-php-censor.

Чтобы установить PHP Censor у себя на сервере вручную нужно выполнить следующую последовательность действий:

  • Получить последнюю версию дистрибутива PHP Censor можно несколькими способами. Проще всего загрузить приложение через Composer:

    cd /var/www
    composer create-project php-censor/php-censor php-censor.local --keep-vcs
    
  • После выполнения этой команды в директории /var/www/php-censor.local появится последняя версия дистрибутива со всеми необходимыми зависимостями. Дистрибутив так же можно скачать вручную с релизной страницы на GitHub-е проекта, но тогда придется установить зависимости проекта самостоятельно с помощью Composer-а (Обычно команда для установки зависимостей выглядит примерно так: composer install).

  • Необходимо создать пустую БД (MySQL или PostgreSQL) и пользователя для работы с ней.

  • Необходимо запустить команду установки приложения, попутно отвечая на вопросы о подключении к БД, очереди и прочих конфигурационных данных:

    cd /var/www/php-censor.local
    ./bin/console php-censor:install
    
  • Далее необходимо настроить виртуальный хост приложения на сервере. Например, примерно так будет выглядеть конфигурация виртуального хоста php-censor.local для Nginx:

    server {
        listen *:80;
    
        server_name php-censor.local www.php-censor.local;
        root /home/corpsee/Projects/php-censor.local/public;
    
        access_log /home/corpsee/Projects/php-censor.local/runtime/nginx_access.log;
        error_log  /home/corpsee/Projects/php-censor.local/runtime/nginx_errors.log warn;
    
        location ~* \.(htm|html|xhtml|jpg|jpeg|gif|png|css|zip|tar|tgz|gz|rar|bz2|doc|xls|exe|pdf|ppt|wav|bmp|rtf|swf|ico|flv|txt|docx|xlsx)$ {
            error_page 404 405 502 504 500 = @fpm;
            expires    30d;
        }
    
        location / {
            try_files $uri @fpm;
        }
    
        location @fpm {
            fastcgi_pass  unix:/var/run/php/php7.0-fpm.sock;
    
            include fastcgi_params;
    
            fastcgi_index index.php;
            fastcgi_param SCRIPT_FILENAME $document_root/index.php;
            fastcgi_param SCRIPT_NAME index.php;
        }
    }
    
  • В завершение установки необходимо настроить запуск агента. У PHP Censor-а есть 2 типа агентов, - команда, которая запускается по расписанию и демон, который запущен постоянно. Crontab задание для запуска сборщика по расписанию будет выглядеть примерно так:

    SHELL=/bin/bash
    PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
    
    * * * * * flock -n /tmp/run-builds.lock --command '/path/to/php-censor/bin/console php-censor:run-builds'
    

Настройка проекта 🔗

PHP Censor имеет декларативный стиль описания конфигурации проектов (используется формат YAML).

Файл конфигурации .php-censor.yml берется из корня репозитория проекта (или просто рабочей директории проекта, если речь идет о локальном источнике), так же есть возможность задать конфигурацию непосредственно в проекте при его создании (Конфигурация сборки, определенная через GUI имеет более высокий приоритет, чем конфигурация находящаяся в репозитории проекта. Это позволяет перекрывать конфигурацию из репозитория и использовать конфиденциальные данные в конфигурации).

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

Ниже небольшой пример файла конфигурации .php-censor.yml:

build_settings:
  ignore: 
    - "vendor"
    - "tests"
setup:
  composer:
    action: "install"
test:
  php_unit:
    config:
      - "phpunit.xml"
  php_mess_detector:
    allow_failures: true
  php_cpd:
    allow_failures: true
  php_loc:
    allow_failures: true
  php_parallel_lint:
    allow_failures: true

branch-dev:
  run-option: replace
    test:
      php_unit:
        config:
          - "phpunit.dev.xml"

Файл конфигурации имеет несколько корневых раздела:

  • build_settings — настройки сборки проекта (игнорирование директорий, настройки подключения к базам данных);
  • setup — раздел инициализации сборки проекта (установка зависимостей, выполнение запросов к базам данных, миграции для баз данных);
  • test — раздел тестирования готовой сборки проекта (над сборкой проекта запускаются различные плагины, которые возвращают успешный или нет результат, провал, как правило, приводит к провалу сборки, хотя для отдельных плагинов это не так и можно установить количество ошибок, приводящих к провалу всей сборки);
  • complete — раздел, вызываемый системой после тестирования независимо от его результата;
  • success — раздел, вызываемый системой после тестирования только в случае успешной сборки и тестирования проекта;
  • failure — раздел, вызываемый системой после тестирования только в случае провала сборки или тестирования проекта;

Директива branch-name позволяет переопределять или дополнять основную конфигурацию сборки для отдельных веток. Параметр run-option может принимать следующие значения:

  • replace — позволяет перекрывать некоторые настройки для отдельных веток;
  • before — позволяет дополнить конфигурацию для конкретной ветки настройками, которые будут запущены до основной конфигурации;
  • after — позволяет дополнить конфигурацию для конкретной ветки настройками, которые будут запущены после основной конфигурации;