Тестирование веб-ориентированных приложений. Часть-2: тестирование форм.

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

В этот раз поговорим об экранных формах и связанных с ними нюансах обеспечения качества веб-ориентированных приложений.

Итак, формы в общем случае делятся на два основных вида:

  • однооконные формы – полностью (со всеми своими полями) расположены на одной странице;
  • пошаговые формы – новые поля появляются (после загрузки новой страницы или в рамках старой с использованием JavaScript/AJAX) по мере заполнения уже показанных.

Начнём с однооконных форм, т.к. здесь многие моменты будут более очевидны.

Сначала – с точки зрения разработчика: посмотрим, что надо сделать, и что (очень часто) не делается.

1. Путь (URL).

GOOD: После обработки данных формы пользователь должен попадать на некую "информативную страницу", т.е., например: пользователь хочет изменить количество заказанных товаров в корзине, он меняет число в соответствующем поле, кликает "Пересчитать", и должен оказаться снова на странице корзины. Проще всего достичь этого эффекта можно так: указать в атрибуте action тега form URL самой же страницы, на которой расположена форма.

BAD: Вместо страницы корзины появляется надпись "Спасибо, операция выполнена успешно". В лучшем случае после этого происходит редирект на страницу корзины. В худшем – пользователю приходится нажимать в браузере Back и… видеть подхваченную из кэша страницу, на которой остались старые данные.

Вывод: работа с веб-приложением должна быть похожа на работу с "обычным настольным приложением" в плане своей последовательности и плавности. Следует избегать лишних сообщений, действий и т.п. Это следует продумывать и при программировании, и при тестировании.

2. Месторасположение.

GOOD: Если форма расположена достаточно низко, нужно сделать автоматическую прокрутку к форме. Например, так: action="/order/#form" (при обработке данных) или href="/order/#form" (при изначальном переходе к форме). Перед самой формой пишем <a name="form"></a>

BAD: Страница с формой или результатами выполнения операции открывается в состоянии "вверху окна браузера – верх страницы". Форма или некоторая информация о выполненной операции видна частично или не видна вообще. Даже если пользователь догадается проскроллить страницу, это всё равно неудобно. А пользователь может и не догадаться.

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

3. Ошибочные ситуации.

GOOD: В случае, если пользователь ввёл некоторые данные некорректно (или не ввёл вообще), форма должна быть показана заново, и при этом: а) все введённые данные (за исключением паролей и полей CAPTCHA) должны сохранять свои значения (ВСЕ ПОЛЯ! Т.е. и чек-боксы, и радиобаттоны, и списки и т.д.); б) в удобном для восприятия месте (чаще всего – сразу над формой) следует чётко указать причину неудачи отправки данных; все неверно заполненные поля следует визуально выделить, а рядом с полем (при возможности) указать суть ошибки заполнения и подсказку по правильному заполнению.

BAD: Иногда можно увидеть такое:
а) Значения полей "обнуляются" (поля или очищаются вообще или принимают некоторые значения по умолчанию. Особенно круто, когда так себя ведёт лишь часть полей.
б) Причина неудачи отправки данных не объяснена вообще или объяснена в стиле "Вы неверно заполнили некоторые поля". Развиваем интуицию пользователя?
в) Ошибочно заполненные поля не указаны, суть ошибки не подчёркнута или подчёркнута способом, допускающим недопонимание. Например: "Неверно указана дата". Какая и почему? Может быть, пользователь допустил ошибку в самой дате (42 декабря) в поле "Дата рождения", а может – указал просто заведомо абсурдную дату (например: дату своего рождения как 01.01.2150).

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

4. Поля, их значения и иже с ними.

Только что (в пункте 3) мы говорили об обработке ситуации "юзер что-то ввёл не так". Но, допустим, юзер ещё ничего не ввёл. Итак.

GOOD: Одно поле – одно значение. Согласитесь, что заполнять, обрабатывать и тестировать такое – просто (пока опустим вопросы выравнивания, цветового и графического оформления и т.д.).

Хорошая форма

BAD: А вот такое и заполнять, и обрабатывать (парсить значения) и тестировать сложно.

Плохая форма

GOOD: Если это возможно (и, особенно, если желательно!) – помещайте рядом с полем пример его заполнения (диапазон дат, пример имени пользователя и т.п.) Это облегчает жизнь и посетителям сайта (проще заполнять форму), и программистам (проще понять, какие будут значения, какие на них можно наложить ограничения и т.д.), и тестировщикам (в случае с диапазонами пример заполнения даёт готовые граничные условия для классов эквивалентности, в случае "просто примера" сразу есть входные данные для простого позитивного теста).

