如何使用 python unittest 对函数中的两个函数 return 值进行单元测试
How to unittest two function return values in a function using python unitttest
我在 python 程序中有一个函数调用了两次函数:
def add_user(uname,dserver,pwd,dinstance,proc1, query1):
db_conn = db_connect(uname,dserver,pwd,dinstance)
if db_conn is not_conn:
print("Failed to connect")
sys.exit(-1)
db_conn.run_proc(proc1)
if db_conn.error_msg:
print("Failed procedure")
sys.exit(-1)
db_conn.run_query(query1)
if db_conn.err_msg:
print("Failed query")
sys.exit(-1)
现单元测试如下:
@patch('mydir.proj_dir.db_execu.db_connect')
def test_add_user(self, mock_conn):
mock_conn.return_value.not_conn.return_value = True
mock_conn.return_value.run_proc.return_value = True
mock_conn.return_value.run_query.return_value = True
mock_conn.return_value.err_msg.side_effect= [True, False]
with self.assertRaises(SystemExit):
add_user(name,dserver,pwd,dinstance,proc1, query1)
print("failed query")
我的objective是为了测试第二种错误情况。但是在添加 side_effect 之后,它只会进入显示为 "Failed procedure" 的第一个条件。我想测试 "Failed Query" 条件。我测试了前两个错误条件,但第三个错误条件失败并始终调用第二个条件。请指教
不是很清楚你到底在问什么。你只调用了一次 add_user
,所以你只测试了一个 "path",你需要多次调用它来测试多个 "paths"。
除此之外,在访问属性时,您对 mock
return_value
和 side_effect
配置模拟 作为可调用对象 的理解存在很大问题但不调用它们,您只是获得链中的下一个模拟,您没有使用任何配置。 mock也支持配置一些"magic methods"的数据模型,但是不支持配置__getattr__
("simple"属性访问)由 mock 内部使用。
因此,您应该只使用 mock 来修补/替换 db_connect
到 return 伪连接,而不是 mock 那个伪连接应该是 fake:你自己构建的一个对象,它看起来像一个连接,但行为却如你所愿,例如
class PseudoConnection:
def __init__(self, fail_proc=False, fail_query=False):
self._fail_proc = fail_proc
self._fail_query = fail_query
self.err_msg = None # or error_msg, or both
def run_proc(self, proc):
self.err_msg = self._fail_proc
def run_query(self, query):
self.err_msg = self._fail_query
然后您只需配置 mock_conn.return_value = PseudoConnection(True, False)
测试第一种情况,mock_conn.return_value = PseudoConnection(False, True)
测试第二种情况。
另外正如评论所暗示的那样,您正在访问 error_msg
和 err_msg
,并且仅尝试配置 err_msg
。我不知道哪个是对的,但我怀疑两者都是。
我在 python 程序中有一个函数调用了两次函数:
def add_user(uname,dserver,pwd,dinstance,proc1, query1):
db_conn = db_connect(uname,dserver,pwd,dinstance)
if db_conn is not_conn:
print("Failed to connect")
sys.exit(-1)
db_conn.run_proc(proc1)
if db_conn.error_msg:
print("Failed procedure")
sys.exit(-1)
db_conn.run_query(query1)
if db_conn.err_msg:
print("Failed query")
sys.exit(-1)
现单元测试如下:
@patch('mydir.proj_dir.db_execu.db_connect')
def test_add_user(self, mock_conn):
mock_conn.return_value.not_conn.return_value = True
mock_conn.return_value.run_proc.return_value = True
mock_conn.return_value.run_query.return_value = True
mock_conn.return_value.err_msg.side_effect= [True, False]
with self.assertRaises(SystemExit):
add_user(name,dserver,pwd,dinstance,proc1, query1)
print("failed query")
我的objective是为了测试第二种错误情况。但是在添加 side_effect 之后,它只会进入显示为 "Failed procedure" 的第一个条件。我想测试 "Failed Query" 条件。我测试了前两个错误条件,但第三个错误条件失败并始终调用第二个条件。请指教
不是很清楚你到底在问什么。你只调用了一次 add_user
,所以你只测试了一个 "path",你需要多次调用它来测试多个 "paths"。
除此之外,在访问属性时,您对 mock
return_value
和 side_effect
配置模拟 作为可调用对象 的理解存在很大问题但不调用它们,您只是获得链中的下一个模拟,您没有使用任何配置。 mock也支持配置一些"magic methods"的数据模型,但是不支持配置__getattr__
("simple"属性访问)由 mock 内部使用。
因此,您应该只使用 mock 来修补/替换 db_connect
到 return 伪连接,而不是 mock 那个伪连接应该是 fake:你自己构建的一个对象,它看起来像一个连接,但行为却如你所愿,例如
class PseudoConnection:
def __init__(self, fail_proc=False, fail_query=False):
self._fail_proc = fail_proc
self._fail_query = fail_query
self.err_msg = None # or error_msg, or both
def run_proc(self, proc):
self.err_msg = self._fail_proc
def run_query(self, query):
self.err_msg = self._fail_query
然后您只需配置 mock_conn.return_value = PseudoConnection(True, False)
测试第一种情况,mock_conn.return_value = PseudoConnection(False, True)
测试第二种情况。
另外正如评论所暗示的那样,您正在访问 error_msg
和 err_msg
,并且仅尝试配置 err_msg
。我不知道哪个是对的,但我怀疑两者都是。