Testing with mock in Python 2015-02-23

Mocking is pretty awesome in python, especially when using the Mock library. It simplifies making stubs when testing, covers partial mocking, setting custom return values, how they were called, etc.

However there are a few pitfalls when initially working with Mock. Some of these things are pretty obvious, but this is a quick reference for a few gotchas I found while mocking a few projects.

side_effect vs return_value:

You'd only use side_effect if you want to test something that happens in a function instead of a return value. For example if you want to test exceptions that are raised in a method, use side_effect:

dork_mock = mock.Mock()
dork_mock.some_method.side_effect = ZeroDivisionError
dork_mock.some_method()

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "build/bdist.linux-x86_64/egg/mock.py", line 955, in __call__
  File "build/bdist.linux-x86_64/egg/mock.py", line 1010, in _mock_call
ZeroDivisionError
When to use Mock vs. MagicMock

Basically with MagicMock you can mock magic methods. That's pretty much the only difference, otherwise you should use Mock. as the docs say, one tiny thing to remember is that MagickMock returns set default values for some preconfigured methods:

m = MagicMock()
int(m) # 1
Patch:

Used as a context manager, it makes a specific context when your mocked modules live. You'll need to use mock.patch() when you want to mock modules in the classes you test. e.g.:

    with mock.patch('module.to.test.first_module') as first_mock:
        with mock.patch('module.to.test.second_module') as second_mock:

If you are doing more than one, you can write is like this so your identations don't go crazy:

with mock.patch('module.to.test.first_module') as first_mock,\
    mock.patch('module.to.test.second_module') as second_mock:

If you are mocking methods on modules, you can put them in the return value to save you some lines + style:

    with mock.patch('module.to.test.first_method', return_value='flickity flam'):

I've seen mainly the above in our test cases, but you can use patch as a decorator too, and mock the class as you go:

from mock import patch

@patch('class_to_mock.the_method')
def test_the_method(self, the_method)
    the_method.return_value = 'awesome'

PHP III (PHP's Infernal Internal Index) 2015-02-04

Recently I was debugging some confounded PHP code, and came across an error when trying to get something back from an array:

$services = [array('service'=>'Car Wash'),
             array('service'=>'Dork Library'),
             array('service'=>'Pet bnb')];

foreach($services as $service_index => $service){
    print_r($service);
    // Remove any Car wash service
    if($service['service'] == 'Car Wash'){
        unset($services[$service_index]);
    }
}

print_r($services[0]); // No output?!!?!?

Why doesn't $services[0] return anything?

As someone who doesn't use php much, this was confusing. I assumed that if you destory the variable here, then this means the next variable in line would of course be returned. But no, php has something much more devious, an internal array. Going through the details of this can get to O(C language) intensity. Basically the resolution to this gotacha is using:

reset($services);   // Fixes the index on this array
current($services); // Calls the item at the currently internal index,
                    // defaults to the first index

But Not Simpler 2015-01-19

Everything Should Be Made as Simple as Possible, But Not Simpler

As both a developer and support engineer this point frustrates me to no end, simply because people break this principle a lot. It comes up all the time when you work in software. KISS. Everyone agrees that ideally things best be clear, concise, understandable, scalable, ... Simple.

Defining simplicity itself is hard. Watch this Ted Talk because it's awesome and way more entertaining than a dictionary.

What is simplicty when it comes to software?

Everything Should Be Made as Simple as Possible

However, the devil is in the details, so when you start throwing in tons of design patterns and hunky frameworks and all that stuff then you suffer. Because you have to take care of all of these things and it gets complicated.

But it has to work the other way around too:

but Not Simpler

Because, as Mr. Whitesides wearing a black suit says, if things are too simple then the function of it is gone. It doesn't work anymore. We shouldn't forget who we're working for. The design should be independent from the implementation.