2013-08-02 28 views
7

Tôi mới đến Mock và đang viết một bài kiểm tra đơn vị cho chức năng này:Django unittest và chế giễu các yêu cầu mô-đun

# utils.py 
import requests  

def some_function(user): 
    payload = {'Email': user.email} 
    url = 'http://api.example.com' 
    response = requests.get(url, params=payload)  

    if response.status_code == 200: 
     return response.json() 
    else: 
     return None 

Tôi đang sử dụng Michael Foord's Mock thư viện như là một phần của bài kiểm tra đơn vị của tôi và đang gặp khó khăn trong chế giễu response.json() để trả về một cấu trúc json. Đây là thử nghiệm đơn vị của tôi:

# tests.py 
from .utils import some_function 

class UtilsTestCase(unittest.TestCase): 
    def test_some_function(self): 
     with patch('utils.requests') as mock_requests: 
      mock_requests.get.return_value.status_code = 200 
      mock_requests.get.return_value.content = '{"UserId":"123456"}' 
      results = some_function(self.user) 
      self.assertEqual(results['UserId'], '123456') 

Tôi đã thử kết hợp nhiều cài đặt giả khác nhau sau khi đọc tài liệu không có may mắn. Nếu tôi in results trong thử nghiệm đơn vị của tôi nó luôn luôn hiển thị sau thay vì cấu trúc dữ liệu json Tôi muốn:

<MagicMock name=u'requests.get().json().__getitem__().__getitem__()' id='30315152'> 

Suy nghĩ về những gì tôi đang làm sai?

Trả lời

13

json phương thức thay vì content. (content không được sử dụng trong some_function)

Hãy thử mã sau đây.

import unittest 

from mock import Mock, patch 

import utils 

class UtilsTestCase(unittest.TestCase): 
    def test_some_function(self): 
     user = self.user = Mock() 
     user.email = '[email protected]' 
     with patch('utils.requests') as mock_requests: 
      mock_requests.get.return_value = mock_response = Mock() 
      mock_response.status_code = 200 
      mock_response.json.return_value = {"UserId":"123456"} 
      results = utils.some_function(self.user) 
      self.assertEqual(results['UserId'], '123456') 
+0

Rất cám ơn cho câu trả lời này. Nó bây giờ làm việc như tôi đã hy vọng. –

+0

Một thử nghiệm xác nhận khác tôi sẽ thêm vào thử nghiệm đơn vị của bạn sẽ là đảm bảo phương thức request.get được gọi với các tham số dự kiến. Một cái gì đó như, 'mock_get.assert_called_with ('http://api.example.com', payload = {'Email': self.user.email}'. Điều này đảm bảo rằng mã thư viện của bạn đang thực hiện cuộc gọi yêu cầu với các tham số dự kiến, điều đó cũng quan trọng như kiểm tra giá trị trả về của mã thư viện, là giá trị được mô phỏng. – adam

1

Một mẫu khác tôi thích sử dụng lại có thể sử dụng lại nhiều hơn để bắt đầu bản vá trong phương pháp setUp của đơn vị thử nghiệm của bạn. Nó cũng quan trọng để kiểm tra xem yêu cầu mô hình được gọi với các thông số mong đợi:

class UtilsTestCase(TestCase): 

    def setUp(self): 
     self.user = Mock(id=123, email='[email protected]m') 

     patcher = patch('utils.requests.get') 
     self.mock_response = Mock(status_code=200) 
     self.mock_response.raise_for_status.return_value = None 
     self.mock_response.json.return_value = {'UserId': self.user.id} 
     self.mock_request = patcher.start() 
     self.mock_request.return_value = self.mock_response 

    def tearDown(self): 
     self.mock_request.stop() 

    def test_request(self): 
     results = utils.some_function(self.user) 

     self.assertEqual(results['UserId'], 123) 

     self.mock_request.assert_called_once_with(
      'http://api.example.com' 
      payload={'Email': self.user.email}, 
     ) 

    def test_bad_request(self): 
     # override defaults and reassign 
     self.mock_response.status_code = 500 
     self.mock_request.return_value = self.mock_response 
     results = utils.some_function(self.user) 

     self.assertEqual(results, None) 

     self.mock_request.assert_called_once_with(
      'http://api.example.com' 
      payload={'Email': user.email}, 
     ) 
0

Một cách khác mà tôi tin là rõ ràng hơn và thẳng về phía trước:

import unittest 

from mock import Mock, patch 

import utils 

class UtilsTestCase(unittest.TestCase): 
    def test_some_function(self): 
     mock_response = Mock() 
     mock_response.status_code = 200 
     mock_response.json.return_value = {"UserId": "123456"} 
     with patch('utils.requests.get') as mock_requests: 
      results = utils.some_function(self.user) 
      self.assertEqual(results['UserId'], '123456') 
Các vấn đề liên quan