MiniMockのTraceTracker使い方メモ

MockとかTraceTrackerの使い方ってちょっとめんどくさいと思うので、小さいサンプルを作ってメモしておこうと思いました。
適当なサンプルですが。


こんなモジュールがあるとします

some_utils.py

from datetime import datetime

valid_users = ['yuhei']


def now():
    return datetime.now()


def validate_name(name):
    return name in valid_users


def ask_time(name):
    if validate_name(name):
        return "Hello, %s. It is %s o'clock" % (name, now().strftime("%H"))


ask_timeのテスト

some_utils_test.py

from unittest import TestCase
from minimock import Mock, TraceTracker, restore
from datetime import datetime
import some_utils


class SomeUtilsTest(TestCase):
    def setUp(self):
        self.tracker = TraceTracker()
        self.dummy_now = datetime(2012, 12, 30, 15, 0, 0)
        some_utils.validate_name = Mock("some_utils.validate_name",
                                        returns=True,
                                        tracker=self.tracker)
        some_utils.now = Mock("some_utils.now",
                              returns=self.dummy_now,
                              tracker=self.tracker)

    def tearDown(self):
        restore()

    def test_ask_time(self):
        res = some_utils.ask_time('yuhei')
        self.assertEqual(res, "Hello, yuhei. It is 15 o'clock")

        expected = """Called some_utils.validate_name('yuhei')
Called some_utils.now()
"""
        #print self.tracker.dump()
        #print self.tracker.diff(expected)

        self.assertTrue(self.tracker.check(expected))


Mockを作るときにtrackerを仕込んでおけば、呼ばれたか、呼ばれてないか、呼ばれたなら引数は何だったのか?とかをtracker.checkでテストできます。

期待値をさらっと書けない場合は、tracker.dumpで、何が呼ばれたかを確認するといいと思います。

あってるはずなのにtracker.checkがFalseになる、なんて場合はtracker.diffで差分がわかります。