Start PHP’s Built-in Web Server From PHPUnit

Sometimes in PHP we want to write integration tests and sometimes those integration tests will need a web server. Available since PHP 5.4, the built-in web server can be used to run those tests.

The basics of starting the server as laid out in the PHP documentation are:

php -S <addr>:<port> -t <docroot>

This can be run with exec but it is simpler to use the Symfony Process component to manage the server from within the test. The main things to do are run the process asynchronously, make sure the port is free and wait for a couple of microseconds to allow the server to start.

The next requirement is some way to call the web server. This can be done with curl but it’s a little neater to use Guzzle . When using Guzzle the http errors need to be suppressed using `[‘http_errors’ => false]`. If running the code behind a proxy bypass it by setting the proxy option to an empty string.

Putting it all together gives the following Silex app:

and then the following integration test:

Which can be run with:

bin/phpunit IntegrationTest.php --bootstrap=vendor/autoload.php

The code leverages the setUpBeforeClass and tearDownAfterClass methods to start one web server per test class and stop the server when all the test cases in that class have run.

All the code and dependencies can be found on GitHub.