I am using Selenium to test a web app that uses Dojo, and it uses java script to display certain elements. I want to wait until all of the elements are desplayed before I try to manipulate the page, however I am having trouble.
I have started by waiting for the dojo inFlight variable to be 0, this says that all ajax has finished. This doesn't always work because it seems to do some things on a timeout afterwards.
I have also tried repeatedly looking for the element, but this isn't too nice, as perhaps there is some javascript later which will use this field in some way.
So basically I want a method (in firefox at least) to query the javascript waiting to run on a setTimeout (or setInterval) I could even cope with a way of wrapping the built in call through a function of my own just to keep track of this.
Any thoughts or suggestions appreciated!
I am using Selenium to test a web app that uses Dojo, and it uses java script to display certain elements. I want to wait until all of the elements are desplayed before I try to manipulate the page, however I am having trouble.
I have started by waiting for the dojo inFlight variable to be 0, this says that all ajax has finished. This doesn't always work because it seems to do some things on a timeout afterwards.
I have also tried repeatedly looking for the element, but this isn't too nice, as perhaps there is some javascript later which will use this field in some way.
So basically I want a method (in firefox at least) to query the javascript waiting to run on a setTimeout (or setInterval) I could even cope with a way of wrapping the built in call through a function of my own just to keep track of this.
Any thoughts or suggestions appreciated!
Share Improve this question asked Aug 18, 2011 at 8:16 Sam MarlandSam Marland 5823 silver badges24 bronze badges3 Answers
Reset to default 6Every function in JavaScript can be replaced. Consider something like this:
window.originalSetTimeout = window.setTimeout;
window.setTimeout = function(func, delay, params) {
window.timeoutCounter++;
window.originalSetTimeout(window.timeoutCallback, delay, [func, params]);
}
window.timeoutCallback = function(funcAndParams) {
window.timeoutCounter--;
func = funcAndParams[0];
params = funcAndParams[1];
func(params);
}
Then:
selenium.waitForCondition("window.timeoutCounter == 0");
Whenever you call setTimeout
of setInterval
-- a timer id is returned.
- Save that timer id in an array
- Inside the function that you're calling on the timeout, pop that timer id off the array. Because we have to remove that id from the array as soon as the timer ends.
- Any time you want to check the no. of active timers, just query the length of that array.
Another approach could be like this
const timeoutIndexThen = setTimeout(() => {});
// Some code that might call timeouts...
const timeoutIndexNow = setTimeout(() => {});
const countOfTimeoutsFiredSinceThen = timeoutIndexNow - timeoutIndexThen - 1;
It is based on the fact that each timeout will return a number that is greater by 1 on each call.
So we create some dummy timeout just to get this number at some point.
Then, after a while we call it again and we get a new number. Difference between those numbers is how many times interval was called in between.
Downside of this is that you have to actually create the timeout. Upside is that you don't have to modify original function.