#protractor
#транспортир
Вопрос:
Мы тестируем приложения JS с помощью транспортира, и иногда мы получаем несколько случайно нестабильных тестов. Иногда возникают ошибки Сбой: устаревшая ссылка на элемент: элемент не прикреплен к документу страницы
Просто догадка, но иногда разработчики пишут код следующим образом
await element(await by.css('.pager-next')).click();
И иногда вот так
await element(by.css('.pager-next')).click();
Является ли любой из этих «более» правильным? Есть ли какая-либо необходимость во внутреннем ожидании или это не имеет значения? Может ли это быть причиной ошибок ссылки на устаревший элемент?
Ответ №1:
await
полезно только для функций, которые возвращают Promise
. Из трех функций в вашем фрагменте только одна из них возвращает Promise
. (Вы можете проверить, что каждый из них возвращает в Protractor api).
ElementFinder.click()
возвращает Promise
.
element()
возвращает ElementFinder
.
by.css()
возвращает ProtractorLocator
.
Следовательно, единственный вызов, который должен иметь await
значение, это click()
, который вы правильно выполнили во втором фрагменте.
StaleElementReferenceException
обычно возникает, когда вы сохраняете ссылку на объект, который был удален со страницы, например, с помощью ElementFinder.getWebElement()
. Иногда это удаление может быть незаметным. Например, Angular иногда незаметно удаляет элемент из DOM и быстро заменяет его на идентично выглядящий. Трудно сказать, что что-то вообще изменилось, но с точки зрения Webdriver элемент, на который у него была ссылка, исчез.
Ответ №2:
Я думаю, что лучшей практикой было бы не использовать локаторы записи, подобные этому. Я бы оставил ожидания для функций, связанных с элементом. У меня был бы локатор, написанный следующим образом:
const myElement = element(by.css('.pager-next'));
А затем использовать async / await в функции:
let clickMyElement = async function(){
await myElement.click();
};
Комментарии:
1. Чем это лучше, чем
await element(by.css('.pager-next')).click();
?