无法在Selenium+Firefox中使用私有Socks5代理(Python)

0 投票
1 回答
1406 浏览
提问于 2025-06-18 04:06

背景:我正在使用Python、selenium和Geckodriver来自动化Firefox浏览器,但在使用私人代理时遇到了问题。我无法配置我的socks5代理的用户名和密码。因此,Firefox虽然能打开,但连接却不成功。

我想做的简单任务是:

  1. 我想用selenium(自动化的Firefox)和一个代理(带密码的SOCKS5代理)一起使用
  2. 在一个网站上检查我的IP,看看代理是否正常工作

到目前为止,我注意到的情况是:

  • 我使用的是Firefox版本76.0.1,Geckodriver和Python3
  • 当我选择代理时,应该弹出的用户名/密码框没有出现,这可能是Firefox版本的问题,可以通过在about:settings中覆盖一些设置来解决。一个解决方案是让这个弹窗正常工作,并编写一些用户密码认证的代码 - 见下面的登录函数。老实说,这个方法不太稳定,我更希望找到一个不需要这个弹窗的解决方案。
  • 管理socks5代理的唯一稳定方法(不管弹窗认证)是使用一个叫FoxyProxy的插件。
  • 我无法更改这个(FoxyProxy插件),在Python中我能更改的只是可以通过Firefox的URL(about:config)访问的设置。
  • 简单的不需要密码的代理没有问题,但带有用户名和密码的SOCKS5代理就成了问题。
  • 另外:我在想是否可以覆盖FoxyProxy插件,添加一些可以在Firefox(about:config)中访问的选项(老实说,我不是Firefox插件开发者,所以也许这是可能的!?)

所以当前的代码是,把HOST/USERNAME/PORT/PASSWORD替换成socks5代理的数据:

    from selenium import webdriver
    from base64 import b64encode
    from selenium import webdriver

    def login(browser):
        alert=browser.switch_to_alert()
        alert.send_keys("username"+webdriver.common.keys.Keys.TAB+"password")
        alert.accept()

    proxy = {'host': HOST, 'port': PORT, 'usr': USERNAME, 'pwd': PASSWORD}
    fp = webdriver.FirefoxProfile()
    fp.set_preference('network.proxy.type', 1)
    fp.set_preference('network.proxy.http', proxy['host'])
    fp.set_preference('network.proxy.http_port', int(proxy['port']))
    fp.set_preference('network.proxy.no_proxies_on', 'localhost, 127.0.0.1')
    fp.set_preference("network.proxy.socks_version", 5)
    credentials = '{usr}:{pwd}'.format(**proxy)
    fp.set_preference("network.proxy.type", 1)
    fp.set_preference("network.proxy.socks_version", 5)
    fp.set_preference("network.proxy.socks", HOST)
    fp.set_preference("network.proxy.socks_port", PORT)
    fp.set_preference("network.http.use-cache", False)
    driver = webdriver.Firefox(fp)
    # normally a proxy login popup should appear and we should call the login function here!!
    driver.get('https://wtfismyip.com')

这个方法不行,有什么想法吗?

相关问题:

  • 暂无相关问题
暂无标签

1 个回答

1

要把foxyproxy添加为一个扩展:

driver = webdriver.Firefox(executable_path="path to geckodriver", options=options)
driver.install_addon("path to .xpi file of the extension", temporary=None)
driver.switch_to.window(driver.window_handles[1])`

这时会打开一个网页,你可以在这里设置你的代理。首先,我定义一个函数,让我可以输入所有代理的信息(主机、端口、用户名、密码)。

def set_proxy(address, port, usernamex, passwordx):
    proxy_address_xpath = '//*[@id="proxyAddress"]'
    proxy_address_box = driver.find_element_by_xpath(proxy_address_xpath)
    proxy_address_box.send_keys(address)
    proxy_port_xpath = '//*[@id="proxyPort"]'
    proxy_port_box = driver.find_element_by_xpath(proxy_port_xpath)
    proxy_port_box.send_keys(port)
    proxy_username_xpath = '//*[@id="proxyUsername"]'
    proxy_username_box = driver.find_element_by_xpath(proxy_username_xpath)
    proxy_username_box.send_keys(usernamex)
    proxy_pass_xpath = '//*[@id="proxyPassword"]'
    proxy_pass_box = driver.find_element_by_xpath(proxy_pass_xpath)
    proxy_pass_box.send_keys(passwordx)
    save_xpath = '/html/body/div[2]/div[2]/button[4]'
    save_box = driver.find_element_by_xpath(save_xpath)
    save_box.click()

接着,使用下面的代码,我设置代理并选择它,这样当我浏览网页时就会使用这个代理。

# go to the page where you can add the proxies
xpath_back ="/html/body/div[2]/div[2]/button"
back_box = driver.find_element_by_xpath(xpath_back)
back_box.click()
    
# add proxy
add_xpath = "/html/body/div[4]/div/nav/a[1]"
add_box = WebDriverWait(driver, timeout=10).until(lambda x: x.find_element_by_xpath(add_xpath))
add_box.click()
    
# select proxy type (in my case socks5)
type_xpath = '//*[@id="proxyType"]'
type_box = driver.find_element_by_xpath(type_xpath)
type_box.click()
    
socks5_xpath = '/html/body/div[2]/div[1]/div[2]/div[1]/select/option[3]'
socks5_box = driver.find_element_by_xpath(socks5_xpath)
socks5_box.click()
    
# write the proxy stuff
set_proxy('socks5', 'host', 'port', 'pass')
    
# select the proxy you just saved (in this case it selects the first one)
change_xpath = '//*[@id="mode"]'
change_box = WebDriverWait(driver, timeout=10).until(lambda x: x.find_element_by_xpath(change_xpath))
change_box.click()
    
select_xpath = '/html/body/div[4]/div/div/div[1]/select/option[2]'
select_box = driver.find_element_by_xpath(select_xpath)
select_box.click()

然后,记得在新窗口中进行浏览,或者使用下面的代码切换到第一个窗口:

driver.switch_to.window(driver.window_handles[0])

这样你就可以保留foxyproxy的窗口,方便你更改代理。

如果你想用其他方法,可以查看 如何使用Python + Selenium设置代理认证(用户名和密码)

撰写回答