我对python和mocking很陌生。所以我试图通过阅读文档来找到解决问题的方法:
https://docs.python.org/3/library/unittest.mock.html#magic-methods,以下文章:http://alexmarandon.com/articles/python_mock_gotchas/
还有很多堆积如山的问题。但我还没找到解决办法。
我尝试模拟两个函数,它们正在创建数据库连接,并将数据放入pandas数据框中。它们用于post函数(覆盖django post函数):
def post(self, request, *args, **kwargs):
db_connection = du_db.get_connection(dbtype='mssql', username=crd.MS_SQL_USER, password=crd.MS_SQL_PWD)
df = du_db.fetch_dataframe(sql, connection=db_connection)
在测试环境中,
get_connection
不应返回任何内容,fetch_dataframe
应返回以前定义的pandas数据帧。我的测试课是这样的:
class IndexViewTest(TestCase):
@mock.patch('du_db.db.get_connection')
@mock.patch('du_db.db.fetch_dataframe')
def setUp(self, mock_get_connection, mock_fetch_dataframe):
self.c = Client()
mock_get_connection = mock_get_connection()
mock_fetch_dataframe = mock_fetch_dataframe()
mock_get_connection.return_value = ""
df = {'lot_of_data': ['xy', 'z'], 'more_data': [8, 9]}
mock_fetch_dataframe.return_value = pd.DataFrame(df)
assert mock_get_connection is data_utils.db.get_connection()
assert mock_fetch_dataframe is data_utils.db.fetch_dataframe()
assert mock_get_connection.called
assert mock_get_connection.called
# Lot of test-functions similar to this:
def test_valid_data(self):
resp = self.c.post('/', data={'id': 3338})
self.assertEqual(resp.status_code, 200)
self.assertContains(resp, 'Hello', status_code=200)
我收到以下错误消息:
通过模拟替换原始函数是行不通的。
谢谢你的帮助。
最佳答案
class IndexViewTest(TestCase):
@mock.patch('du_db.db.get_connection')
@mock.patch('du_db.db.fetch_dataframe')
def setUp(self, mock_fetch_dataframe, mock_get_connection):
self.c = Client()
mock_get_connection = mock_get_connection() # remove this
mock_fetch_dataframe = mock_fetch_dataframe() # remove this
当您调用上面的mock时,它们会返回另一个新的mock。通过指定相同的名称,您将失去对修补模型的引用。您将无法配置或检查它们。
mock_get_connection.return_value = "" # this is NOT the mock you think
# unless removing lines above.
# And so on...
df = {'lot_of_data': ['xy', 'z'], 'more_data': [8, 9]}
mock_fetch_dataframe.return_value = pd.DataFrame(df)
# data__utils or du_db ??
assert mock_get_connection is data_utils.db.get_connection()
assert mock_fetch_dataframe is data_utils.db.fetch_dataframe()
assert mock_get_connection.called
assert mock_get_connection.called
# Lot of test-functions similar to this:
def test_valid_data(self):
resp = self.c.post('/', data={'id': 3338})
self.assertEqual(resp.status_code, 200)
self.assertContains(resp, 'Hello', status_code=200)
编辑:
据我所知,你已经看到了pdb的模拟工作。要使测试按您喜欢的方式工作,您需要对使用这两个函数的每个测试函数(例如,使用patch decorators)进行修补。然后,您必须在修补的测试函数中设置模拟。通常在测试中断言,但不在设置中断言。我知道你来这里只是为了方便,因为你对运行的代码有些怀疑。
如果您正在考虑在setup中设置mock以供其他测试函数使用(您不能这样做,您必须将它们存储在self中,然后在测试函数中再次管理它们),那么您可能对mock文档中的这个示例感兴趣:
管理修补程序的另一种方法是使用修补程序方法:
开始和停止。这些允许您将修补程序移动到您的设置中
以及拆卸方法。
>>> class MyTest(TestCase):
...
def setUp(self):
...
self.patcher = patch(’mymodule.foo’)
...
self.mock_foo = self.patcher.start()
...
...
def test_foo(self):
...
self.assertTrue(mymodule.foo is self.mock_foo)
...
...
def tearDown(self):
...
self.patcher.stop()
...
>>> MyTest(’test_foo’).run()
关于python - 如何模拟数据库方法,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/53832528/