使用 Selenium 在封闭的 Shadow DOM 中选择按钮

发布于 2025-01-12 04:32:24 字数 701 浏览 1 评论 0原文

我正在尝试使用 Selenium 解决谷歌验证码,使用 python

我正在使用 this 简单示例网站进行测试,但我很难理解如何选择影子根中的按钮。

该图像显示了我需要获取的按钮元素。 输入图片这里的描述

我知道我需要先获取外部 div 元素,然后搜索内部元素,但我没有这样做,因为我不是 100% 清楚如何导航到内部元素执行类似操作后的元素

driver.execute_script("return document.querySelector('div[class=\"button-holder help-button-holder\"]')

这个问题是关于类似(相同?)的问题,但是有没有可行的解决方案。

I am trying to solve a google captcha with Selenium, using python

I'm using this simple example site to test with, but I am having difficulties understanding how to select a button that is within a shadow root.

This image shows the button element I need to get.
enter image description here

I understand I need to get the outer div element first, then search for the inner element, but I'm failing to do so, as I am not 100% clear on how to navigate to the inner element after executing something like

driver.execute_script("return document.querySelector('div[class=\"button-holder help-button-holder\"]')

This question is on similar (same?) problem, but there is no working solution.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

楠木可依 2025-01-19 04:32:24

您的元素被放置在 shadow-root 中,并处于 close 状态。

当影子根的模式为“关闭”时,影子根的实现内部不可访问且不可更改,因此您无法访问 shadowRoot 属性。

由于 Selenium 实现了 CDP 协议 API,因此可以在页面加载时使用 open 状态覆盖具有 close 状态的 shadow-root 状态。

您只需要在页面加载之前重写 Element 类原型方法 attachShadow 并在新文档上评估脚本即可。

如何覆盖元素属性

如何通过 CDP 协议加载时执行脚本

代码示例:

url = "yourUrl"
driver.execute_cdp_cmd('Page.addScriptToEvaluateOnNewDocument', {'source': """
Element.prototype._attachShadow = Element.prototype.attachShadow;
Element.prototype.attachShadow = function () {
    return this._attachShadow( { mode: "open" } );
};
"""})
driver.get(url)
closed_shadow_host = driver.find_element(By.CSS_SELECTOR, 'div[class=\"button-holder help-button-holder\"]')
shadow_root = driver.execute_script('return arguments[0].shadowRoot', closed_shadow_host)

Your element is placed in shadow-root with closed state.

When the mode of a shadow root is "closed", the shadow root's implementation internals are inaccessible and unchangeable, so you can't access shadowRoot property.

Since Selenium implemented CDP protocol API, shadow-root with closed state can be overridden with open state on page load.

You just need to override Element class prototype method attachShadow and evaluate script on new document before page load.

How to override Element properties

How to executed script on load via CDP Protocol

Example of code:

url = "yourUrl"
driver.execute_cdp_cmd('Page.addScriptToEvaluateOnNewDocument', {'source': """
Element.prototype._attachShadow = Element.prototype.attachShadow;
Element.prototype.attachShadow = function () {
    return this._attachShadow( { mode: "open" } );
};
"""})
driver.get(url)
closed_shadow_host = driver.find_element(By.CSS_SELECTOR, 'div[class=\"button-holder help-button-holder\"]')
shadow_root = driver.execute_script('return arguments[0].shadowRoot', closed_shadow_host)
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文