由Selenium启动的Firefox忽略了pyvirtualdisplay创建的显示

Lou*_*uis 2 python firefox selenium pyvirtualdisplay

pyvirtualdisplay在创建WebDriver实例之前启动了一个显示.如果我使用Chrome,它可以毫无问题地运行:Chrome会在pyvirtualdisplay创建的Xephyr实例中显示.但是,当我使用Firefox时,会出现Xephyr实例,但Firefox会出现在它之外.

以下是完全重现问题的代码:

from selenium import webdriver
from selenium.webdriver.firefox.webdriver import FirefoxBinary
import pyvirtualdisplay

binary = FirefoxBinary()

with pyvirtualdisplay.Display(visible=True):
    if True:  # Set to False to use Chrome...
        driver = webdriver.Firefox(None, binary)
    else:
        driver = webdriver.Chrome()

    driver.get("http://www.google.com")
    driver.quit()
Run Code Online (Sandbox Code Playgroud)

上面的代码是一个更复杂的代码的最小版本(这解释了看似无用的FirefoxBinary()).

Lou*_*uis 8

FirefoxBinary在上下文管理的上下文中移动对象的创建pyvirtualdisplay.Display:

from selenium import webdriver
from selenium.webdriver.firefox.webdriver import FirefoxBinary
import pyvirtualdisplay

with pyvirtualdisplay.Display(visible=True):
    if True:  # Set to False to use Chrome...
        binary = FirefoxBinary()
        driver = webdriver.Firefox(None, binary)
    else:
        driver = webdriver.Chrome()

    driver.get("http://www.google.com")
    driver.quit()
Run Code Online (Sandbox Code Playgroud)

说明

问题是幕后发生的事情.名为的环境变量DISPLAY决定了Firefox和Chrome的连接位置.它没有按照您期望的方式设置.

以下是您的代码:

  1. 您创建一个实例FirefoxBinary.如果您阅读了源代码,您将看到当创建此类的对象时,它会复制os.environ(环境).

  2. 您创建一个显示pyvirtualdisplay.Display并将其用作上下文管理器.当你进入的背景下,显示器会改变os.environ,这样只要上下文中的效果,DISPLAY环境变量被设置成X客户端将连接到新的显示,而不是什么DISPLAY之前的背景下生效.

  3. 你创建了你的驱动程序 当您使用Chrome时,一切都很好,因为Chrome会DISPLAY从修改后的环境中获取变量.但是,当您使用Firefox时,它将使用第一步中复制DISPLAY环境中的环境.这个环境包括一个值DISPLAY之前在上一步骤中所描述的变化,所以它不会连接到您创建的新的显示.