Селен неявно ждать не работает
Это первый раз, когда я использую селен и безголовый браузер, так как я хочу сканировать некоторые веб-страницы, используя технологию ajax.
Эффект отличный, но в некоторых случаях загрузка всей страницы занимает слишком много времени (особенно, когда какой-либо ресурс недоступен), поэтому мне нужно установить время для селена.
Прежде всего я попробовал set_page_load_timeout()
а также set_script_timeout()
, но когда я установлю эти таймауты, я не получу никакого источника страницы, если страница не загружается полностью, как показано ниже:
driver = webdriver.Chrome(chrome_options=options)
driver.set_page_load_timeout(5)
driver.set_script_timeout(5)
try:
driver.get(url)
except Exception:
driver.execute_script('window.stop()')
print driver.page_source.encode('utf-8') # raise TimeoutException this line.
поэтому я пытаюсь использовать неявное ожидание и условное ожидание, например:
driver = webdriver.Firefox(firefox_options=options, executable_path=path)
print("Firefox Headless Browser Invoked")
wait = WebDriverWait(driver, timeout=10)
driver.implicitly_wait(2)
start = time.time()
driver.get(url)
end = time.time()
print 'time used: %s s' % str(end - start)
try:
WebDriverWait(driver, 2, 0.5).until(expected.presence_of_element_located((By.TAG_NAME, 'body')))
print driver.find_element_by_tag_name('body').text
except Exception:
driver.execute_script('window.stop()')
На этот раз я получил контент, который мне нужен. Однако это занимает очень много времени (более 40 секунд), что означает, что тайм-аут, который я установил на 2 секунды, вообще не работает.
На мой взгляд, это похоже на driver.get()
вызов заканчивается до тех пор, пока браузер не прекратит загрузку страницы, только после этого могут работать приведенные ниже коды, и вы не сможете убить get()
позвони или ты ничего не получишь. Но это сильно отличается от документации по селену, мне ДЕЙСТВИТЕЛЬНО интересно, где ошибка.
среда: OSX 10.12, селен 3.0.9 с FireFox и GoogleChrome Headless(обе последние версии.)
--- Обновить ----
Спасибо за помощь. Я изменяю код, как показано ниже, используя WebDriverWait()
в одиночку, но все еще существуют случаи, когда вызов длится очень долго, намного больше, чем установленное мной время ожидания. Интересно, смогу ли я немедленно остановить загрузку страницы по истечении времени?
driver = webdriver.Firefox(firefox_options=options, executable_path=path)
print("Firefox Headless Browser Invoked")
start = time.time()
driver.get('url')
end = time.time()
print 'time used: %s s' % str(end - start)
try:
WebDriverWait(driver, 2, 0.5).until(expected.presence_of_element_located((By.TAG_NAME, 'body')))
print driver.find_element_by_tag_name('body').text
except Exception:
driver.execute_script('window.stop()')
driver.quit()
Вот вывод терминала в тесте:
Firefox Headless Browser Invoked
time used: 44.6049938202 s
в соответствии с кодом это означает driver.get()
вызов занимает 44 секунды, чтобы завершить вызов, что является неожиданным, интересно, неправильно ли я понял поведение безголовых браузеров?
1 ответ
Как вы упомянули в своем вопросе, загрузка всей страницы занимает слишком много времени (особенно когда какой-либо ресурс недоступен) в значительной степени возможен, если тестируемое приложение (AUT) использует вызовы JavaScript или AJAX.
- В вашем первом сценарии вы вызвали оба
set_page_load_timeout(5)
а такжеset_script_timeout(5)
set_page_load_timeout(time_to_wait)
: Устанавливает время ожидания завершения загрузки страницы, прежде чем выдать исключение.set_script_timeout(time_to_wait)
: Устанавливает время ожидания сценарияexecute_async_script
позвоните, прежде чем выбросить исключение.
Следовательно, тестируемое приложение, зависящее от вызовов JavaScript или AJAX при наличии обоих условий, вызывает TimeoutException.
В вашем втором сценарии вы вызвали оба
implicitly_wait(2)
а такжеWebDriverWait(driver, 2, 0.5)
,implicitly_wait(time_to_wait)
: Устанавливает время ожидания для неявного ожидания поиска элемента или выполнения команды.WebDriverWait(driver, timeout, poll_frequency=0.5, ignored_exceptions=None)
: Устанавливает таймаут в сочетании с различнымиexpected_conditions
- Но вы испытываете очень большой тайм-аут (40+ секунд), как это четко указано в документации. Не смешивайте неявные и явные ожидания, которые могут привести к непредсказуемым временам ожидания.
ВНИМАНИЕ: не смешивайте неявные и явные ожидания. Это может привести к непредсказуемому времени ожидания. Например, установка неявного ожидания 10 секунд и явного ожидания 15 секунд может привести к возникновению тайм-аута через 20 секунд.
Решение:
Лучшим решением будет удалить все экземпляры implicitly_wait(time_to_wait)
и заменить на WebDriverWait()
для стабильного поведения тестируемого приложения (AUT).
Обновить
Согласно вашему встречному вопросу, текущий блок кода выглядит идеально. Измерение времени, которое вы видите как time used: 44.6049938202 s
это время, необходимое для полной и функциональной загрузки веб-страницы, то есть время, необходимое клиенту (т. е. веб-браузеру) для возврата элемента управления обратно в экземпляр WebDriver после достижения значения document.readyState, равного "complete". Selenium или как пользователь, у вас нет контроля над этим процессом рендеринга. Однако для повышения производительности вы можете следовать следующим рекомендациям:
- Обновите свою версию JDK в настоящее время Java SE Development Kit 8u162
- Обновите версию Selenium Client в настоящее время селен 3.9.0
- Держите вашу версию WebDriver обновленной.
- Обновляйте версию своего веб-браузера.
- Регулярно очищайте рабочее пространство проекта в своей среде IDE, чтобы построить проект только с необходимыми зависимостями.
- Используйте инструмент CCleaner, чтобы стереть с себя рутинную работу ОС до и после выполнения Test Suite.
- Если базовая версия веб-браузера устарела, удалите веб-браузер с помощью Revo Uninstaller и установите последнюю версию GA, выпущенную веб-браузером.
- Выполните свой тест.