Автоматизированное тестирование проектов на 1С-Битрикс

Что такое качество? Качество — предсказуемость, стабильность работы, соответствие ожиданиям.


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

Современный софт — не музейный экспонат, он постоянно меняется вместе с условиями работы компании.

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

Решение — автоматизированное тестирование и непрерывная интеграция (continuous integration).

Удивительно, но в мире заказной веб-разработки, создания сайтов и запуска интернет-магазинов почти никто не применяет эти технологии.

Мы в отделе сопровождения сайтов в крупных проектах (Альфа-Банк, mybox, Издательство “Учитель”) освоили работу на основе автотестов и непрерывной интеграции.

Расскажем зачем это нужно, как работает и сколько стоит.

Идея автоматического тестирования сайтов

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

Хозяйке на заметку:
Чтобы быть уверенным в корректности работы программы, нужно проверять её на отсутствие ошибок. В ответственных проектах enterprise-сегмента вопрос качества становится важнейшим. Сайт, портал, сервис, которому нельзя доверять — плохой продукт. В разработке программного обеспечения этот процесс называется тестированием.  При больших объемах работы тестирование нужно автоматизировать.

В простых случаях тестирование выполняет человек. Он проверяет работу различных сценариев использования в разных браузерах, для учётных записях с разными правами (оптовик, партнёр, гость, админ и т.д.). Чем больше проект, тем больше проверок.

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

Существует разные подходы и инструменты для организации автоматизированного тестирования. Наиболее популярны тестирование отдельных частей проекта (модулей) и тестирование конкретных сценариев использования (например, добавление товара в корзину и оформление заказа).

Тестирование по частям принято называть модульным или Unit-тестированием. Тестирование сценариев, которые позволяют пользователям решать определённые задачи (например, оформлять заказы), называется функциональным тестированием.

Мы расскажем о том, как внедрить оба вида тестирования в крупном проекте.

Модульное тестирование

Хозяйке на заметку: 

Для использования модульного тестирования весь проект должен разрабатываться как набор модулей и связей между ними. Автомобиль - система, состоящая из отдельных частей (ДВС, ГУР, климат-контроль и т.д). Это отдельные модули, работу которых можно проверить. Мясной фарш - не модульная система, хотя и состоит из отдельных частей.

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

Для модульного тестирования веб-проектов на 1С-Битрикс мы используем PHPUnit. Если проект запрограммирован аккуратно (с соблюдением принципов объектно-ориентированного программирования), PHPUnit позволяет быстро покрывать код тестами.

atp1c_14.png

Важно:
Модульные тесты дают понять разработчикам, какое изменение явилось причиной ошибки и вовремя её исправить (до переноса изменений с тестового сервера на основной).


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


Из опыта:
Для покрытия кода на 60% уходит 1/10 времени затраченного на разработку (5 дней пишем код, пол дня пишем тесты). Код считается “покрытым”, если в ходе тестирования он выполнялся хотя бы 1 раз, а лучше 2.


Функциональное тестирование

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

Сценарий оформления заказа:

  1. Открыть главную страницу

  2. Найти первый товар в списке и кликнуть на его название (или фото)

  3. Запомнить название товара

  4. Найти на странице кнопку с текстом “Купить” и нажать на неё

  5. Открыть страницу “Корзина”

  6. Проверить есть ли в корзине элемент с нужным названием (мы его запомнили на шаге 3)

  7. Найти кнопку “Оформить заказ” и нажать на неё

  8. Заполнить поля формы оформления заказа тестовыми данными (в поле “имя” ввести имя и т.д.)

  9. Найти кнопку “Отправить заказ” и нажать на неё

  10. Запомнить номер, присвоенный заказу

  11. Открыть список заказов и найти заказ с нужным номером

  12. Если заказ найден - тест пройден успешно

Прохождение таких тестов после завершения доработки сайта гарантирует работу основных сценариев работы проекта. Если после обновления сайта заказ перестал оформляться вы об этом узнаете немедленно, а не через 1-2 дня простоя интернет-магазина.

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


