2016-12-06 115 views
0

這裏是一個小類(在myapp/getters.py):如何模擬Django模型管理器的方法?

from django.contrib.auth.models import User 

class UserGetter: 
    def get_user(self): 
     return User.objects.get(username='username') 

我想調用模擬出到User.objects.get,返回MagicMock,並測試該方法返回我注射。在myapp/tests/tests_getters.py

from unittest import TestCase 
from django.contrib.auth.models import User, UserManager 
from mock import patch, create_autospec 
from myapp.getters import UserGetter 

class MockTestCase(TestCase): 
    @patch('myapp.getters.User', autospec=True) 
    def test(self, user_class): 
     user = create_autospec(User) 
     objects = create_autospec(UserManager) 
     objects.get.return_value = user 
     user_class.objects.return_value = objects 
     self.assertEquals(user, UserGetter().get_user()) 

但是當我運行這個測試(與python manage.py test myapp.tests.tests_getters)我得到

AssertionError: 
    <MagicMock name='User.objects().get()' spec='User' id='4354507472'> != 
    <MagicMock name='User.objects.get()' id='4360679248'> 

爲什麼我不回來我注射模擬?我該如何正確編寫這個測試?

回答

1

我覺得這是你的問題:

user_class.objects.return_value = objects 

您指示模擬有功能的「對象」,返回右側的對象。
但是你的代碼永遠不會調用任何對象()函數。它訪問User.objects屬性,用戶在這裏是一個模擬,所以用戶返回一個新的模擬屬性訪問。

+0

就是這樣。解決方法是將'user_class.objects.return_value = objects'更改爲'user_class.objects = objects'。如果我不修補'User'並將其分配給'User.objects',它也可以工作,但是我懷疑這會污染其他測試。 –