Search code examples
javaseleniumselenium-webdriverwebdrivergeckodriver

How to Conceal WebDriver in Geckodriver from BotD in Java?


I followed this post on Stackoverflow to disable Firefox WebDriver detection.

Launch Geckodriver:

System.setProperty("webdriver.gecko.driver", geckdriverExecutableFilePath);



File firefoxProfileFile = new File(fullPathOfFirefoxInstallationFolder);



FirefoxProfile firefoxProfile = null;

        
 try {
    firefoxProfile = new FirefoxProfile(firefoxProfileFile);
     } catch (Exception e) {

    e.printStackTrace();
     }

I disabled WebDriver:

WebDriver Disabled

FirefoxOptions firefoxOptions = new FirefoxOptions();

firefoxOptions.setProfile(firefoxProfile);

// Disables WebRTC
firefoxProfile.setPreference("media.peerconnection.enabled", false);

I disabled Automation Extensions:

Automation Extension Disabled

// Disables Automation Extension
firefoxProfile.setPreference("useAutomationExtension", false);

I added Proxy:

    DesiredCapabilities dc = DesiredCapabilities.firefox();
    Proxy proxy = new Proxy();
    proxy.setHttpProxy(ipAddress + ":" + port);
    proxy.setFtpProxy(ipAddress + ":" + port);
    proxy.setSslProxy(ipAddress + ":" + port);

   dc.setCapability(CapabilityType.PROXY, proxy);




   firefoxOptions.merge(dc);

   driver = new FirefoxDriver(firefoxOptions);

Yet BotD still detects my browser as being controlled by automation tool.

BotD Detection

How can I solve this?


Solution

  • When using Selenium driven GeckoDriver initiated Browsing Context

    The webdriver-active flag is set to true when the user agent is under remote control. It is initially false.

    webdriver-active flag

    where, webdriver returns true if webdriver-active flag is set, false otherwise.

    As:

    navigator.webdriver Defines a standard way for co-operating user agents to inform the document that it is controlled by WebDriver, for example so that alternate code paths can be triggered during automation.

    Further @whimboo in his comments confirmed:

    This implementation have to be conformant to this requirement. As such we will not provide a way to circumvent that.


    Conclusion

    So, the bottom line is:

    Selenium identifies itself

    and there is no way to conceal the fact that the browser is WebDriver driven.


    Recommendations

    However some pundits have suggested some different approaches which can conceal the fact that the Mozilla Firefox browser is WebDriver controled through the usage of Firefox Profiles and Proxies as follows:

    compatible code

    from selenium.webdriver import Firefox
    from selenium import webdriver
    from selenium.webdriver.firefox.service import Service
    from selenium.webdriver.firefox.options import Options
    
    profile_path = r'C:\Users\Admin\AppData\Roaming\Mozilla\Firefox\Profiles\s8543x41.default-release'
    options=Options()
    options.set_preference('profile', profile_path)
    options.set_preference('network.proxy.type', 1)
    options.set_preference('network.proxy.socks', '127.0.0.1')
    options.set_preference('network.proxy.socks_port', 9050)
    options.set_preference('network.proxy.socks_remote_dns', False)
    service = Service('C:\\BrowserDrivers\\geckodriver.exe')
    driver = Firefox(service=service, options=options)
    driver.get("https://www.google.com")
    driver.quit()
    

    Potential Solution

    A potential solution would be to use the browser as follows:

    compatible code

    from selenium.webdriver import Firefox  
    from selenium import webdriver
    from selenium.webdriver.firefox.service import Service
    from selenium.webdriver.firefox.options import Options
    import os
    
    torexe = os.popen(r'C:\Users\username\Desktop\Tor Browser\Browser\TorBrowser\Tor\tor.exe')
    profile_path = r'C:\Users\username\Desktop\Tor Browser\Browser\TorBrowser\Data\Browser\profile.default'
    firefox_options=Options()
    firefox_options.set_preference('profile', profile_path)
    firefox_options.set_preference('network.proxy.type', 1)
    firefox_options.set_preference('network.proxy.socks', '127.0.0.1')
    firefox_options.set_preference('network.proxy.socks_port', 9050)
    firefox_options.set_preference("network.proxy.socks_remote_dns", False)
    firefox_options.binary_location = r'C:\Users\username\Desktop\Tor Browser\Browser\firefox.exe'
    service = Service('C:\\BrowserDrivers\\geckodriver.exe')
    driver = webdriver.Firefox(service=service, options=firefox_options)
    driver.get("https://www.tiktok.com/")
    

    References

    You can find a couple of relevant detailed discussions in