python - 无法让 XPath 单击 selenium 中的弹出窗口

标签 python selenium selenium-webdriver xpath selenium-chromedriver

我正在尝试从“SEC”中提取一些简单的“CIK”代码。如果运行下面的代码,您将收到有关“调查”的弹出消息。如果您手动执行此操作,您将看不到它。它轰炸了我的代码。但由于它是在 Selenium 中,我无法使用 chropath 检查它以使 xpath 单击“NO”。我无法在普通浏览器中重新创建弹出窗口。我该怎么办?

from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.common.by import By
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
import time
from random import randint

path ='C:\\Users\\Jason\\Google Drive\\python\\chromedriver.exe' 
ticker='alrm'
main='https://www.sec.gov/search/search.htm'
driver=webdriver.Chrome(path)

tickers=['AAL','AAN','AAOI','AAPL']
# starts the process
def get_CIK(ticker):
    driver.get(main)
    stock_code = WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.ID, "cik")))
    stock_code.click()
    stock_code.send_keys(ticker)
    
    
    driver.find_element_by_xpath("//input[@value='Find Companies']").click() # click on search buttom
    link = driver.find_element_by_xpath("/html[1]/body[1]/div[4]/div[1]/div[3]/span[1]/a[1]").get_attribute("href") # get link
    cik= link[link.index('CIK=')+4:link.index("owner")-1] # extract cik
    print cik
    
for i in tickers:
    get_CIK(i)

最佳答案

您偶尔会看到“预见弹出窗口”,它通常会随机显示。

我能想到 5 种通用方法:

  • 设置一个特定的 Cookie,该 Cookie 将禁用预见弹出窗口“假装”您已经将其关闭。究竟要设置哪个 cookie 目前还是一个悬而未决的问题。还有关于它的相关线程:Handle random ForeSee popup using Python and Selenium
  • 在与网站交互的过程中始终检查“弹出窗口”是否存在。弹出窗口不是 selenium 意义上的经典“警报”,而是只是一个“覆盖层”,它具有以下 HTML 表示形式:

    <div class="__acs " aria-labelledby="fsrHeading">
        <div class="acsModalBackdrop acsAbandonButton" data-isbackdrop="true">
            <div class="acsFocusFirst acsClassicInvite" tabindex="1"
                 id="acsMainInvite" role="dialog" aria-labelledby="fsrHeading">
                <div class="acsClassicInner" role="document">
                    <div class="acsLogoSpacer"><img
                        src="//gateway.foresee.com/sites/sec-gov/production/trigger/sitelogo.png"
                        class="acsSiteLogo" title="" alt=""> <img
                        src="https://static.foresee.com/logos/foresee/150_67.png"
                        class="acsNoDisplay" title="ForeSee" alt="ForeSee">
                        <div title="ForeSee" alt="ForeSee"
                            class="acsVendorLogoSVG"></div>
                            ... 
    

    例如,您可以检查是否存在“拒绝”按钮,如果存在则单击它:

    <a href="#" tabindex="2" class="acsInviteButton acsDeclineButton" title="" role="button"></a>
    
  • 您还可以“阻止”预见要加载的 JS 脚本,例如,使用浏览器 mobproxy 来阻止来自“foresee.com”的所有流量。或者,按照类似的轨迹 - 您可以使用广告拦截器启动 selenium,该广告拦截器将/应该阻止开箱即用的“预见”

  • 或者,您可以重写“foresee”全局对象的 showInvite() 函数:

    driver.execute_script("window.FSR.showInvite = function () {};")
    

    请注意,您每次导航到新页面后都需要调用此脚本。

  • 经过一些逆向工程,我发现“foresee”JS对象具有这个全局配置,其中包含许多有趣的信息,包括设备黑名单:

    device_blacklist: ["HTC_Rezound", "blackberry"]
    

    然后您可以 override the browser's user-agent并假装来自,比如说,Blackberry device :

    BLACKBERRY_UA = "Mozilla/5.0 (BlackBerry; U; BlackBerry 9900; en) AppleWebKit/534.11+ (KHTML, like Gecko) Version/7.1.0.346 Mobile Safari/534.11+"
    
    opts = Options()
    opts.add_argument("user-agent={0}".format(BLACKBERRY_UA))
    
    driver = webdriver.Chrome(chrome_options=opts)
    
<小时/>

第二个选项在技术上更具挑战性且更容易出错,并且会减慢速度,因为您会不断检查此弹出窗口是否存在。好吧,至少在你驳回它之前是这样。

第四个选项很有希望,但我还没有完全测试它。

最后一个选项,无论听起来多么疯狂,实际上对我来说很有效。

关于python - 无法让 XPath 单击 selenium 中的弹出窗口,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51978555/

相关文章:

python - Numpy 将输入数组作为 `out` 参数传递给 ufunc

java - Appium 的 implicitlyWait 不起作用

java - Selenium 测试 - 通过弹出窗口添加文本未保存

python - 使用 Python Selenium webdriver 登录雅虎电子邮件帐户

python - 给定两个列表,没有得到创建元组列表的正确输出

python - 如何使用 Python 检查我的服务器是否正常运行?

python - Django MySql,外键查询

java - 无法使用 Selenium 在 Chrome 浏览器的“权限”弹出窗口中单击 “Allow” 或 “Block”?

java - Selenium 程序抛出编译错误 org.openqa.selenium.internal.Killable cannot be resolved

selenium - 在制作 Maven 项目时出现 "could not calculate build plan"插件错误