Проблемы:
Любое изменение верстки требует внесения изменений в тесты. 



Из нашего опыта:  
На создание теста для формы обратной связи уходит 2-4 часа.



Автоматизация запуска тестирования

Современные инструменты разработки позволяют запускать тесты нажатием одной кнопки. Эта задача решается с помощью специального программного обеспечения. Мы используем Jenkins.
Эта система работает на отдельном сервере. Программист даёт сигнал что он закончил решать задачу и пора запускать тестирование. Jenkins получает изменения программиста, добавляет их на сайт и запускает тесты. По окончанию тестирования, Jenkins отправит всем заинтересованным письма с подробным отчётом о провалившихся тестах  и результатах свой работы.

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

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

Шаги сборки

atp1c_17.png

Создание независимой копии проекта

На этом этапе на отдельном сервере Jenkins создаёт копию файлов проекта. Это нужно чтобы исключить возможность влияния внешних факторов (пользователи, программисты, боты google и Яндекс).

Синтаксический анализ

На этом этапе Jenkins проверяет код проекта на наличие синтаксических ошибок, а также ищет копипаст в коде.

Модульное тестирование

На этом этапе Jenkins выполняет все модульные тесты и проверяет работоспасобность  всех частей проекта. Во время выполнения Jenkins проверяет, какой код исполнялся в ходе теста, а какой нет. На основе этого создаётся отчёт о покрытии кода тестами. Чем выше процент покрытия, тем лучше.

Функциональное тестирование

На этом этапе Jenkins проверяет выполнение тестовых сценариев в основных браузерах. Результаты этих тестов дают уверенность в том, что последние изменения не сломали бизнес-логику проекта.

Построение отчётов и e-mail уведомления

На этом этапе Jenkins подбивает накопившуюся информацию о результатах тестирования и рассылает их по почте.

Важно:


  • Если модульного тестирования нет, ошибки накапливаются и переплетаются. Проект становится хрупким.

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

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

  • Актуальность такого функционального теста зависит только от вёрстки в вашем проекте. Поменяли вёрстку — поменяйте тест.

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

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


Заключение, или “Сколько это стоит?” и “Что для этого нужно?”

Что нужно:

  1. Организовать сервер, на котором будет работать Jenkins.

  2. Купить сервер, на котором будут размещены виртуальные машины с разными операционными системами (+лицензии для операционных систем) и разными версиями браузеров

  3. Настроить VPN между серверами

  4. Установить и настроить Jenkins

  5. Написать тесты

Сколько стоит:

  1. Настройка серверов, установка операционных систем, установка и настройка Jenkins и прочих программных пакетов для среднего проекта — 40 часов работы.

  2. Разработка тестов — очень индивидуальная процедура, ее трудоемкость сильно зависит от конкретики.
    Например, автотест для проверки процедуры авторизации — 3 часа работы, тест оформления заказа с выбором первой системы оплаты и первой службы доставки 8 часов

Для каких веб-проектов нужно автоматическое тестирование и непрерывная интеграция

Веб-разработка по модели “continuous integration” с использованием автоматического тестирования требует заметных организационных и технических затрат.

В небольших, коротких и простых проектах это не окупается.

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

На практике только при автоматизированном тестировании удается добиться стабильности процесса и предсказуемости результата.

А это — качество.



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

...
  • Иван Иванов
  • 17.12.2015 10:23:38
В тексте с 10 пункта ошибки с пробелами. Прогоните текст через лебедевский типограф. Не благодарите )
...
Действительно. Исправим. Правда, дело не в типографике.
...
  • Антон Мышкин
  • 17.12.2015 11:08:28
Про PHPUnit понятно, а вот тут:

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

Можно как-то поподробнее, с помощью каких инструментов? Разве PHPUnit не позволяет проводить также и функциональное тестирование или я слишком разбалован RSpec'ом в рельсах?