Тестирование скриншотов

Тестирование скриншотов – очень эффективный способ проверки интерфейса приложения. Тесты скриншотов могут быть частью тестов компонентов, функций и приложений.

Для создания как инструментальных, так и локальных тестов скриншотов можно использовать сторонние инструменты. Если вы используете Compose, то можете воспользоваться официальным инструментом тестирования Compose Preview Screenshot.

Определение

Тесты скриншотов делают снимок экрана и сравнивают его с ранее одобренным изображением, которое называется "референсным" или "золотым".

В тесте сравниваются два изображения: новый скриншот и референсное изображение.
Рисунок 1. Тестирование скриншотов позволяет сравнить два изображения.

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

Отчет о тестировании скриншотов, в котором слева и справа показаны эталонный и новый скриншоты, а посередине – их различия.
Рисунок 2. Отчет о тестировании скриншотов, в котором по обе стороны показаны исходный и новый скриншоты, а посередине – их различия.

После получения отчета вы можете:

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

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

Преимущества

Преимущества тестирования скриншотов:

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

Недостатки

Однако у тестирования скриншотов есть и недостатки:

  • Работа с референсными изображениями может быть сложной, поскольку в большом проекте могут быть тысячи файлов PNG.
  • На разных платформах (Linux, macOS и Windows) скриншоты выглядят немного по-разному.
  • Они выполняются медленнее, чем аналогичные тесты поведения.
  • Большое количество тестов скриншотов может привести к проблемам, например когда одно изменение влияет на тысячи скриншотов.

В следующих разделах приведены рекомендации по устранению этих проблем.

Сведите к минимуму тестирование скриншотов

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

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

  • разных тем.
  • Использование разных размеров шрифта
  • в разных размерах экрана или границах;

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

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

Некоторые сочетания свойств интерфейса можно опустить.
Рисунок 3. Некоторые сочетания свойств интерфейса можно опустить.

Как хранить референсные изображения

Опорные изображения обычно представляют собой PNG-файлы, которые можно добавить в систему контроля версий. Однако Git и большинство систем управления версиями оптимизированы для текстовых файлов, а не для больших двоичных файлов.

У вас есть три варианта:

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

Различия между платформами

Скриншот-тесты опираются на низкоуровневые API платформы для отрисовки определенных элементов, таких как текст или тени, а платформы могут реализовывать их по-разному. Если вы разрабатываете на Mac и сохраняете новые скриншоты, сделанные локально, то можете столкнуться с тем, что тесты на машине с Linux CI будут выполняться некорректно.

Обойти эту проблему можно двумя способами:

  • Допускать небольшие изменения
  • Как делать скриншоты на сервере

Допускать небольшие изменения

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

Есть два способа:

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

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

Как делать скриншоты на сервере

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

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

  1. Запускает тесты скриншотов (требуется, только если не используется точное соответствие пикселей).
  2. Записывает новые скриншоты, если предыдущий шаг не удался.
  3. Сохраняет новые файлы в ветке.
Альтернативный текст: диаграмма, показывающая, как делать скриншоты в CI
Рисунок 4. Схема, показывающая, как делать скриншоты на устройстве CI

При таком подходе тесты скриншотов никогда не завершаются с ошибкой в CI, но при этом изменяют код. Таким образом вы и проверяющие изменения сможете принять новые скриншоты, объединив изменения.

Инструменты для тестирования скриншотов

Учитывайте следующие ключевые различия между доступными инструментами и библиотеками для тестирования скриншотов:

  • Среда: локальные тесты, выполняемые на хосте, или инструментальные тесты, выполняемые на эмуляторе или устройстве.
  • Механизм отрисовки. Решения для создания скриншотов на стороне хоста могут использовать Layoutlib – механизм отрисовки Android Studio для предварительного просмотра – или Robolectric Native Graphics (RNG).
    • Фреймворки на основе Layoutlib ориентированы на отрисовку статических компонентов, в которых разные состояния используются для демонстрации разного поведения. Они обычно проще в использовании.
    • Фреймворки, интегрированные с RNG, могут использовать все функции Robolectric, что позволяет проводить более масштабные тесты.