document.writeln('');

本教程深入探讨了在python单元测试中使用`unittest.mock`模拟类方法抛出异常时,`call_count`意外为零的常见困惑。文章将阐明`patch`类时,方法调用计数应针对模拟的实例对象而非模拟类本身,并通过详尽的代码示例和解释,指导开发者正确地设置`side_effect`并断言方法调用,确保测试逻辑的准确性。
在编写单元测试时,我们经常需要模拟(mock)外部依赖的行为,包括模拟这些依赖抛出异常的情况。unittest.mock库是Python中实现这一目标的强大工具。然而,在使用patch来模拟一个类及其方法,并期望该方法抛出异常时,开发者可能会遇到一个令人困惑的问题:即使方法确实被调用并成功抛出异常(且异常可能被捕获),其call_count却显示为0。本文将深入分析这一现象的根本原因,并提供正确的解决方案。
考虑一个服务类UploadService,其中包含一个upload方法,该方法内部调用了Blob类的一个实例方法upload_from_string。我们希望测试当upload_from_string方法抛出异常时,UploadService的异常处理逻辑是否正确。
以下是相关的代码示例:
upload_service.py
立即学习“Python免费学习笔记(深入)”;
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
|
test_upload_service.py (原始的、有问题的测试)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
|
运行上述测试,会得到如下错误:
1 2 3 |
|
这表明尽管side_effect被正确触发,并且异常被捕获,但MockedBlobClass.upload_from_string.call_count却为0。
使用 MapV-Three 构建专业的 3D 地图和 GIS 应用 - 基于 Z-up 坐标系的 3D 地图库,支持地图编辑、测量工具、要素绘制、数据管理等地理可视化功能。适用于创建地图编辑器、测量工具、空间数据可视化等 Web-GIS 应用。
问题的核心在于对unittest.mock.patch如何模拟类的理解。当使用patch("module.ClassName")时,MockedClassName实际上是一个模拟的类对象。这意味着:
因此,MockedBlobClass.upload_from_string实际上是一个从未被调用的Mock对象,因为它代表的是“类方法”或“未实例化的类上的方法”。而真正被调用的是MockedBlobClass.return_value.upload_from_string。
要解决这个问题,我们需要将call_count的断言指向正确的Mock对象,即模拟的实例对象的方法。在我们的测试代码中,gcs_blob_instance就是这个模拟的实例对象。
以下是修正后的测试代码:
test_upload_service.py (修正后的测试)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
|
通过将断言从MockedBlobClass.upload_from_string.call_count改为gcs_blob_instance.upload_from_string.call_count,测试将成功通过。这是因为gcs_blob_instance正是UploadService.upload方法中实际操作的Blob实例的模拟。
在Python单元测试中使用unittest.mock.patch模拟类及其方法时,正确理解模拟类和模拟实例之间的区别至关重要。当被测试代码实例化一个类并调用其方法时,方法调用实际上发生在模拟的实例对象上。因此,设置side_effect和断言call_count都应针对这个模拟实例的方法。遵循这些原则,可以避免常见的call_count为零的困惑,并编写出更准确、更可靠的单元测试。
5元云服务器:入门级新手首选 我是一名刚毕业的大学生,对编程充满了热情,但现实总是骨感一些。刚踏入职场,我梦想着能独立开发一个网站或应用,却苦于没有足够的资源。买一台实体服务器太贵,租个虚拟空间又觉得门槛太高。直到有一天,我在网上偶然看到“5元云服务器”这个关键词,那一刻,我感觉就像黑暗中看到了一盏小灯——它便宜得几乎让人不敢相信,却可能就是通往梦想的第一步。 那天晚上,我点开了一个云服务网站,输…
云服务器免费使用活动全面开启 嗨,大家好!我是小明,一个普通的大学生,去年还在为学校的创业项目发愁呢。那时候,我有个小想法:做个简单的网站,展示我们团队的环保APP概念。但问题是,我们连个像样的服务器都没有,每次在宿舍的电脑上测试代码,都卡得要死,感觉像在泥潭里爬行。我心想,如果能有个免费的东西试试就好了——谁知道呢,说不定一试就上瘾了。 那天,我在社交媒体上刷着朋友圈,突然看到一条消息:“云服务…
云服务器收费:这些套路你中招了吗? 你有没有试过租用云服务器?作为一个企业主或自由职业者,我经常看到朋友或同事在谈到服务器成本时,眼睛发亮地说:“哇,云服务器真方便,弹性扩展,几乎不用操心。”但后来,他们又会苦笑着说:“哎呀,账单来了,我差点被吓晕过去!”这不奇怪,因为云服务器收费的套路,就像一场隐形的迷宫,等着你一步步走进去。今天,我们就来聊聊“云服务器怎么收费的”,帮你揭开这些层层包裹的陷阱。…
2021年最全云服务器优惠大揭秘 嗨,大家好,我是小明,一个普通的小白领,最近我打算自己建个网站分享旅行照片和心得。刚开始,我觉得这挺简单的,但一查资料,就陷入了云服务器的世界。哈哈,别笑,我刚开始也觉得云服务器是高科技的东西,搞得我一头雾水。不过,2021年的时候,各大云服务商推出了不少优惠套餐,让我这个新手觉得机会来了。你想知道2021年云服务器优惠套餐有哪些吗?让我来和你分享我的经历。 回想…
一、预算有限也能出奇迹:低成本小程序的成功密码 很多人认为开发一个高质量小程序至少要花几万元,但其实只要掌握“精准定位 + 资源复用 + 数据驱动”的方法论,仅用1000元也能做出价值10万的效果。关键在于: 突出核心功能:剔除冗余模块,集中资源打造用户最需要的核心体验。 善用免费资源:借助开源框架、模板平台和免费云服务大幅压缩成本。 以数据为导向:通过用户行为反馈不断优化产品,提升转化效率。从…
163邮箱超大文件发送有五种方法:一、用内置大附件功能(≤2GB);二、启用云附件服务(单次≤3GB,总容量16GB);三、通过网易网盘共享链接(支持10GB以上);四、本地分卷压缩后逐个添加;五、检查并规避安全拦截机制。 如果您在163邮箱中需要发送体积超过常规限制的文件,但发现直接添加附件失败或提示“文件过大”,则可能是由于163邮箱对普通附件设置了严格上限。以下是针对该问题的多种可行操作路…