Function Mocker new powers 01

Mocking interfaces with function-mocker.

Code to an interface

Be it a real interface or an abstract class type-hinting those in place of concrete classes is a good idea. Testing and mocking those dependencies is a possibility PHPUnit offers already. Given the client class below

class Client {
    /**
     * @var ObjectI
     */
    protected $objectInterface; 

    /**
     * @var AbstractObject
     */
    protected $abstractObject; 


    public function setInterfaceObject(ObjectI $object) {
        $this->objectInterface = $object;
    }

    public function setAbstractObject(AbstractObject $object) {
        $this->abstractObject = $object;
    }

    public function useObjectInterface(){
        $value = $this->objectInterface->method;

        return $value * 10;
    }

    public function useAbstractObject(){
        $value = $this->abstractObject->method();

        return $value + 10;
    }
}

and the two dependencies

interface ObjectI {
    public function method();
}

abstract class AbstractObject {
    abstract public function method();
    public function anotherMethod();
}

then a test could be set up like this

public function test_calls_method_on_interface(){
    $mockI = $this->geMock('ObjectI');
    $mockI->expects($this->once())
        ->method('method')
        ->willReturn(23);

    $sut = new Client();
    $sut->setInterfaceObject($mockI);

    $value = $sut->useObjectInterface()
    $this->assertEquals(230, $value);
}

public function test_calls_method_on_interface(){
    $mockAbstract = $this
        ->geMockBuilder('AbstractObject')
        ->disableOriginalConstructor()
        ->setMethods('method')
        ->getMockForAbstractObject();
    $mockAbstract->expects($this->once())
        ->method('method')
        ->willReturn(23);

    $sut = new Client();
    $sut->setAbstractObject($mockAbstract);

    $value = $sut->useAbstractObject()
    $this->assertEquals(33, $value);
}

Function Mocker alternative

The test code above can be now rewritten using function-mocker in a shorter way

public function test_calls_method_on_interface(){
    $mockI = FunctionMocker::replace('ObjectI::method', 23);

    $sut = new Client();
    $sut->setInterfaceObject($mockI);

    $value = $sut->useObjectInterface()

    $mockI->wasCalledOnce();
    $this->assertEquals(230, $value);
}

public function test_calls_method_on_interface(){
    $mockAbstract = FunctionMocker::replace('AbstractObject::method', 23);

    $sut = new Client();
    $sut->setAbstractObject($mockAbstract);

    $value = $sut->useAbstractObject()

    $mockAbstract->wasCalledOnce();
    $this->assertEquals(33, $value);
}

Which slims down the tests a bit.
As always the magic happens in PHPUnit for the most part and its mocking engine.

Next

Trait replacement.