如何使用 java 在 Selenium WebDriver 中处理 iframe

Posted

技术标签:

【中文标题】如何使用 java 在 Selenium WebDriver 中处理 iframe【英文标题】:How to handle iframe in Selenium WebDriver using java 【发布时间】:2012-04-14 03:15:41 【问题描述】:
<div>    
  <iframe id="cq-cf-frame ">    
    <iframe id="gen367">   
      <body spellcheck="false" id="CQrte" style="height: 255px; font-size: 12px; font-family:tahoma,arial,helvetica,sans-serif; background-image: url(&quot;/libs/cq/ui/widgets/themes/default/ext/form/text-bg.gif&quot;); background-repeat: repeat-x; background-attachment: fixed;">
        <p>4t43t4<br></p>
      </body >
    </iframe>
  </iframe>    
</div> 

在这种情况下,iframe 下有一个 iframe。我必须选择外部iframe 去内部iframe 并写入内部iframe 的正文。

接下来,我必须从内部iframe 出来到外部iframe 并点击OK 按钮,(在外部iframe 中)。

以下是我的代码

/*Line 1 */ driver.switchTo().frame("cq-cf-frame");
/*     2 */ driver.findElement(By.css("#extdd-9 > div.tblRow >  input.edititem").click();
/*     3 */ driver.switchTo().Frame("cq-gen379");
/*     4 */ driver.findElement(By.id("CQrte").sendKeys("Tnx");  
/*     5 */ selenium.selectFrame("relative=up");       
/*     6 */ driver.findElement(By.xpath("//button[text()='OK']")).click(); 

以下是我的问题:

我的测试代码在第 4 行之前工作正常,即写入正文,但我想从内到外出来 iframe 它说元素 //button[text()='OK'] 未找到。

我尝试使用索引、父级、相对级,但没有成功。

注意:如果我不选择内框 (cq-gen379)。我可以点击确定按钮。

【问题讨论】:

【参考方案1】:

您必须使用以下代码退出 iframe:

driver.switchTo().frame(driver.findElement(By.id("frameId")));
//do your stuff
driver.switchTo().defaultContent();

【讨论】:

我同意这个答案。在“//do your stuff”部分中,如果返回的 DOM 恰好显示为空,我将使用 javascriptExectutor。问:为什么实际标签名称是“iframe”时方法调用“.frame”???框架/框架集不是与 iframe 不同吗? 您好,这只是我的猜测,但 iframe 仍然是某种框架,并且这段代码不是 iframe 独有的,因此它应该与其他框架一起使用(我没有检查) 如果您使用driver.getCurrentUrl().then(function(data) console.log("the url is : "+data); ); 保存网址,您会发现它是一条没有某些功能的不同路径。您基本上已经留下了所有脚本。我仍在尝试自己解决这个问题。【参考方案2】:

在 Webdriver 中,您应该使用 driver.switchTo().defaultContent(); 来跳出框架。 您需要先退出所有框架,然后再切换到外框架。

// between step 4 and step 5
// remove selenium.selectFrame("relative=up");
driver.switchTo().defaultContent(); // you are now outside both frames
driver.switchTo().frame("cq-cf-frame");
// now continue step 6
driver.findElement(By.xpath("//button[text()='OK']")).click(); 

【讨论】:

另外,作为一个仅供参考:我发现 switchTo().frame 需要隐式等待禁用:driver.manage().timeouts().implicitlyWait(0, TimeUnit.SECONDS);【参考方案3】:

要返回父框架,请使用:

driver.switchTo().parentFrame();

要返回第一个/主框架,请使用:

driver.switchTo().defaultContent();

【讨论】:

【参考方案4】:

您需要先找到iframe。您可以使用以下语句来执行此操作。

WebElement iFrame= driver.findElement(By.tagName("iframe"));

然后,您可以在 WebDriver 对象上使用 switchTo 方法切换到它。

driver.switchTo().frame(iFrame);

要返回父框架,您可以使用switchTo().parentFrame(),或者如果您想返回主(或最父)框架,您可以使用switchTo().defaultContent();

driver.switchTo().parentFrame();    // to move back to parent frame
driver.switchTo().defaultContent(); // to move back to most parent or main frame

希望对你有帮助。

【讨论】:

【参考方案5】:
WebDriver driver=new FirefoxDriver();
driver.get("http://www.java-examples.com/java-string-examples");
Thread.sleep(3000);
//Switch to nested frame
driver.switchTo().frame("aswift_2").switchTo().frame("google_ads_frame3");

【讨论】:

【参考方案6】:

下面的框架处理方法:当嵌套框架没有给出 id 或 name 时

WebElement element =driver.findElement(By.xpath(".//*[@id='block-block19']//iframe"));
driver.switchTo().frame(element);
driver.findElement(By.xpath(".//[@id='carousel']/li/div/div[3]/a")).click();

【讨论】:

【参考方案7】:

Selenium Web 驱动程序处理框架 因为iframe是一个iframe,所以无法通过XPath直接点击iframe。 首先我们必须切换到框架,然后我们可以使用 xpath 进行点击。

driver.switchTo().frame() 有多个重载。

    driver.switchTo().frame(name_or_id) 这里你的iframe 没有id 或名字,所以不适合你。

    driver.switchTo().frame(index) 这是最后一个选择,因为使用索引并不像你想象的那样稳定。如果这是页面中唯一的 iframe,请尝试 driver.switchTo().frame(0)

    driver.switchTo().frame(iframe_element) 最常见的一种。您可以像其他元素一样定位 iframe,然后将其传递给方法。

driver.switchTo().defaultContent(); [parentFrame, defaultContent, frame]

// Based on index position:
int frameIndex = 0;
List<WebElement> listFrames = driver.findElements(By.tagName("iframe"));
System.out.println("list frames   "+listFrames.size());
driver.switchTo().frame(listFrames.get( frameIndex ));

// XPath|CssPath Element:
WebElement frameCSSPath = driver.findElement(By.cssSelector("iframe[title='Fill Quote']"));
WebElement frameXPath = driver.findElement(By.xpath(".//iframe[1]"));
WebElement frameTag = driver.findElement(By.tagName("iframe"));

driver.switchTo().frame( frameCSSPath ); // frameXPath, frameTag


driver.switchTo().frame("relative=up"); // focus to parent frame.
driver.switchTo().defaultContent(); // move to the most parent or main frame

// For alert's
Alert alert = driver.switchTo().alert(); // Switch to alert pop-up
alert.accept();
alert.dismiss();

XML 测试:

<html>
    <IFame id='1'>...       parentFrame() « context remains unchanged. <IFame1>
    |
     -> <IFrame id='2'>...  parentFrame() « Change focus to the parent context. <IFame1>
</html>

</html>
<frameset cols="50%,50%">
    <Fame id='11'>...     defaultContent() « driver focus to top window/first frame. <html>
    |
     -> <Frame id='22'>... defaultContent() « driver focus to top window/first frame. <Fame11> 
                           frame("relative=up") « focus to parent frame. <Fame11>
</frameset>
</html>

将 RC 转换为 Web-Driver Java 命令。 link.


&lt;frame&gt; 是一个 HTML 元素,它定义了一个可以显示另一个 HTML 文档的特定区域。应在&lt;frameset&gt; 中使用框架。 « Deprecated。不适用于新网站。

【讨论】:

以上是关于如何使用 java 在 Selenium WebDriver 中处理 iframe的主要内容,如果未能解决你的问题,请参考以下文章

已下载 Selenium Webdriver Java zip,但缺少 selenium JAR

零基础Selenium:Webdriver图文入门教程java篇(附相关包下载)

Selenium eclipse 配置与 Webdriver 2 和 Selenium Java 客户端驱动程序

如何在 Selenium Webdriver 3 中为 Firefox 驱动程序设置默认配置文件?

Selenium 验证 div 是不是有滚动条

Chrome如何设定webdriver=undefined以避免Selenium检测?