Class Posing support for Mock Objects #15

Closed
sebastianbergmann opened this Issue May 25, 2010 · 0 comments

Projects

None yet

1 participant

@sebastianbergmann

A mock object can be used anywhere in the program where the program expects an object of the mocked class. However, this only works as long as the object can be passed into the context where the original object is used.

Consider the following example:

<?php
class SomeClass
{
    public function doSomething()
    {
        $object = new SomeOtherClass;
        // ...
    }
}
?>

With the code above, it is impossible to run a unit test for the SomeClass::doSomething() method without also creating an object of SomeOtherClass. As the method creates the object of SomeOtherClass itself, we cannot inject a mock object in its stead.

In a perfect world, code such as the above could be refactored using Dependency Injection:

<?php
class SomeClass
{
    protected $object;

    public function __construct(SomeOtherClass $object)
    {
        $this->object = $object;
    }

    public function doSomething()
    {
        // ...
    }
}
?>

Unfortunately, this is not always possible (not because of technical reasons, though).

This is where the set_new_overload() function of the test-helpers extension to the PHP interpreter comes into play. It can be used to register a callback that is automatically invoked when the new operator is executed:

<?php
class Foo {}
class Bar {}

function callback($className) {
    if ($className == 'Foo') {
        $className = 'Bar';
    }

    return $className;
}

var_dump(get_class(new Foo));

set_new_overload('callback');
var_dump(get_class(new Foo));
?>

string(3) "Foo"
string(3) "Bar"

This issue is about wrapping set_new_overload() in the PHPUnit Mock Object API.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment