PHPUnit Mock an object's properties

30,802

Solution 1

To add properties to a mocked object, you just set them as you'd normally do with an object:

$mock = $this->getMockBuilder('MyClass')
             ->disableOriginalConstructor()
             ->getMock();

$mock->property = 'some_value';

$mock->property will now return 'some_value'

Thanks to akond

P.s. for my project, this doesn't work with some classes, and when I try to call $mock->property it just returns NULL

Solution 2

If you have classes with magic methods you can use:

$mock->method('__get')->with('property')->willReturn('value');
Share:
30,802
Riccardo Cedrola
Author by

Riccardo Cedrola

Updated on June 19, 2021

Comments

  • Riccardo Cedrola
    Riccardo Cedrola almost 3 years

    I'm looking for a way to mock an object and populate its properties. Here's an example of a method who uses a property of another object:

    class MyClass {
    
        private $_object;
    
        public function methodUnderTest($object) {
            $this->_object = $object;
            return $this->_object->property
        }
    }
    

    To Unit Test this method I should create a mock of $object with the getMockBuilder() method from PHPUnit. But I can't find a way to mock the properties of the $object, just the methods.

  • vivanov
    vivanov over 6 years
    Make sure you don't use magic methods inside the original class.
  • Riccardo Cedrola
    Riccardo Cedrola over 5 years
    If your class uses magic methods you actually have to mock the __get() method and make it return the desired output. This was the reasons behind the failure in some of my classes
  • gArn
    gArn over 5 years
    disableOriginalConstructor() needs parenthese to indicate it is a method, not a property. Otherwise you will get an error
  • emmanuel honore
    emmanuel honore over 4 years
    @RiccardoCedrola how would you create such mocked __get() construct?
  • Riccardo Cedrola
    Riccardo Cedrola over 4 years
    @powtac as you would normally do with any other method, you just mock the __get() and make it return the desired value. The problem is that this approach isn't really dynamic and it's hard to mock if is used multiple times inside the method you are testing. I might be wrong but I think there's a way where you mock a method by saying "when you receive A return B, when you receive X return Y"
  • Collin Krawll
    Collin Krawll over 4 years
    If your class uses magic methods, you can mock __get for the specific property like this: $mock->method('__get')->with('propname')->willReturn('fakeva‌​lue');
  • Olle Härstedt
    Olle Härstedt almost 4 years
    @CollinKrawll This seems not to work when you need to mock __get for two or more different arguments?
  • AlbinoDrought
    AlbinoDrought almost 4 years
    @OlleHärstedt Try PHPUnit's return value map: stackoverflow.com/a/30482721/3649573