代码之家  ›  专栏  ›  技术社区  ›  Samix

Selenium在关闭另一个iframe时切换到错误的iframe

  •  1
  • Samix  · 技术社区  · 6 年前

    我用硒来做一些测试。我的问题是我有4个嵌套的iframes,当我关闭一个iframes时,Selenium切换到错误的iframes。

    为了帮助你理解我的问题,我有一个小草图:

    所以我的第一帧(黑色的)打开一个嵌套的帧(灰色的),打开另一帧(橙色的),再次打开另一帧(白色的)。问题是:当我关闭白色框架时,Selenium切换到灰色框架,但Is应正常切换到橙色框架。

    当帧关闭时,我使用 driver.switchto().parentframe(); 。每次都很好,但在这种情况下,它不起作用,我找不到问题。

    我尝试了一些测试代码作为

    if(driver.findelements(by.xpath(“//iframe”)).size()>0){
    driver.switchto().frame(driver.findElements(by.xpath(“//iframe”)).size()-1);
    }
    

    但它也不起作用。

    如果有人有想法或遇到同样的问题,我很乐意尝试您的答案。

    编辑:这是我的stacktrace,因此在执行某些操作之前,我切换到所需的帧:

    frameLocator=by.xpath://*[@id='greyWindow']
    __切换前和执行前__
    当前帧=:标题=默认窗口
    
    __切换后和执行前__
    currentframe=<iframe src=grey id=greyWindow>
    
    frameLocator=by.xpath://*[@class='redwindow']
    __切换前和执行前__
    currentframe=<iframe src=grey id=greyWindow>
    
    __切换后和执行前__
    currentframe=<iframe src=red class=redwindow>
    
    framelocator=by.xpath://iframe[包含(@src,'whitewindow')]
    __切换前和执行前__
    currentframe=<iframe src=red class=redwindow>
    
    __切换后和执行前__
    currentframe=<iframe src=whitewindow>
    
    当前可用的框架:【RemoteWebDriver:Chrome on Linux(5C408EF997226A10C864CBEEC0A2472d)】
    ->标记名:iframe]frame.getattribute(“innerhtml”)=//未显示任何内容
    当前可用的框架:【RemoteWebDriver:Chrome on Linux(5C408EF997226A10C864CBEEC0A2472d)】
    ->标记名:iframe]frame.getattribute(“innerhtml”)=//未显示任何内容
    
    //在这里,我只放了一些值,然后像以前一样关闭帧
    
    __切换前和执行后__
    当前帧=标题=默认窗口
    
    __切换后和执行后__
    当前帧=标题=默认窗口
    

    然后我得到nullpointerException,因为当前帧不是红色窗口而是默认窗口enter image description here

    所以我的第一帧(黑色的)打开一个嵌套的帧(灰色的),打开另一帧(橙色的),再次打开另一帧(白色的)。问题是:当我关闭白色框架时,硒会切换到灰色框架,但正常情况下应该切换到橙色框架。

    当框架关闭时,我使用driver.switchTo().parentFrame();.每次都很好,但在这种情况下,它不起作用,我找不到问题。

    我尝试了一些测试代码作为

    if (driver.findElements(By.xpath("//iframe")).size() > 0) {
         driver.switchTo().frame(driver.findElements(By.xpath("//iframe")).size() - 1);
    }
    

    但它也不管用。

    如果有人有想法或遇到同样的问题,我很乐意尝试你的答案。

    编辑:这是我的stacktrace,因此在执行某些操作之前,我切换到所需的帧:

    frameLocator = By.xpath: //*[@id='greyWindow']
    ___Before switch and before execute___ 
    CurrentFrame =: title=defaultWindow
    
    ___After switch and before execute___ 
    CurrentFrame = <IFRAME src=grey id=greyWindow>
    
    frameLocator = By.xpath: //*[@class='redWindow']
    ___Before switch and before execute___ 
    CurrentFrame = <IFRAME src=grey id=greyWindow>
    
    ___After switch and before execute___
    CurrentFrame = <IFRAME src=red class=redWindow>
    
    frameLocator = By.xpath: //iframe[contains(@src,'whiteWindow')]
    ___Before switch and before execute___ 
    CurrentFrame = <IFRAME src=red class=redWindow>
    
    ___After switch and before execute___ 
    CurrentFrame = <IFRAME src=whiteWindow>
    
    Frame currently available : [[RemoteWebDriver: chrome on LINUX (5c408ef997226a10c864cbeec0a2472d)] 
    -> tag name: iframe] | frame.getAttribute("innerHTML") = // Nothing appear
    Frame currently available : [[RemoteWebDriver: chrome on LINUX (5c408ef997226a10c864cbeec0a2472d)]
    -> tag name: iframe] | frame.getAttribute("innerHTML") = // Nothing appear
    
    //Here i just put some value and close the frame as every frame before
    
    ___Before switch and after execute___ 
    CurrentFrame = title=defaultWindow
    
    ___After switch and after execute___ 
    CurrentFrame = title=defaultWindow
    

    然后我得到nullpointerException,因为当前帧不是红色窗口而是默认窗口

    3 回复  |  直到 6 年前
        1
  •  1
  •   Shivam Mishra    6 年前

    为什么不按名称或其他选择器切换到帧?

    driver.switchTo().frame("name_or_id");
    

    或者您可以尝试将框架保存在WebElement变量中,然后切换到该变量。前任:

    WebElement iframeElement = driver.findElement(By.id("name"));
    driver.switchTo().frame(iframeElement);
    

    如注释中所述,如果在验证列表是否正确后需要从列表中访问iframes,可以尝试:

    List <WebElement> all_iframes = driver.findElements(By.tagName("iframe"));
    for(WebElement iframe : all_iframes)
    {
      if(iframe.getAttribute("name") == "your required name")
      { 
        //do some stuff
      }
    }
    
        2
  •  0
  •   Samix    6 年前

    使用 driver.switchTo().defaultContent();

    或使用: driver.switchTo().parentFrame();

        3
  •  0
  •   Samix    6 年前

    通过使用@shivam mishra的想法,我创建了以下方法:

    public static void switchToTheParentFrame(final WebDriver driver) {
            driver.switchTo().defaultContent();
            iframeList.remove(iframeList.size() - 1);
            final Iterator<By> itr = iframeList.iterator();
            if (!iframeList.isEmpty()) {
                while (itr.hasNext()) {
                    final WebElement frame = driver.findElement(itr.next());
                    try {
                        driver.switchTo().frame(frame);
                    } catch (final WebDriverException wde) {
                        LOG.error("Error while switching to the frame : " + frame.toString(), wde);
                    }
                }
            }
        }
    

    iFrameList 是一个全局变量,我在每个带有空列表的测试中初始化它。

    然后我可以继续我的测试而不会崩溃。所以我强迫硒回到良好的父框架。我希望这能帮助别人!