Вступление
Equivalence Classes (Класс эквивалентности) – это входные (а иногда и выходные) данные, которые обрабатываются приложением одинаково или обработка которых приводит к одному и тому же результату.
Equivalence Class Testing (Тестирование классами эквивалентности) это техника тест дизайна способная резонно уменьшить количество ваших тест-кейсов. Использовать ее можно на всех уровнях тестирования - unit, integration, system, and system-integration test levels.
Как мне кажется эта техника тест дизайна интуитивно понятна и интуитивно применяется каждым тестировщиком, но стоит знать теорию, чтобы осознанно применять технику на практике.
Подход
Использовать эту технику достаточно просто, правила такие:
Использование классов эквивалентности будем рассматривать на примерах.
Пример 1. Одна сущность.
Представим, что мы тестируем модуль для HR, который определяет брать на работу кандидата или нет, базируясь на возрасте кандидата. Условия такие:
Определеим классы эквивалентности по сущностям:
При составлении _не_ валидных тест кейсов советую создавать по 1 тест кейсу на каждое _не_ валидное значение 1 сущности:
Ну вот собственно и всё. Готово. Можно тестировать.
Этот пост является вольным переводом Chapter 3 из книги "A Practitioner'S Guide To Software Test Design" by Lee Copeland.
Equivalence Classes (Класс эквивалентности) – это входные (а иногда и выходные) данные, которые обрабатываются приложением одинаково или обработка которых приводит к одному и тому же результату.
Equivalence Class Testing (Тестирование классами эквивалентности) это техника тест дизайна способная резонно уменьшить количество ваших тест-кейсов. Использовать ее можно на всех уровнях тестирования - unit, integration, system, and system-integration test levels.
Как мне кажется эта техника тест дизайна интуитивно понятна и интуитивно применяется каждым тестировщиком, но стоит знать теорию, чтобы осознанно применять технику на практике.
Подход
Использовать эту технику достаточно просто, правила такие:
- Определите классы эквивалентности.
- На каждый класс эквивалентности сделайте хотя бы 1 тест-кейс.
Использование классов эквивалентности будем рассматривать на примерах.
Пример 1. Одна сущность.
Представим, что мы тестируем модуль для HR, который определяет брать на работу кандидата или нет, базируясь на возрасте кандидата. Условия такие:
- 0–16 : Не нанимать
- 16–18 : Можем нанять только на part time
- 18–55 : Можем нанять на full time
- 55–99 : Не нанимать
If (applicantAge == 0) hireStatus="NO";
If (applicantAge == 1) hireStatus="NO";
…
If (applicantAge == 14) hireStatus="NO";
If (applicantAge == 15) hireStatus="NO";
If (applicantAge == 16) hireStatus="PART";
If (applicantAge == 17) hireStatus="PART";
If (applicantAge == 18) hireStatus="FULL";
If (applicantAge == 19) hireStatus="FULL";
…
If (applicantAge == 53) hireStatus="FULL";
If (applicantAge == 54) hireStatus="FULL";
If (applicantAge == 55) hireStatus="NO";
If (applicantAge == 56) hireStatus="NO";
…
If (applicantAge == 98) hireStatus="NO";
If (applicantAge == 99) hireStatus="NO";
К счастью, наши родные девелоперы так код не пишут (по крайней мере как правило :)). На самом деле для этого модуля мы, как правило, увидим примерно такой код:
If (applicantAge > 0 && applicantAge <=16)
hireStatus="NO";
If (applicantAge > 16 && applicantAge <=18)
hireStatus="PART";
If (applicantAge > 18 && applicantAge <=55)
hireStatus="FULL";
If (applicantAge > 55 && applicantAge <=99)
hireStatus="NO";
Поэтому явно видно, что не стоит тестировать все значения 0, 1, 2, ... 14, 15, 16. Более разумно будет протестировать диапазоны каждого условия, что собственно и есть наши классы эквивалентности.:
- Класс эквивалентности NO: 0-16.
- Класс эквивалентности PART: 17-18.
- Класс эквивалентности FULL: 19-55.
- Класс эквивалентности NO: 56-99.
Вспомним правила - после определения классов эквивалентности мы должны создать тест кейс с любым значением из диапазона класса эквивалентности. Итого у нас 4 позитивных тест кейса вместо 100. Неплохая оптимизация.
Так же не стоит забывать о не валидных диапазонах, добавим классы эквивалентности и для них:
Так же не стоит забывать о не валидных диапазонах, добавим классы эквивалентности и для них:
- (-100) – (-1). Значнеие (-100) было взято наугад, по поводу подобных границ лучше консультироваться с девелоперами.
- 100-1000. Значнеие (1000) было взято наугад, по поводу подобных границ лучше консультироваться с девелоперами.
- 0.1-0.9. Выбрано любое дробное значение входящее в валидный диапазон.
- Символы.
- Пустой ввод.
- ...
Вот собственно и всё. Осталось на каждый класс эквивалентности создать тест-кейс.
Важно помнить, что классы эквивалентности определяются по сущностям. В нашем примере была одна сущность – возраст, но в реальной жизни чаще встречаются случаи взаимодействия нескольких сущностей одновременно.
Для этого лучше рассмотреть следующий пример.
Пример 2. Несколько сущностей.
Допустим ситуацию, когда нам нужно протестировать форму регистрации на сайте. Для регистрации нам нужно ввести логин, пароль, возраст и способ оплаты товаров на сайте. Требования такие:
Важно помнить, что классы эквивалентности определяются по сущностям. В нашем примере была одна сущность – возраст, но в реальной жизни чаще встречаются случаи взаимодействия нескольких сущностей одновременно.
Для этого лучше рассмотреть следующий пример.
Пример 2. Несколько сущностей.
Допустим ситуацию, когда нам нужно протестировать форму регистрации на сайте. Для регистрации нам нужно ввести логин, пароль, возраст и способ оплаты товаров на сайте. Требования такие:
Сущность | Тип ввода | Допустимые значения |
Логин | Ввод с клавиатуры | Латинские символы |
Пароль | Ввод с клавиатуры | Латинские символы |
Возраст | Выбор из списка (список от 1 до 100) | От 16 до 100 |
Способ оплаты | Выбор из списка | Оплата картой, интернет деньги, наличные |
Определеим классы эквивалентности по сущностям:
- 1. Логин:
- a. Латинские символы
- b. Не латинские символы
- c. Пустой ввод
- 2. Пароль:
- a. Латинские символы
- b. Не латинские символы
- c. Пустой ввод
- 3. Возраст:
- a. От 16 до 100
- b. От 1 до 16
- 4. Способ оплаты:
- a. Любое значение из списка
Примечание: Некоторые сущности, например "не латинские символы", стоило бы разложить на подсущности, но для простоты примера мы этого делать не будем.
Для тестирования способа оплаты мы должны выбрать значение «Оплата картой», «интернет деньги» или «наличные». Это тот случай, когда здравый смысл должен победить любые правила :) Хотя правило предлагает нам выбрать одно значение из класса эквивалентности, здесь будет лучше проверить каждое из них. Это имеет смысл потому что здесь входных значений немного.
Возможно появится вопрос – а что с возрастом? Может и тут стоит все значения протестировать? А если бы мы вводили город проживания? Стоило бы все возможные значения городов из списка проверить? Ответ на эти вопросы зависит от риска пропустить серьезные дефекты и от количества времени выделенного под тестирование.
Возможно появится вопрос – а что с возрастом? Может и тут стоит все значения протестировать? А если бы мы вводили город проживания? Стоило бы все возможные значения городов из списка проверить? Ответ на эти вопросы зависит от риска пропустить серьезные дефекты и от количества времени выделенного под тестирование.
Итого у нас получатся следующие валидные тест-кейсы:
Логин | Пароль | Возраст | Способ оплаты | Результат |
Латинские символы | Латинские символы | От 16 до 100 | Оплата картой | Успешная регистрация |
Латинские символы | Латинские символы | От 16 до 100 | Интернет деньги | Успешная регистрация |
Латинские символы | Латинские символы | От 16 до 100 | наличные | Успешная регистрация |
При составлении _не_ валидных тест кейсов советую создавать по 1 тест кейсу на каждое _не_ валидное значение 1 сущности:
Логин | Пароль | Возраст | Способ оплаты | Результат |
Не латинские символы | Латинские символы | От 16 до 100 | Оплата картой | Ошибка регистрации |
Пустой ввод | Латинские символы | От 16 до 100 | Оплата картой | Ошибка регистрации |
Латинские символы | Не Латинские символы | От 16 до 100 | Интернет деньги | Ошибка регистрации |
Латинские символы | Пустой ввод | От 16 до 100 | Интернет деньги | Ошибка регистрации |
Латинские символы | Латинские символы | От 1 до 16 | наличные | Ошибка регистрации |
Ну вот собственно и всё. Готово. Можно тестировать.
Этот пост является вольным переводом Chapter 3 из книги "A Practitioner'S Guide To Software Test Design" by Lee Copeland.
If (applicantAge > 0 && applicantAge <16)
ОтветитьУдалитьhireStatus="NO";
If (applicantAge > 16 && applicantAge <18)
hireStatus="PART";
If (applicantAge > 18 && applicantAge <55)
hireStatus="FULL";
If (applicantAge > 55 && applicantAge <99)
hireStatus="NO";
В этом примере - у нас выпадут значения 16, 18, 55 и 99. Т.е. там, имхо, лучше юзать <=
Да, моя вина, спасибо. Исправил.
ОтветитьУдалитьКстати с чего вы взяли что программисты не пишут так как у вас нарисовано в первом примере пишут - пишут , если это будет работать быстрее (например на процессоре с длинным командным словом особенно если от if - избавится)
ОтветитьУдалить============================
Вопрос а можно разделить на классы эквивалентности входное значение которое нельзя упорядочить, на котором не определены операции больше ,меньше?
Прочитал, интуитивное определение классов эквивалентности.
ОтветитьУдалитьЦелевая функция hireStatus от applicantAge на отрезках [0;16] , [55;99] - имеет одно и тоже значение, так почему вы эти значения относите к разным классам эквивалентности?
Да, результат один, выходное значение одинаковое. Но входные данные для этих диапазонов разные:
ОтветитьУдалить* Во-первыйх. Возможно разный код отработает по этим диапазонам. Поэтому стоит проверить каждый из диапазонов.
* Во-вторых. Все таки анализ граничных значений мы применять будем, поэтому удобней будет разделить эти диапазоны.
* Ну и в-третьих. Это все таки логика приложения. Есть такой диапазон входных значений сущности - лучше его проверить.
Извините, пропустил ваш комментарий.
ОтветитьУдалить>>Вопрос а можно разделить на классы эквивалентности входное значение которое нельзя упорядочить, на котором не определены операции больше ,меньше?
Да. Такие входные данные почаще исчисляемых встречаются. В этих случаях разбиение на классы эквивалентности, в основном, производиться по логике приложения.
Если после ввода 2х разных значений одного входного параметра вы можете получить разный логический результат их обработки, то эти значения стоит вынести в разные классы эквивалентности.
Возможно ли найти граничные значения для латинских символов?
ОтветитьУдалитьВозможно :D
УдалитьКакие по вашему мнению являются граничными для символов?
УдалитьЗависит от контекста. Символы или алфавит, кодировка, раскладка, один символ или совокупности и так далее.
УдалитьP.S.: Этот пост про классы эквивалентности ;)
P.P.S.: Отличные у вас бложики, заценил :D
Всем привет! Только изучаю тестирование, еще даже нигде не работал. Попал на этот интересный блог, изучая техники тест-дизайна. Заметил ошибку (математическую) во втором примере. Прошу прощения, если конечно, ошибаюсь сам.
ОтветитьУдалитьСобственно ошибка: в позитивном тесте №3 мы указываем возраст от 16 до 100 и при этом он проходит. Негативный тест №5 предусматривает диапазон возрастов от 1 до 16 и при этом тест должен завалить приложение. Так вот неясным остается значение возраста 16, ибо нигде не нашел условия включающего или исключающего цифру 16 из диапазонов значений.
Спасибо за внимание!
Все верно, при возрасте 16 непонятно и неизвестно что произойдет.
УдалитьЭта ошибка допущена специально чтобы разбираться с ней в следующей статье про технику граничных значений. Затравочка.
А касательно классов эквивалентности и этого примера. Про 16 нужно уточнять условия и по результату уточнения 16 либо должно быть включено в какой то из определенных классов, либо вынесено в отдельный, собственный класс эквивалентности :)
Спасибо за вопрос, удачного изучения тестирования ;)
кашерный дизайн :D
ОтветитьУдалитьпоследний вариант не_валидного теста идентичен последнему варианту валидного теста, так почему же ошибка регистрации?
ОтветитьУдалитьВнимательнее смотрите "Возраст"
УдалитьКто здесь в 2021 - ставте лайк))
ОтветитьУдалитьЛайк :D
Удалитьлайк
ОтветитьУдалитьеще лайк)
ОтветитьУдалитьВсем привет и хорошего дня !
ОтветитьУдалитьTitanium Bike | www.titanium-arts.com | www.titanium-arts.com
ОтветитьУдалитьT-Sport is cerakote titanium the largest motorsports brand in the world. Our titanium piercing jewelry titanium bike makes perfect venza titanium glow use of a traditional battery titanium piercings pack with the titanium coating
Еще один не валидный лайк, т.к. уже 2022 год
ОтветитьУдалить