If your inner iterable can be continued after an exception, all you need to wrap it is a trivial generator:
def wrapper(gen):
while True:
try:
yield next(gen)
except StopIteration:
break
except Exception as e:
print(e) # or whatever kind of logging you want
For example:
In [9]: list(wrapper(csv.reader(open('test.csv', 'r'))))
field larger than field limit (10)
Out[9]: [['foo', 'bar', 'baz'], ['abc', 'def', 'ghi']]
On the other hand, if the inner iterator can’t be continued after an exception, there’s no way you can wrap it:
def raisinggenfunc():
yield 1
raise ValueError("spurious error")
yield 3
In [11]: list(wrapper(raisinggenfunc()))
spurious error
Out[11]: [1]
Any generator created by calling a Python generator function or evaluating a generator expression will not be resumable.
In such a case, you need to find some way to create a new iterator that resumes iteration. For something like csv.reader, that would mean reading n lines from the file before wrapping it in a csv.reader. In other cases it might mean passing n to the constructor. In other cases—as with raisinggenfunc above, it’s just not possible.