我目前正在将Selenium用于网络爬虫应用程序,并且在成功使用了几个模块之后,以下情况使我陷于困境:我试图通过文本“ Reports”找到位于其中的“菜单”类的元素一个名为“ frame_applic”的框架。
很简单,对吧?应该很简单:
browser = webdriver.Chrome()
#Do the necessary crawling to get to this specific menu...
browser.switch_to_frame('frame_applic')
for obj in browser.find_elements_by_class_name('menu'):
if obj.text == 'Reports':
bt_reports = obj
break
#The variable bt_reports should be the one requested.
这是有趣的地方:尽管当我尝试切换到所需的帧时没有出现错误,但是没有找到类名称为“菜单”的元素。当然,我肯定拼错了框架或类名,对吗?因此,在决定检查HTML并且不做任何其他更改之后,这些元素就存在了,就好像仅查看网页源代码的行为就改变了结果的结果一样。这里可能会发生什么?
不允许发布完整的HTML,但是以下结构包含了这个问题:
<html>
<head>
<TITLE>Page</TITLE>
</head>
<frameset ...>
<frame name="frame_menu" src="https:..." >
<frame name="frame_applic" src="menu.asp?...">
#document
<table width="100%" border="0" cellpadding="5" cellspacing="0">
<tr>
<td colspan="2" align="right">
<table width="95%" border="0" cellpadding="5" cellspacing="0">
<tr><td><a href="https:..." class="menu">Reports</a></td></tr>
<tr><td><a href="https:..." class="menu">Change Password</a></td></tr>
<tr><td><a href="https:..." class="menu">Change Secret Phrase</a></td></tr>
</table>
</td>
</tr>
</table>
</body>
<frame name="frame_bottom" src="https:...">
</frameset>
</html>
答案 0 :(得分:1)
经过仔细检查,我发现潜在的问题是所需帧中的源信息在Active Server Page(asp)中,如下所示:
<frame name="frame_applic" src="menu.asp?...">
它不能从我所在的页面上直接访问。 在浏览器上检查元素的行为显然迫使这些元素共存于webdriver实例中,这使我能够在框架内获取元素,而以前无法访问它们。
我能够解决此问题,方法是先找到请求的框架,然后将Webdriver指向它的源,方法是:
browser.get(browser.find_element_by_xpath("//frame[@name='frame_applic']")\
.get_attribute('src'))
然后像以前一样简单地获取元素,
menu_list = browser.find_elements_by_class_name('menu')