BAD: Иногда из названия поля невозможно догадаться, что и в каком формате следует ввести. И если у программиста и тестировщика есть спецификации (да в них лазить, как известно, часто – лень), то у пользователя остаётся только телепатия. Пример: поле "Идентификатор товара". Ага. И какой он? Может, "Т001-24-н-87-Б"? Или "123-6"? Или "Мониторчик синенький"?

TOO BAD! Но есть одно исключение. Категорически не рекомендуется приводить примеры паролей (по той простой причине, что львиная доля "пользователей невдумчивых" именно такой пароль и использует). Даже сгенерированный уникальный пароль лучше не приводить (он будет закэширован как часть текста страницы).

Вывод: уделяйте внимание тому, как организованы поля формы. Это, в конечном итоге, экономит время всем разработчикам и пользователям проекта.

5. Значения полей и спецсимволы.

GOOD: Следует чётко отдавать себе отчёт в том, что через поле, теоретически, могут быть введены любые символы. ЛЮ-БЫ-Е. Из этого, конечно, следует необходимость тщательной фильтрации данных перед передачей их в БД или иной приёмник. Но также следует фильтровать данные и правильно оформлять формы, имея в виду, что в случае неверного заполнения части полей данные будут снова показаны в форме (см. пункт 3).

Базовые идеи:
1. Помним и используем простое правило: значения атрибутов тегов берутся в кавычки. Без исключений.
2. Используем функции, позволяющие отобразить данные как часть HTML-кода (например, банальную функцию htmlspecialchars() в PHP).

BAD: Плохого по этому пункту можно написать много. Но самые "весёлые" ситуации возникают, когда нарушены вышеназванные "базовые идеи". Например, пользователь заполняет поле "Место проживания" так:

Отель "Минск", 2-й этаж.

Форма сделана бездарно, фильтрации нет, а в коде прописано так:

<input type=text name=place value={value} />

Когда плейсхолдер {value} будет заменён на реальное значение, код примет вид:

< … value=Отель "Минск", 2-й этаж />

В переводе на русский:

value="Отель"

Всё. Данные о названии отеля и этаже утеряны.

Вывод: переоценить правильное оформление HTML-кода и вдумчивую фильтрацию полученных от пользователя данных едва ли возможно.

6. JavaScript в формах – "за" и "против".

GOOD: JavaScript, AJAX и иже с ними – прекрасные инструменты, которые позволяют значительно "оживить" в плане эстетического восприятии, а также ускорить работу с формами. Так, например, можно проверять значения полей на корректность ещё в процессе заполнения и/или перед отправкой данных из формы. Можно выводить красивые подсказки, элегантно сообщать об ошибочных ситуациях и способах их решения.

BAD: Но! JavaScript может быть отключён. Он также может "сглючить" в силу множества сложнопредсказуемых причин. И что тогда? А тогда форма, рассчитанная на активное использование JavaScript и лишённая альтернативных способов "общения с пользователем" становится как минимум неинформативной (принимает "bad вид" из пункта 4), а как максимум – неработоспособной.

Вывод: НЕЛЬЗЯ полагаться ТОЛЬКО на JavaScript при работе с формами. Формы и механизмы их обработки должны оставаться полностью функциональными (и терять минимум юзабилити) при отключённом JavaScript.

7. Пошаговые формы.

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

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

BAD: Механизм управления шагами работает "как повезёт". В зависимости от браузера и иных факторов возврат то не работает ("page has expired"), то работает нестабильно (данные искажаются и теряются), то вытворяет иные трюки и фокусы.

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

Переходим к тестированию.

Как обычно – краткий, "максимально универсализированный" чек-лист:

  1. Расположение формы на экране перед заполнением, после неверного заполнения, после верного заполнения.
  2. Сохранение/изменение URL при отправке данных из формы.
  3. Отправка формы с незаполненными обязательными полями.
  4. Отправка формы с неверно заполненными полями (числа вне диапазонов, строки превышают допустимую длину и т.п.)
  5. Отправка формы с "нелогичными данными" (например, дата рождения – в будущем).
  6. Отправка формы с полями, содержащими спецсимволы.
  7. Восстановление значений полей после отправки формы с неверно заполненными полями.
  8. Информативность сообщений об ошибках.
  9. Функциональная сгруппированность полей формы. Информативность надписей, подсказок.
  10. Работоспособность и юзабилити формы с отключённым JavaScript.
  11. + использовать чек-листы по каждому стандартному полю (текстовое, числовое, дата и т.п.)