我有cassandra python驱动程序的代码。
from cassandra.cqlengine.management import sync_table
def sync_my_tables():
print sync_table
print "*" * 80
sync_table(my_models.student)
当我尝试为此编写UT时,我使用sync_table
嘲笑@patch
。
from unittest import TestCase
from mock import patch
class TestCassandraSetup(TestCase):
@patch('cassandra.cqlengine.management.sync_table', return_value=True)
def test_sync_my_tables(self, _):
from cassandra.cqlengine.management import sync_table
print "*"*80
print sync_table
print "*"*80
cass_setup.sync_my_tables()
在patch
之后,它调用实际函数并给出错误。
Traceback (most recent call last):
File "/venv/lib/python2.7/site-packages/mock/mock.py", line 1305, in patched
return func(*args, **keywargs)
File "/venv/tests/test_cassandra_setup.py", line 26, in test_sync_database_tables
cassandra_client.sync_database_tables()
File "/venv/code/cass_setup.py", line 18, in sync_my_tables
sync_table(my_tables.student)
File "/venv/lib/python2.7/site-packages/cassandra/cqlengine/management.py", line 200, in sync_table
cluster = get_cluster()
File "/venv/lib/python2.7/site-packages/cassandra/cqlengine/connection.py", line 182, in get_cluster
raise CQLEngineException("%s.cluster is not configured. Call one of the setup or default functions first." % __name__)
CQLEngineException: cassandra.cqlengine.connection.cluster is not configured. Call one of the setup or default functions first.
-------------------- >> begin captured stdout << ---------------------
********************************************************************************
<MagicMock name='sync_table' id='4490003152'>
********************************************************************************
<function sync_table at 0x10b8075f0>
********************************************************************************
在print语句中,它首次打印MagicMock
,但在实际代码中打印时,它会打印实际函数而不是模拟对象。
乳清之间的变化?
答案 0 :(得分:1)
Python不能模拟(替换)模块范围内已有的东西。导入后,您无法从外部更改它。要使代码可测试,您需要导入更高级别的模块并从那里使用该方法,因为它只是一个可以更改的属性。
from cassandra.cqlengine import management
def sync_my_tables():
print management.sync_table
print "*" * 80
management.sync_table(my_models.student)
这种方式mock能够在运行时替换函数(只是management.sync_table = MagicMock()
)。
在测试功能中,您在更换功能后进行导入,以便按预期工作。
答案 1 :(得分:1)
使用补丁时,您需要修补使用补丁的对象。因此,如果sync_my_tables
位于路径为foo/bar/baz.py
的文件中,则需要调用此类补丁:
@patch('foo.bar.baz.sync_table')
def test_sync_table(self, _):
# test code