Django的单元测试会将警告转换为异常吗?
我在使用Django的单元测试工具(manage.py test),结果遇到一个错误,代码在生成警告时就停止了。而同样的代码在用标准的Python unittest模块测试时,虽然会生成警告,但代码会继续执行。
经过一些研究,我发现Python可以设置将警告当作异常来处理,这样测试框架就会认为发生了错误。不幸的是,Django的测试文档对“错误”的定义有点模糊,也没有说明如何修改警告的处理方式。
所以,我想问:Django的单元测试框架默认是把警告当作错误来处理的吗?Django有没有什么方法可以改变这种行为?如果没有,大家有没有建议让我在Django中打印出错误但继续执行代码?还是说我完全误解了这个问题?
更新:测试代码在MySQLdb的调用中遇到警告时停止了。这些调用在Python unittest框架下测试时也会产生相同的警告,但不会停止。我会想办法用简洁的代码复现这个情况,以便分享。
回答:
进一步研究发现,这种行为与Django的MySQL后端有关:
/usr/...django/.../mysql/base.py:
if settings.DEBUG:
...
filterwarnings("error", category=Database.Warning)
当我把settings.py中的DEBUG设置为False时,代码会抛出警告但不会停止。
我之前没有遇到过这种情况,因为我的数据库调用是由我自己写的后端生成的。由于我没有调用Django的后端,所以没有重置警告的处理方式,代码在警告出现时仍然继续执行。而Django的测试框架肯定会调用Django的后端——它会对数据库做各种操作——而这个调用会在我的代码执行之前重置警告的处理方式。
1 个回答
根据更新的信息,我觉得这是Django应该做的事情。MySQL的警告可能意味着很多问题,甚至可能导致数据丢失(比如,如果你尝试插入一个超出列能容纳的值,MySQL会发出警告并默默地截断这个值)。这些都是在测试时你希望能发现的问题。所以,最好的办法就是查看它产生的警告,然后修改你的代码,确保不再出现这些警告。