I'm working with automated tests and I'm trying to set up selenium grid for running tests in multiple environments.

I've successfully ran tests with chrome driver in Mac OS X 10.11 and Windows10.

Right now when I try to run a test feature, in a page with a video element, and the following message prompts on firefox (geckodriver):

Firefox is installing components needed to play audio or video, please try again later and the video does not start.

I'm running selenium standalone both on the Hub(Mac OS X) and Node(Windows 10) of the selenium grid.

I've tried to create a profile and import it on the node config (windowsNodeConfig.json):

{
"capabilities": [
    (...)
    {
        "browserName": "firefox",
        "maxInstances": 5,
        "platform": "WINDOWS",
        "marionette": true,
        "acceptInsecureCerts": true,
        "webdriver.gecko.driver": "geckodriver.exe",
        "firefox_profile": "firefoxProfile"
    }
    (...)
],
"nodeTimeout": 180000,
"browserTimeout": 180,
"timeout": 180,
"newSessionWaitTimeout": 180,
"cleanUpCycle": 5000,
"firefoxProfileTemplate": "firefoxProfile"
}

Versions: Selenium standalone : 3.4.0
Geckodriver : 0.16.1
Firefox (Windows) : 53.0.3

I'm running the node as follows:

$ java -jar selenium-server-standalone-3.4.0.jar -role node -nodeConfig windowsNodeConfig.json -hub http://<IP_ADDRESS>:4444

Running the Hub as follows:

$ java -jar selenium-hub/selenium-server-standalone-3.4.0.jar -role hub

The firefox profile I've created has the Widevine Content Decryption Module addon installed. However on the node logs I can see the following line:

JavaScript error: resource://gre/modules/AddonManager.jsm, line 2570: NS_ERROR_NOT_INITIALIZED: AddonManager is not initialized

The same test feature runs in chrome.

I've created the firefox profile as described in: https://support.mozilla.org/en-US/kb/profile-manager-create-and-remove-firefox-profiles#w_creating-a-profile

Am I missing any config?


The approaches have changed since the question was asked, nowadays these three work to me:

  1. Just modify the autogenerated temporary FF profile preferences to let it download the plugins and enable the playback:

    import { Builder } from 'selenium-webdriver';
    import firefox from 'selenium-webdriver/firefox';
    
    const driver = new Builder()
      .withCapabilities({
        browserName: 'firefox',
        ...,
      })
      .setFirefoxOptions(
        new firefox.Options()
          .setPreference('media.eme.enabled', true)
          .setPreference('media.gmp-manager.updateEnabled', true),
      )
      .build();
    

    This downloads the plugins every time, but is still fast. There is no need to duplicate the profile before every testing to prevent cache/cookies/storage... carry-over and there is no need for transferring the profile over the network if you test remotely.

    If this fails to set the FF preferences from time to time (e.g. on BrowserStack), you can try the same via a lower level approach:

    import { Builder } from 'selenium-webdriver';
    
    const builder = new Builder()
      .withCapabilities({
        browserName: 'firefox',
        ...,
        'moz:firefoxOptions': {
          prefs: {
            'media.eme.enabled': true,
            'media.gmp-manager.updateEnabled': true,
          },
        },
      })
      .build();
    
  2. Create your custom profile, open it, install OpenH264 Video Codec and Widevine Content Decryption Module plugins (go to a video page and FF will do it), close it, delete unnecessary files (everything except gmp-gmpopenh264, gmp-widevinecdm, prefs.js and times.json seems to be OK to be deleted) and setup your scripts to duplicate the profile before every Selenium run (to prevent the carry-overs). The profile can be used via:

    import { Builder } from 'selenium-webdriver';
    
    const driver = new Builder()
      .withCapabilities({
        browserName: 'firefox',
        ...,
        'moz:firefoxOptions': { args: ['-profile', './path/to/firefoxProfile'] }
      })
      .build();
    

    This way (args: ['-profile') FF is told to load the profile from the file system, there are some implications. This does not work to me on BrowserStack (Can't provide both a --profile argument and a profile).

  3. Create the profile the same way as in 2. and load it via:

    import { Builder } from 'selenium-webdriver';
    import firefox from 'selenium-webdriver/firefox';
    
    const driver = new Builder()
      .withCapabilities({
        browserName: 'firefox',
        ...,
      })
      .setFirefoxOptions(
        new firefox.Options()
          .setProfile('./path/to/firefoxProfile'),
      )
      .build();
    

    This way the profile gets compressed and encoded, so FF gets it as a string.

      1. ... FF profiles can be created programmatically, so there are a few more options how to avoid the manual creation in 2. I have not tried these.