无头脚本在运行几次后崩溃

8

我有一个使用无头浏览器的脚本,我正在使用crontab -e运行。它前几次运行得很好,然后会崩溃,并显示以下Traceback:

Traceback (most recent call last):
  File "/home/clint-selenium-firefox.py", line 83, in <module>
    driver.get(url)
  File "/usr/local/lib/python2.7/dist-packages/selenium/webdriver/remote/webdriver.py", line 248, in get
    self.execute(Command.GET, {'url': url})
  File "/usr/local/lib/python2.7/dist-packages/selenium/webdriver/remote/webdriver.py", line 236, in execute
    self.error_handler.check_response(response)
  File "/usr/local/lib/python2.7/dist-packages/selenium/webdriver/remote/errorhandler.py", line 192, in check_response
    raise exception_class(message, screen, stacktrace)
selenium.common.exceptions.WebDriverException: Message: Failed to decode response from marionette

我的crontab行是:

*/10 * * * * export DISPLAY=:0 && python /home/clint-selenium-firefox.py >> /home/error.log 2>&1

我不想在这里过多地涉及Python脚本,因此我已经提取出我认为相关的部分。

from pyvirtualdisplay import Display

display = Display(visible=0, size=(800, 600))
display.start()
...
driver = webdriver.Firefox()
driver.get(url)
...
driver.quit()
...
display.stop()

非常感谢你的帮助。

编辑

版本信息:Firefox 49.0.2;Selenium: 3.0.1;geckodriver: geckodriver-v0.11.1-linux64.tar.gz

错误代码(在 driver.get(url) 处失败):

driver = webdriver.Firefox()
if DEBUG: print "Opened Firefox"

for u in urls:
    list_of_rows = []
    list_of_old_rows = []

    # get the old version of the site data
    mycsvfile = u[1]
    try:
        with open(mycsvfile, 'r') as csvfile:
            old_data = csv.reader(csvfile, delimiter=' ', quotechar='|')
            for o in old_data:
                list_of_old_rows.append(o)
    except: pass

    # get the new data
    url = u[0]
    if DEBUG: print url    

    driver.get(url)
    if DEBUG: print driver.title
    time.sleep(1)
    page_source = driver.page_source
    soup = bs4.BeautifulSoup(page_source,'html.parser')  

我已经阅读了很多关于这个的内容。我需要使用Marionette吗? - HenryM
你正在使用的 Firefox、Selenium 和 GeckoDriver 版本是什么? - Naveen Kumar R B
在每种情况下,我都会下载最新版本。 - HenryM
我明白了,但我需要版本名称以确认。此外,请分享包含clint-selenium-firefox.py中第83行的方法的Python代码。 - Naveen Kumar R B
@Naveen 我已经按照你的要求添加了信息。 - HenryM
显示剩余7条评论
1个回答

6

来自多个Firefox实例出现NS_ERROR_SOCKET_ADDRESS_IN_USE#99错误 这是因为没有向geckodriver传递--marionette-port选项,这意味着所有geckodriver实例都会启动firefox并传递相同的默认端口(2828)。第一个firefox实例绑定到该端口,未来的实例则无法绑定,所有geckodriver实例最终连接到第一个firefox实例,这会产生各种不可预测的行为。

接下来是:我认为一个合理的短期解决方案是做其他驱动程序正在做的事情,并要求Marionette绑定到由geckodriver生成的随机的空闲端口。目前,它将2828用作它生成的所有Firefox实例的默认值。 由于Marionette不幸地还没有一种带外方式与客户端(geckodriver)通信端口,因此这本质上是竞争的,但我们可以通过bug 1240830中的一个提议在未来改善情况。

这个更改是在哪里进行的

Selenium 3.0.0.b2
* Updated Marionette port argument to match other drivers.

我猜随机只能运行一段时间。提出问题。你可能需要修复selenium、firefox和geckodriver的版本问题。在这个问题被解决之前,你可以回退到使用Selenium 2.53.0和Firefox esr 38.8。由你决定。
更新:尝试
from selenium import webdriver
from selenium.webdriver.firefox.firefox_binary import FirefoxBinary

binary = FirefoxBinary('path/to/binary')
driver = webdriver.Firefox(firefox_binary=binary)

我正在尝试返回早期版本。安装Selenium 2.53.0很容易,但我正在努力获取firefox esr 38.8。我正在尝试“sudo apt-get install iceweasel”,但它只是选择并安装最新版本的firefox。您能否建议如何强制使用旧版本。 - HenryM
在Linux上,我打开了Google Chrome浏览器,并输入了https://download.mozilla.org/?product=firefox-38.8.0esr-SSL&os=linux&lang=ach。 - MikeJRamsey56
我已经在一个单独的目录中安装了Firefox,并使用driver = webdriver.Firefox(firefox_binary = path / to / binary)进行调用。当我运行我的脚本时,我会得到上面提到的OSError。 - HenryM
sudo chown -R $USER /path/to/binary请注意,这是一条Linux命令。它的作用是将二进制文件的所有权更改为当前用户。 - MikeJRamsey56
请将其更改为sudo chown 775 $USER /path/to/binary。 - MikeJRamsey56
显示剩余6条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接