8

Я использую рубиновый камень watir-webdriver. Он запускает браузер (Chrome) и начинает загружать страницу. Страница загружается слишком медленно, и watir-webdriver вызывает ошибку таймаута. Как заставить браузер перестать загружать страницу?Сделать загрузку без браузера на страницу загрузки

require 'watir-webdriver' 

client = Selenium::WebDriver::Remote::Http::Default.new 
client.timeout = 10 
@browser = Watir::Browser.new :chrome, :http_client => client 

sites = [ 
    "http://google.com/", 
    "http://yahoo.com/", 
    "http://www.nst.com.my/", # => This is the SLOW site 
    "http://drupal.org/", 
    "http://www.msn.com/", 
    "http://stackoverflow.com/" 
] 

sites.each do |url| 

    begin 
    @browser.goto(url) 
    puts "Success #{url}" 
    rescue 
    puts "Timeout #{url}" 
    end 

end 

########## Execution result ########## 

# Success http://google.com/ 
# Success http://yahoo.com/ 
# Timeout http://www.nst.com.my/ 
# Timeout http://drupal.org/ 
# Timeout http://www.msn.com/ 
# Timeout http://stackoverflow.com/ 

########## Expected result ########## 

# Success http://google.com/ 
# Success http://yahoo.com/ 
# Timeout http://www.nst.com.my/ 
# Success http://drupal.org/ 
# Success http://www.msn.com/ 
# Success http://stackoverflow.com/ 

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

ОБНОВЛЕНО

Я нашел интересный возможность флаг loadAsync http://src.chromium.org/svn/trunk/src/chrome/test/webdriver/webdriver_capabilities_parser.cc Может быть, это может быть полезно для решения этой проблемы? Я еще не понимаю, как заставить watir (webdriver) установить это при запуске хромированного ребра. Этот флаг был введен здесь http://codereview.chromium.org/7582005/

+0

На вершине моей головы есть только одно объяснение этой вещи. Ватир однопоточный. –

+0

Я не пытаюсь использовать его в нескольких потоках.Мне просто интересно, почему после одной команды и ее таймаута невозможно выполнить следующую команду. – Molfar

+0

Когда я говорю однопоточное, я имею в виду, что при отправке комманда webdriver для выполнения чего-то вы синхронный вызов и ничего не можете сделать, пока не получите ответ от webdriver. Так что вещь, которую вы хотите сделать в этом сценарии, не может быть выполнена, пока вы не измените синхронный вызов на асинхронный. –

ответ

4

Есть несколько различных способов сделать то, что Вы желаете, но вот что я хотел бы сделать:

require 'watir-webdriver' 

client = Selenium::WebDriver::Remote::Http::Default.new 
client.timeout = 60 
@browser = Watir::Browser.new :firefox, :http_client => client 

begin 
    @browser.goto mySite 
rescue => e 
    puts "Browser timed out: #{e}" 
end 

next_command 

Если у вас есть много сайтов, которые вы пытаетесь для загрузки для подтверждения таймаута или нет, поместите их в массив:

mySites = [ 
      mySite1, 
      mySite2, 
      mySite3 
] 

mySites.each do |site| 
    begin 
     @browser.goto site 
    rescue 
     "Puts #{site} failed to load within the time allotted." 
    end 
end 

ОБНОВЛЕНИЕ для доказательства концепции. Этот скрипт всегда переходит к шагу 2. Спасание не требуется даже для второго goto, но используется для более четкого вывода. Как ваш сценарий отличается от этого?

require 'watir-webdriver' 

client = Selenium::WebDriver::Remote::Http::Default.new 
client.timeout = 1  #VERY low timeout to make most sites fail 
@browser = Watir::Browser.new :firefox, :http_client => client 


def testing 
    begin 
    @browser.goto "http://www.cnn.com" 
    rescue => e 
    puts "Browser timed out on the first example" 
    end 

    begin 
    @browser.goto "http://www.foxnews.com" 
    rescue => e 
    puts "Browser timed out on the second example" 
    end 
end 
+0

