fing
fing

Reputation: 358

Handling Chrome client certificates in Watir tests

I have an application with client-certificate based authentication which I have been trying to automate. By selecting different certificates the user can get different application rights. The idea is to use watir-webdriver based script and rautomation gem and login into the application. In Chrome web browser it looks pretty much like this:

client-certificate

The basic idea is the following:

require 'watir-webdriver'
require 'rautomation'

b = Watir::Browser.new :chrome  
b.goto 'https://example.com' 

# Get the Chrome window
window = RAutomation::Window.new(:title => /Chrome/i)
# Select client certificate     
window.send_keys :return

However, when the script executes and reaches b.goto 'https://example.com' it is stuck because the page is not loaded until certificate is selected. After 60 seconds this results in client timeout and I get a Net::ReadTimeout exception. Thus, the code for certificate selection is never reached.

I have solved this by catching the Net::ReadTimeout exception:

begin
 b.goto 'https://example.com' 
rescue      
  window = RAutomation::Window.new(:title => /Chrome/i)   
  window.send_keys :return
end

This solution is far from optimal as the script has to wait 60 seconds to start the execution. The timeout can be lowered to reasonable wait times with the following piece of code:

client = Selenium::WebDriver::Remote::Http::Default.new
client.timeout = 5 # seconds – default is 60
b = Watir::Browser.new :chrome, :http_client => client

But for the rest of the script client.timeout of 5 seconds would be far too low.

I thought the problem was with goto so I've tried other methods but it seems they all behave in the same way:

b.driver.navigate.to 'https://example.com' # => Net::ReadTimeout
b.execute_script('window.location.href = "https://example.com"') # => Net::ReadTimeout

Can anyone provide me with an optimization advice or some other optimal way to handle the mentioned client certificates?

Upvotes: 0

Views: 936

Answers (2)

Jarmo Pertman
Jarmo Pertman

Reputation: 1905

Wouldn't Thread help you out in here? Not sure if it would, because it depends on Ruby's GIL (global interpreter lock) and underlying Webdriver's technicalities, but you could give it a try.

Something along in these lines could work (not tested):

t = Thread.start { b.goto }

# Not sure if getting handle works or not, but if it does
# then it should be a better way to locate the browser window
window = RAutomation::Window.new(:hwnd => b.window.handle)

# Wait until client certificate window exists
RAutomation::WaitHelper.wait_until { window.windows.any? { |w| w.text =~ /Select a certificate/ }}

# Select client certificate     
window.send_keys :return

# Wait for the page load to finish
t.join

Upvotes: 3

titusfortner
titusfortner

Reputation: 4194

Watir only works on browser rendered pages. Try ignoring the certificate completely. http://watirwebdriver.com/browser-certificates/

Upvotes: 0

Related Questions