Selenium how to manage wait for page load?
To wait for document.readyState
to be complete
isn't a full proof approach to ensure presence, visibility or interactibility of an element.
Hence, the function:
JavascriptExecutor js = (JavascriptExecutor) driver.getWebDriver();
String result = js.executeScript("return document.readyState").toString();
if (!result.equals("complete")) {
Thread.sleep(1000)
}
}
And even waiting for jQuery.active == 0
:
public void WaitForAjax2Complete() throws InterruptedException
{
while (true)
{
if ((Boolean) ((JavascriptExecutor)driver).executeScript("return jQuery.active == 0")){
break;
}
Thread.sleep(100);
}
}
Will be a pure overhead.
You can find a couple of relevant discussions in:
- Selenium IE WebDriver only works while debugging
- Do we have any generic function to check if page has completely loaded in Selenium
Solution
The effective approach will be to induce WebDriverWait inconjunction with the ExpectedConditions either for:
- presence of element
- visibility of element
- interactibility of element
You can find a couple of relevant discussions in:
- Selenium: How selenium identifies elements visible or not? Is is possible that it is loaded in DOM but not rendered on UI?
- WebDriverWait not working as expected
More than one thread to crawl
WebDriver is not thread-safe. Having said that, if you can serialise access to the underlying driver instance, you can share a reference in more than one thread. This is not advisable. But you can always instantiate one WebDriver instance for each thread.
Ideally the issue of thread-safety isn't in your code but in the actual browser bindings. They all assume there will only be one command at a time (e.g. like a real user). But on the other hand you can always instantiate one WebDriver instance for each thread which will launch multiple browsing tabs/windows. Till this point it seems your program is perfect.
Now, different threads can be run on same Webdriver, but then the results of the tests would not be what you expect. The reason behind is, when you use multi-threading to run different tests on different tabs/windows a little bit of thread safety coding is required or else the actions you will perform like click()
or send_keys()
will go to the opened tab/window that is currently having the focus regardless of the thread you expect to be running. Which essentially means all the test will run simultaneously on the same tab/window that has focus but not on the intended tab/window.
Selenium page loading wait methods
There are two different concepts here. The first is that with w3c you can now set a Page Load Strategy in the capabilities at the beginning of a session. This affects what Document readiness state the driver will wait for before returning control to the user. If the specified readiness state is not satisfied before the page load timeout, the driver is supposed to return an error.
Note that both of these things only apply to navigation events, so clicking an element that results in a page load should not trigger these.
To complicate things one more level, Chromedriver has an open bug for incorrectly:
wait[ing] for navigation to complete at the end of almost all commands
So for right now Chrome tests actually will wait for the specified document readiness state on clicks.
Finally, remember that for today's web there is typically a lot of content loaded dynamically via JavaScript, so even when the document readiness state is "complete" the DOM is unlikely to be in it's final state, which is why you are encouraged to use explicit waits for the things you actually want to interact with.
Related Topics
Accept Server'S Self-Signed Ssl Certificate in Java Client
What Are the Effects of Exceptions on Performance in Java
How to Capitalize the First Character of Each Word in a String
Draw a Line in a Jpanel With Button Click in Java
How to Implement a Single Instance Java Application
Java Error: Comparison Method Violates Its General Contract
How to Handle Events from Keyboard and Mouse in Full Screen Exclusive Mode in Java
Intersection and Union of Arraylists in Java
Why Are Arrays Covariant But Generics Are Invariant
How to Measure Time Elapsed in Java
Difference Between String Object and String Literal
Fastest Way to Determine If an Integer'S Square Root Is an Integer
Getting Hold of the Outer Class Object from the Inner Class Object
Swing: Link Toggle Buttons Together With a Button Group, Along With Corresponding Menu Items
Difference Between ≪Context:Annotation-Config≫ and ≪Context:Component-Scan≫