Global Variables and PHPUnit

In PHP, global variables work like this:

  • A global variable $foo = 'bar'; is stored as $GLOBALS['foo'] = 'bar';.
  • $GLOBALS is a so-called superglobal.
  • Superglobals are built-in variables that are always available in all scopes.
  • In the scope of a function or method, you may access the global variable $foo by either directly accessing $GLOBALS['foo'] or by using global $foo; to create a local variable with a reference to the global variable.

It is hard to test code that uses singletons. The same is true for code that uses global variables.

Typically, the code you want to test is coupled strongly with a global variable and you cannot control its creation. An additional problem is the fact that one test's change to a global variable might break another test.

By default, PHPUnit runs your tests in a way where even changes to global and super-global variables (such as $GLOBALS) do not affect other tests.

The implementation of the backup and restore operations for the global and super-global variables uses serialize() and unserialize(). Objects of some classes that are provided by PHP itself, such as PDO, cannot be serialized and the backup operation will break when such an object is stored in the $GLOBALS array, for instance.

The backup and restore operations for the global and super-global variables can be disabled like this:

class MyTest extends PHPUnit_Framework_TestCase
    protected $backupGlobals = FALSE;
    // ...

Please note that setting the $backupGlobals attribute inside the setUp() method, for instance, has no effect.

Starting with PHPUnit 3.3, the configuration of the $GLOBALS isolation is also supported on the TestSuite level. See ticket #497 for details.

Starting with PHPUnit 4.0, there will be support for running each test in a separate PHP process. Among other benefits, this will allow for testing singletons in an isolated environment.