The issue I am having is switching to the parent frame or iFrame using webdriver.js. I tried implementing a function to do this and it does work but only up to the second level of frames. If I wanted to switch to the parent frame from a frame that is like 4 or 5 levels deep this function would be even fuglier than what it is now. One of the major issues is that I have to use a for loop to get the top level of frames and then loop through each of those frames to get there nested frames if they have any. I have to be able to keep looping until no frames have any frames that are nested. Also as you can tell the solution below has alot of redundant code and nested to the point of callback hell. I tried to extract the for loop process to a helper function but the problem I have with that is that I have to switch back to the top level and then navigate back down the frame ladder to check each frame for nested frames. I added comments to help with the ugliness.
this.switchToParentFrame = function (frameOrIFrame) {
//Keep local variable of current frame name
var currentFrameName;
//Get current frame name
this.getCurrentFrameName().then(function (name) {
currentFrameName = name;
return driver.switchTo().defaultContent();
}).then(function () {
//Find top level frames
return driver.findElements(webdriver.By.css(frameOrIFrame));
}).then(function (frames) {
//Loop through each top level frame to find nested frames
frames.forEach(function (frame) {
//Switch back to the default content to check each top level frame
driver.switchTo().defaultContent().then(function () {
return driver.switchTo().frame(frame);
}).then(function () {
//Find the nested frames for each top level frame
return driver.findElements(webdriver.By.css(frameOrIFrame));
}).then(function (nestFrames) {
//Check to make sure the top level frame has a nested frame
if (nestFrames.length > 0) {
//Loop through each nested frame to check its name with the current frame name var
nestFrames.forEach(function (nestFrame) {
//Switch to the default content to switch frames
driver.switchTo().defaultContent().then(function () {
//Switch to the top level frame
return driver.switchTo().frame(frame);
}).then(function() {
//switch to the nested frame
return driver.switchTo().frame(nestFrame);
}).then(function () {
//Get the nested frames name
return driver.executeScript('return self.name');
}).then(function (name) {
//Check to see if the nested frames name is equal to the current frame name var and if so set it equal to the parent frame
if (name === currentFrameName){
currentFrameName = frame;
}
});
});
}
});
});
}).then(function() {
return driver.switchTo().defaultContent();
}).then(function() {
//Switch to the parent frame
return driver.switchTo().frame(currentFrameName);
});
};