首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >模拟迭代器以引发异常

问模拟迭代器以引发异常
EN

Stack Overflow用户
提问于 2019-04-03 18:26:35
回答 1查看 699关注 0票数 0

我正在使用python2.7.15rc1。我试图模拟迭代器,以便它在迭代时抛出异常。例:

代码语言:javascript
复制
elements = [1,2,3,Exception('boom!')]
iterable = <create a mock iterable to iterate over "elements">

# this does not print anything.
for value in iterable:
   ...

我尝试在side_effect实例的next()方法上使用MagicMock属性,如下所示:

代码语言:javascript
复制
from mock import MagicMock

mocked_next = MagicMock()
mocked_next.next.side_effect = [1,2,3,Exception('boom!')]

mocked_iterable = MagicMock()
mocked_iterable.__iter__.return_value = mocked_next
...
# This does not print anything and no exception is raised
for value in mocked_iterable:
    print(value)

我假设for循环最终会调用mocked_iterable上的__iter__,后者返回另一个带有具有side_effect的next属性的模拟对象。我的期望是循环最终会调用mocked_next.next(),这将迭代我在side_effect中提供给它的列表。

显然,我的理解是不正确的。我在这里错过了什么?这是否可以完全通过模拟来实现,或者我是否必须创建一个自定义迭代器来实现这个行为?

编辑:,我正在尝试测试一段代码的异常处理部分,该代码在可迭代的基础上迭代,因此试图模拟一个抛出异常的迭代器。

EN

回答 1

Stack Overflow用户

发布于 2019-04-03 18:48:20

您要寻找的东西不适合MagicMock,因为side_effect可以是异常,也可以是可迭代的,但不能两者兼而有之。相反,您应该创建一个具有__iter__方法的类,该方法生成给定序列中的项,然后引发给定的异常:

代码语言:javascript
复制
class ExceptionRaisingIterable:
    def __init__(self, seq, exception):
        self.seq = seq
        self.exception = exception

    def __iter__(self):
        for i in self.seq:
            yield i
        raise self.exception

for value in ExceptionRaisingIterable([1, 2, 3], Exception('boom!')):
    print(value)

这一产出如下:

代码语言:javascript
复制
1
2
3
Traceback (most recent call last):
  File "test.py", line 11, in <module>
    for value in ExceptionRaisingIterable([1, 2, 3], Exception('boom!')):
  File "test.py", line 9, in __iter__
    raise self.exception
Exception: boom!
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/55501898

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档