diff --git a/CHANGELOG.md b/CHANGELOG.md index 71cbabf2332a390090f924e777c4876d9d1ba36d..fe5888aa30004bb363b680d7f8ac1b4d036eade0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,11 @@ +# v2.26.7 + +* fixed `__str__` method of `CustomException` + +# v2.26.6 + +* Traceback() may accept an Exception instance + # v2.26.5 * added `get_current_traceback` and fixed `RunActionAfterGeneratorCompletes` and `run_when_iterator_completes` default diff --git a/satella/__init__.py b/satella/__init__.py index e7cf032b21c2d4b94779f51904be420354860ccd..ccb871bfdcf75909a9ff1e3a9d0da46b3f3691d4 100644 --- a/satella/__init__.py +++ b/satella/__init__.py @@ -1 +1 @@ -__version__ = '2.26.5' +__version__ = '2.26.7a1' diff --git a/satella/exceptions.py b/satella/exceptions.py index 9ac1a0ed29af1b90dcba4b1ed22dbe9735a30b5e..73c4ab62328f8f24f588bac07a234b4b12663e2e 100644 --- a/satella/exceptions.py +++ b/satella/exceptions.py @@ -29,7 +29,7 @@ class CustomException(Exception): a = '%s(%s' % (self.__class__.__qualname__.split('.')[-1], ', '.join(map(repr, self.args))) try: if self.kwargs: - a += ', ' + ', '.join(map(lambda k, v: '%s=%s' % (k, repr(v)), self.kwargs.items())) + a += ', ' + ', '.join('%s=%s' % (k, repr(v)) for k, v in self.kwargs.items()) except AttributeError: pass a += ')' @@ -42,8 +42,7 @@ class CustomException(Exception): ', '.join(map(repr, self.args))) try: if self.kwargs: - a += ', ' + (', '.join(map(lambda kv: '%s=%s' % (kv[0], repr(kv[1])), - self.kwargs.items()))) + a += ', ' + ', '.join('%s=%s' % (k, repr(v)) for k, v in self.kwargs.items()) except AttributeError: pass a += ')' diff --git a/satella/instrumentation/trace_back/trace_back.py b/satella/instrumentation/trace_back/trace_back.py index 758d5c8f7f95e951d862f2936c0967f5e537fa3a..f57498de1db0212e1082e3876e5ed8adfdcfa401 100644 --- a/satella/instrumentation/trace_back/trace_back.py +++ b/satella/instrumentation/trace_back/trace_back.py @@ -53,7 +53,7 @@ class Traceback(JSONAble): out.append(str(frame)) return ''.join(out) - def __init__(self, starting_frame: tp.Optional[types.FrameType] = None, + def __init__(self, starting_frame: tp.Optional[tp.Union[Exception, types.FrameType]] = None, policy=GenerationPolicy): if inspect.isclass(policy): value_pickling_policy = policy() @@ -69,7 +69,10 @@ class Traceback(JSONAble): else: f = inspect.currentframe() else: - f = starting_frame + if isinstance(starting_frame, Exception): + f = starting_frame.__traceback__.tb_frame + else: + f = starting_frame while f: self.frames.append(StackFrame(f, value_pickling_policy)) diff --git a/tests/test_instrumentation/test_trace_back.py b/tests/test_instrumentation/test_trace_back.py index 36bf8e57d0664a4880d7b32992c7171c21aa70f2..53d231bcfbb7b31a230fd505cd544e079577c865 100644 --- a/tests/test_instrumentation/test_trace_back.py +++ b/tests/test_instrumentation/test_trace_back.py @@ -7,6 +7,14 @@ from satella.instrumentation import Traceback, get_current_traceback class TestTraceback(unittest.TestCase): + + def test_traceback_from_exception(self): + try: + a = 1 / 0 + except ZeroDivisionError as e: + tb = Traceback(e) + self.assertIn('ZeroDivisionError', tb.pretty_format()) + def test_get_current_traceback(self): try: a = 1 / 0