(495) 925-0049, ITShop интернет-магазин 229-0436, Учебный Центр 925-0049
  Главная страница Карта сайта Контакты
Поиск
Вход
Регистрация
Рассылки сайта
 
 
 
 
 

Mutation testing на примере Pitest.

Источник: habrahabr

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

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

Простенький проект.

Начнём с простого проекта[github], содержащего один-единственный класс:

 и тест на него:

 

Чтобы подключить pitest, достаточно добавить его плагин в maven:

 

Чуть подробнее по конфигурации: inScopeClasses определяет те классы, в которых следует искать тесты и классы, которые следует подвергать мутации. Target Classes определяет те классы, которые следует подвергнуть только мутации. Кроме того, есть ещё некоторые опции, полный список которых можно посмотреть тут.

Если вы по какой-то причине не используете maven, то ещё не всё пропало: можно пользоваться и из командной строки, руководство доступно тут.

А чтобы обрести счастье, используя maven, достаточно выполнить команду: mvn org.pitest:pitest-maven:mutation Coverage

Понимание отчётов.

В результате проверки мы получим довольно-таки большую простыню логов. Читать её не особо удобно, но зато в папке target/pit-reports/%TIMESTAMP% генерируется и html-отчёт, похожий на code coverage. В нашем случае интересная его часть будет выглядеть примерно так:

 

Цифра три возле строки 14 тут означает, сколько мутаций было к этой строчке применено. Далее в разделе mutations для каждой строчки описывается, какие были применены мутации, и каков был результат.

Результат выполнения мутации.

KILLED - в результате мутации упали все тесты, проверяющие эту строку. Можно заметить, что у нас все мутации имеют такой статус, что довольно хорошо.
SURVIVED - мутация прошла незамеченной. Это значит, что изменение в функциональности не покрыто тестами
TIMED_OUT - тест работал слишком долго (например, в результате возникновения бесконечного цикла)
NON_VIABLE - получившийся в результате мутации бат-код по какой-то причине оказался не валидным (случается довольно редко)
MEMORY_ERROR - в результате мутации код стал потреблять слишком много памяти и упал с OOM
RUN_ERROR - в результате мутации получился код, генерирующий исключение

Типы мутаций.

На данный момент есть всего 11 мутаций. Зелёным выделены те, которые включены по умолчанию.
CONDITIONALS_BOUNDARY - в проверках меняет строгие неравенства на нестрогие и наоборот. Например, < превратится в <=
NEGATE_CONDITIONALS - в проверках инвертирует условия. Например, == превратится в !=
MATH - заменяет используемые математические операторы. Например, меняет минус на плюс.
INCREMENTS - заменяет инкременты на декременты и наоборот
INVERT_NEGS - инвертирует знак целым и вещественным числам
INLINE_CONSTS - меняет литералы, подставляя на их место другое значение. Например, вместо 42 будет подставлено 43, а вместо true будет подставлено false
RETURN_VALS - подменяет значение, возвращаемое методом, на какое-то другое. Например, вместо полноценного объекта будет возвращаться null.
VOID_METHOD_CALLS - удаляет вызовы void-методов
NON_VOID_METHOD_CALLS - вместо вызовов не-void методов возвращает значение по умолчанию для типа этого метода (false, 0, null)
CONSTRUCTOR_CALLS - вместо вызова конструктора использует null
EXPERIMENTAL_INLINE_CONSTS - похож на INLINE_CONSTS, но несколько умнее.

Детальное описание различных типов мутаций доступно на официальном сайте.

Усложняем пример.

Получается, что в нашем sample-проекте мутации были в условии (2 шт) и в возвращаемом значении. Попробуем теперь добиться большего количества мутаций. Перепишем сам класс так: 

Но вот в тестах новую функциональность тестировать не будем:

При запуске code coverage никаких проблем выявлено не будет. А вот если мы запустим mutation testing, то нас быстро схватят за руку и скажут: а функциональность-то не протестирована!

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

Почему именно pitest?

Идея мутационного тестирования, вообще говоря, не нова, и несколько библиотек уже существовало. Наиболее примечательные из них - Javalanche и Jumble. Однако и они, и другие библиотеки не особо активно развиваются, некоторые из них тормозны и глючны, и практически не имеют интеграции с системами сборки и другими библиотеками. Подробное сравнение доступно тут.

Проверим на реальном проекте.

Для пущей интересности правильно было бы на каком-нибудь реальном проекте продемонстрировать, как mutation testing находит проблемы, которые не находит code coverage. Отлично для этого подойдёт cobertura - утилита, считающая code coverage. Её отчёт может быть найден в полном виде тут, а я приведу лишь маленький кусочек. Чтобы его получить, пришлось немного попотеть с добавлением поддержки maven в исходники и подождать минут двадцать, пока будет идти мутационное тестирование.. Результат получился таким.

Cobertura показывает, что всё хорошо:

Pitest срывает покровы:

Итого.

Итого, подход классный, и явно гораздо более точно оценивает качество тестов, чем code coverage. Конечно, такие проверки и работают существенно дольше, чем обычный coverage, и потому на больших проектах могут занимать часы. Кроме того, сама библиотека Pitest пока несколько сыровата. Например, нет возможности проводить тестирование в несколько потоков, или обязательно успешное выполнение всех тестов без мутаций. Проект, впрочем, opensource, и весьма активно развивается, так что я полагаю, что через какое-то время можно будет начать думать о том, чтобы использовать его всерьёз.



 Распечатать »
 Правила публикации »
  Написать редактору 
 Рекомендовать » Дата публикации: 05.03.2012 
 

Магазин программного обеспечения   WWW.ITSHOP.RU
Oracle Database Personal Edition Named User Plus Software Update License & Support
Oracle Database Standard Edition 2 Processor License
Oracle Database Standard Edition 2 Named User Plus License
Oracle Database Personal Edition Named User Plus License
ABBYY FineReader 14 Standard Full
 
Другие предложения...
 
Курсы обучения   WWW.ITSHOP.RU
 
Другие предложения...
 
Магазин сертификационных экзаменов   WWW.ITSHOP.RU
 
Другие предложения...
 
3D Принтеры | 3D Печать   WWW.ITSHOP.RU
 
Другие предложения...
 
Новости по теме
 
Рассылки Subscribe.ru
Информационные технологии: CASE, RAD, ERP, OLAP
Безопасность компьютерных сетей и защита информации
Новости ITShop.ru - ПО, книги, документация, курсы обучения
CASE-технологии
СУБД Oracle "с нуля"
eManual - электронные книги и техническая документация
Новые материалы
 
Статьи по теме
 
Новинки каталога Download
 
Исходники
 
Документация
 
 



    
rambler's top100 Rambler's Top100