Headstrong Internet Services
  • Home
  • About
  • Blog
  • Contact
  • Home
  • About
  • Blog
  • Contact

Document your app with PHPUnit Testdox output

3 November 2022

When you run your application’s test suite (you do have a test suite, right?) with PHPUnit, you will probably be familiar with the following output style:

PHPUnit 9.5.26 by Sebastian Bergmann and contributors.

Testing
..........................................R.................R.... 65 / 90 ( 72%)
.........................                                         90 / 90 (100%)

Time: 00:05.650, Memory: 155.00 MB

The main advantage of this output format is that it is concise, especially when you have a lot of tests. It quickly gives you an overview of tests that failed, have errors, or are considered risky.

However, the downside is that it’s not immediately clear what each test is actually testing. Each test is simply represented by a . character and that is all.

There is an alternative that many people do not seem to know about. PHPUnit has an option to change the output format to one that is much more descriptive, and that relies on the information already in your tests to create these descriptions.

Lets say you have a test class such as the following:

<?php
declare(strict_types=1);

use PHPUnitFrameworkTestCase;

final class CustomerSubscriptionsTest extends TestCase
{
    public function test_customer_can_be_subscribed_to_the_mailing_list(): void
    {
        // test code
    }

    public function test_customer_can_be_unsubscribed_from_the_mailing_list(): void
    {
        // test code
    }

    public function test_customer_cannot_be_subscribed_more_than_once(): void
    {
        // test code
    }

    public function test_customer_cannot_unsubscribe_if_not_already_subscribed(): void
    {
        // test code
    }
}

If you add the --testdox option to the PHPUnit command, you will get an alternative output format which looks like this:

PHPUnit 9.5.26 by Sebastian Bergmann and contributors.

Testing /var/www/app/tests

Customer Subscriptions
 ✔ Customer can be subscribed to the mailing list
 ✔ Customer can be unsubscribed from the mailing list
 ✔ Customer cannot be subscribed more than once
 ✔ Customer cannot unsubscribe if not already subscribed

The test descriptions are taken from the method names inside the test class. If you name your methods carefully, using natural language, you are creating documentation right there and then, without any further effort.

Overriding the testdox description

If you would like the name your method something slightly different to the outputted description, you can override it with the @testdox annotation:

/**
 * @testdox Customer can be subscribed OK
 */
public function test_customer_can_be_subscribed_to_the_mailing_list(): void
{
    // test code
}

Using testdox with data providers

If you use data provider methods to run your test against multiple data sets, you can get the values from the data provider into the testdox description as well.

/**
 * @dataProvider additionProvider
 * @testdox Adding $a to $b results in $expected
 */
public function test_can_add_a_to_b_successfully($a, $b, $expected)
{
    // test code
}

Additionally, if you use named sets in your data provider, you can access the set name in the testdox annotation using $_dataName as follows:

/**
 * @dataProvider additionProvider
 * @testdox Adding $a to $b results in $expected for $_dataName
 */
public function testAdd($a, $b, $expected)
{
    // test code
}

public function additionProvider()
{
    return [
        'data set 1' => [0, 0, 0],
        'data set 2' => [0, 1, 1],
        'data set 3' => [1, 0, 1],
        'data set 4' => [1, 1, 3]
    ];
}

This would result in the output for the first data set of Adding 0 to 0 results in 0 for data set 1

Conclusion

Once you start playing around with testdox output, you will probably realise how slack you’ve been when naming your test methods. It gets addictive, and you’ll find yourself tweaking things until you get the perfect desired output!

However, this time is well spent, as all one needs to do to get a summary of the behaviour of a part of your application is to run the test suite with the --testdox option, and the tests themselves will describe the desired behaviour.

Filed under: phpunit, testing, documentation, php

Recent posts

  • Improving cohesion in Symfony - storing Twig templates with the code
  • Caring For Your Composer.json
  • Introducing the Gitlab Issues plugin for Obsidian
  • How to eliminate boilerplate code with PHP 8.1
  • Code Quality Tools and CI For Solo Developers

Headstrong Internet Services Ltd

Unit 9, Riverside, Waters Meeting Road,
Bolton, BL1 8TU, United Kingdom
Company No. 06500823   VAT No. GB470255209

  • Home
  • About
  • Blog
  • Contact

© 2026 Headstrong Internet Services Ltd. All rights reserved.

  • Terms & Conditions
  • Privacy Policy
  • Cookie Policy