t.me/atinfo_chat Telegram группа по автоматизации тестирования

Что день грядущий нам готовит или как проверять дату и время в тестах

design-patterns
assert
framework
Теги: #<Tag:0x00007f21df132358> #<Tag:0x00007f21df131e80> #<Tag:0x00007f21df131c28>

(Oleksandr Khotemskyi) #1

Доброго времени суток!

Предлагаю обсудить варианты проверки даты и времени, которую мы получаем со страниц, баз данных, API ответов и других изысканных мест.

Сейчас автоматизирую сайт по типу “поиск такси”, и многое завязано на дату и время когда такси должно приехать. Мне в наследство достался фреймворк в котором дата и время передается в методы просто строкой, в своем формате вида - DD/MM/YYYY_HH:mm

Это работало до поры до времени, но теперь появились дополнительные, локализированные версии сайта, например американская, у которой даты на юайке отображаются как MM/DD/YYYY ну и am/pm . Это вызывает проблемы когда у тебя дата записана в тестовых данных в одном формате, а потом ты читаешь с сайта в другом, и нужно как то переводить строки из формата в формат, и еще и заасертить их между собой. Тупое сравнение строк по === работает плоховато.

Так же столкнулся с проблемами таймзон. К примеру - я делаю прекондишн покупку через API, и получаю HTTP ответ в котором у меня дата по лондону, но тесты я запускаю локально для отладки - киевское время. Дату которую я получаю с странички - это локальная дата для браузера. Опять же сделать сравнение этих двух дат уже сложновато, нужно хитро переопределять таймзоны и сравнивать между собой.

Хотелось бы узнать какие вы используете подходы чтобы работать с датами\временем, как вы сравниваете их между собой? Как парсите дату\время со страницы?

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

  • В тестовых данных хранить дату\время как Date или MomentJS объект, а не строку. Это должно дать возможность приводить дату к нужной локали, а так же легче сравнивать между собой
  • Если нужно привести дату к строке - использовать стандартный ISO формат, чтобы при нужде потом назад отпарсить в Date объект
  • Методы PageObject/PageComponent возвращают дату или время всегда как Date или MomentJS обьект, ну или строка в ISO формате
  • Для таймзон думаю что нужно всегда запускать браузер насильно в нужной таймзоне через capabilities. Хотя еще не уверен что не понадобятся тесты на работу в разных таймзонах


(Sergey Korol) #2

Привет,

С датами всегда проще работать при помощи специализированных структур. Для JS - moment - оптимален, на мой взгляд. Но лучше взять ещё и moment-timezone с возможностью зональной подстройки.

В тестах при работе с датами лучше сделать акцент на вычисляемые значения. В примере с такси не подскажу, т.к. не знаю алгоритм расчёта, формата возвращаемых с бека данных, и кто занимается конвертацией. Ну и тут важно понимать, что тестируется: точность алгоритма или корректность подстройки под тайм зону? Если первое, то это лучше проверять не UI тестами. А для второго достаточно будет дернуть АПИ для расчёта, адаптировать под тайм зону и сравнить с какой-то вычисляемой датой в рамках допустимой погрешности (разница не превышает указанного порога).

Вообще такие задачи очень зависят от алгоритма и контекста проверок. Помню на одном из финансовых проектов проверялась пеймент система, в которой можно было указывать дату платежа только валидным процессинговым днём (будни, без праздников и зональных выходных). Даты естественно динамические. И не было смысла их хардкодить, ровно как и проверять корректность алгоритма. Важно было проверить сам факт осуществления платежа в указанный срок. Посему установка даты являлась всего лишь степом для достижения конечной цели. Таким образом, было гораздо проще ее получать динамически от АПИ, и подстраивать под нужную локаль.

В общем, it depends. Если дашь больше данных, можно подумать детальней.


(Oleksandr Khotemskyi) #3

Пока у меня задача довольно простая. К примеру, я вбиваю в календарь на главной странице 30 августа 2019. На следующей странице она отображается в формате 30.08.2019 а на странице confirmation - 30/08/2019. Хочу сравнить что дата нормально передалась по всему flow.

Ну а moment-timezone конечно подключил, без него работать с таймзонами намного сложней


(Sergey Korol) #4

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


(Михаил Новицкий) #5

Вот как я делаю, хотя у меня только две таймзоны)

String runEnvironmentName = new RunEnvironment().getName();

SimpleDateFormat f = new SimpleDateFormat(“yyyy-MM-dd HH:mm”);
if (runEnvironmentName.equals(“dev”)){
f.setTimeZone(TimeZone.getTimeZone(“GMT-4”));
} else {
f.setTimeZone(TimeZone.getTimeZone(“GMT-8”));
}
String currentDate = f.format(new Date());

так я получаю дату текущую и сравниваю с записью в БД, которую создает тест