Проблема в том, что любая команда next_command (например, @ browser.goto "http://another-site.com" или @ browser.close) вызовет еще одну ошибку Timeout. Похоже, что браузер «заморожен» после первого таймаута. – Molfar

+0

@Molfar Я пробовал это несколько раз, и я не могу воспроизвести вашу ошибку. Я добавил пример кода, чтобы показать вам, что я пытаюсь, и работает, как ожидалось. –

+0

Вот мой тестовый код http://pastebin.com/vNiKZ9tP Он подтверждает описанное поведение. Интересно, почему сценарий достигает второго блока спасения. Он отличается от вашего кода тем, что только первый сайт должен достичь таймаута. – Molfar

2

Вы можете остановить загрузку Google страницы с помощью AutoIT, чтобы отправить клавишу Escape. Это похоже на то, что вы изначально пытались сделать, но используя AutoIT напрямую, а не через сломанный Watir :: Browser.

require 'watir-webdriver' 
require 'win32ole' 

client = Selenium::WebDriver::Remote::Http::Default.new 
client.timeout = 5 
@browser = Watir::Browser.new :chrome, :http_client => client 
begin 
    @browser.goto "http://www.nst.com.my/" 
rescue 
    autoit = WIN32OLE.new("AutoItX3.Control") 
    autoit.AutoItSetOption("WinTitleMatchMode", 2) 
    autoit.WinActivate("Google") 
    autoit.Send("{ESC}") 
end 
@browser.goto "http://www.google.ca" 

Примечание: Я пытался получить autoit.ControlSend("Google", "", "", "{ESC}") работать так, чтобы он не нужен браузер, чтобы быть активным. Хотя он работал, когда запускался сам по себе, по какой-то причине я никогда не смог заставить его работать в вышеупомянутом скрипте (т. Е. Был отправлен ключ, но браузер не реагировал так, как ожидалось).

+1

Все работает на Linux-машине в режиме без звука (производство). – Molfar

0

Я некоторое время борюсь с этой проблемой, я знаю, что это сообщение с 2012 года, но я до сих пор не нашел ничего, что решает эту проблему. Поэтому я сделал работу.

require 'watir-webdriver' 

client = Selenium::WebDriver::Remote::Http::Default.new 
client.timeout = 5 
@browser = Watir::Browser.new :firefox, :http_client => client 

@browser.goto "twitter.com" 

#after the page loads, log in 
def test  
    begin 
    temp = [] 
    temp = @browser.cookies.to_a 
    @browser.goto "twitter.com:81" 
    rescue => e 
    puts "Browser timed out" 
    @browser.close 
    @browser = Watir::Browser.start "twitter.com" 

    temp.each do |me| 
     @browser.cookies.add(me[:name], me[:value]) 
    end 
    @browser.refresh 

    end 
end 

Дополнительный код, который сохраняет и восстанавливает файлы cookie, позволит вам войти в систему на сайтах, которые вы используете. Это отстой, но это единственная работа, о которой я могу думать. Снова это было в 2012 году, поэтому, если кто-нибудь найдет что-нибудь, что лучше работает, пожалуйста, поправьте меня.

+0

Он не разрешает проблему, потому что ваш браузер @ не работает. – Molfar

+0

На моем компьютере он делает. Я использую Linux debian 3.2.0-4-amd64 # 1 SMP Debian 3.2.57-3 + deb7u1 x86_64 GNU/Linux, с Firefox 17.0.10, watir 5, watir-webdriver 0.6.4 – Duck1337

+0

ruby ​​1.9.3p484 (версия 2013-11-22 версия 43786) [x86_64-linux] – Duck1337

0

У меня также была проблема с таймаутами. Мое понимание из онлайн-исследований заключается в том, что после того, как Selenium WebDriver встретит тайм-аут, он попадает в плохую форму и неверно работает (проблема многопоточности). Я следовал советам найти здесь:

https://github.com/watir/watir-webdriver/issues/137

Я реализовал активное убийство (вместо browser.close) и повторный запуск Watir::Browser после любого спасения исключения.