 [ ← blog / drupal ](/) Oct 16, 2018  ·  \#drupal  ·  5 min read 

# Running Drupal's FunctionalJavascript tests on DDEV



This is part two of a series on running Drupal’s testing suites on DDEV. We [left off last time](https://glamanate.com/blog/running-drupals-phpunit-test-suites-ddev) with trying to execute a FunctionalJavscript test and having every test case skipped because no browser emulator was available. In this post, we will run through getting set up to execute Drupal’s FunctionalJavascript tests inside of your DDEV web container.

     ![](/sites/default/files/styles/large/public/ddev-functionaljs-skipped.png?itok=h-U1vHkz) 

 

Drupal 8.3 saw the ability to write tests that interacted with JavaScript when [PhantomJS was added to Drupal’s testing capabilities](https://www.drupal.org/node/2469713). If you are not familiar with PhantomJS it is a headless web browser that was built on QtWebKit. And then in early 2018, a headless version of Chrome became available, essentially pushing PhantomJS into deprecated status. With [Drupal 8.5 we now have the ability to execute WebDriver tests](https://www.drupal.org/node/2941464) that run on headless Chrome. Honestly, this is a great improvement. The WebDriver API allows for using any client which respects its API (ie: FireFox) and not one-off integrations as was required for PhantomJS.

With [JavascriptTestBase deprecated in favor of WebDriverTestBase](https://www.drupal.org/node/2945059), you only need a WebDriver client to run Drupal core’s FunctionalJavascript tests. You may need PhantomJS to run some contributed project tests (like [Drupal Commerce](https://www.drupal.org/project/commerce/issues/2998745).) With that said, next we will get Chromedriver up and running so we can run some tests!

> If you’re writing a JavaScript enabled test as of Drupal 8.5 and extending JavascriptTestBase you will be using the new WebDriver base class. Some core or contrib tests might extend LegacyJavascriptTestBase and still use PhantomJS. One reason: PhantomJS returned response status codes and WebDriver does not — so tests may have not been ported yet to support the new testing API.

To keep things simple, we are going to use a Chromedriver Docker image provided by DrupalCi — the one used when executing tests on Drupal.org. To do this, we need to [define a custom service for DDEV](https://ddev.readthedocs.io/en/latest/users/extend/custom-compose-files/). It is petty simple: we just need to add a file called **docker-compose.chromedriver.yml** to our project's **.ddev** directory.

```bash
version: '3.6'
services:
  chromedriver:
    container_name: ddev-${DDEV_SITENAME}-chromedriver
    image: drupalci/chromedriver:production
    labels:
    # These labels ensure this service is discoverable by ddev
      com.ddev.site-name: ${DDEV_SITENAME}
      com.ddev.approot: $DDEV_APPROOT
      com.ddev.app-url: $DDEV_URL
  # This links the Chromedriver service to the web service defined
  # in the main docker-compose.yml, allowing applications running
  # in the web service to access the driver at `chromedriver`.
  web:
    links:
      - chromedriver:$DDEV_HOSTNAME
```

This file goes right into the project’s **.ddev** directory, as shown.

     ![](/sites/default/files/styles/large/public/ddev-docker-compose-chromedriver.png?itok=tSRNfro9) 

 

Now, restart your project and bring the new service online. The Docker image will be pulled down and the container started, managed by DDEV.

     ![](/sites/default/files/styles/large/public/ddev-pull-chromedriver.png?itok=6uGBkhPX) 

 

Now that we have Chromedriver running, we need to configure **phpunit.xml** once more. We need to change the value of **SIMPLETEST\_BASE\_URL** and add an environment variable called **MINK\_DRIVER\_ARGS\_WEBDRIVER**. Previously we defined **SIMPLETEST\_BASE\_URL** as **<http://localhost>**. There is just one problem: Chrome is going to try and visit localhost and not receive a website! Luckily, via Docker’s network, it can reach the web container through the hostname **web**. So we will need to change that value. The second environment variable passes WebDriver parameters to our service so let it know how it should be executed.

```xml
<php>
  <ini name="error_reporting" value="32767"/>
  <ini name="memory_limit" value="-1"/>
  <!-- Changed to http://web for Chromedriver access -->
  <env name="SIMPLETEST_BASE_URL" value="http://web"/>
  <env name="SIMPLETEST_DB" value="mysql://db:db@db/db"/>
  <env name="BROWSERTEST_OUTPUT_DIRECTORY" value=""/>
  <!-- Parameters pass to Chromedriver. -->
  <env name="MINK_DRIVER_ARGS_WEBDRIVER" value='["chrome", {"browserName":"chrome","chromeOptions":{"args":["--disable-gpu","--headless", "--no-sandbox"]}}, "http://chromedriver:9515"]'/>
</php>
```

You can keep **SIMPLETEST\_BASE\_URL** as **<http://web>** for running your Functional tests, as well. Inside of the **web** container**, <http://web>** resolves as localhost.

> For me, Chromedriver kept crashing until I added the --no-sandbox flag. DrupalCi does not pass this, so I am not sure the difference. But, I kept it for those who may have the same problem.

Time to give it a run! Open a terminal and let’s run the Big Pipe module's FunctionalJavascript tests.

```bash
ddev ssh
../vendor/bin/phpunit -c core core/modules/big_pipe/tests/src/FunctionalJavascript
```

And you should see test passes!

     ![](/sites/default/files/styles/large/public/ddev-phpunit-test-pass.png?itok=xkZTi9lj) 

 

If the tests come back as skipped, communication with the Chromedriver had failed. If this happens, run this command and run the tests again. This will display log output from Chrome.

```bash
docker exec -it {YOUR_PROJECT_NAME}-ddev-chromedriver tail -f /tmp/chromedriver.log
```

## Nightwatch.js

All right! We have now run all of Drupal's PHPUnit test suites. In my next post we will explore Drupal's newest testing framework: Nightwatch.js.

 

  ![](/themes/custom/mglaman/images/headshot.webp)Thanks for reading

I write about Drupal, PHP, and the quiet infrastructure behind large sites — caching, config, and testing. New posts land every week or two.

 [Subscribe via RSS →](/rss.xml) [About me →](/about-me) 

 



 

  [← Older

Running Drupal's PHPUnit test suites on DDEV

 ](/blog/running-drupals-phpunit-test-suites-ddev) [Newer →

Running Drupal's Nightwatch test suite on DDEV

 ](/blog/running-drupals-nightwatch-test-suite-ddev)