Clarify uncertain nature of tracebacks on Python 2 (#42513)

* Only add exception/traceback on Python 3

On Python 2 the traceback could be any exception from the stack frame
and likely unrelated to the fail_json call.

On Python 3 the traceback is cleared outside any exception frame, so the
call always returns the most inner traceback (if any), and therefor is
most likely related to the fail_json call.

* Add uncertainty to traceback on Python 2

On Python 2 the last exception in the stack frame is being returned,
this could be unrelated to the actual error, especially if fail_json()
is called outside an except: block.
This commit is contained in:
Dag Wieers 2018-07-25 17:49:16 +02:00 committed by Brian Coca
parent 1305fca414
commit 9bf22309b3

View file

@ -2384,10 +2384,15 @@ class AnsibleModule(object):
raise AssertionError("implementation error -- msg to explain the error is required") raise AssertionError("implementation error -- msg to explain the error is required")
kwargs['failed'] = True kwargs['failed'] = True
# add traceback if debug or high verbosity and it is missing # Add traceback if debug or high verbosity and it is missing
# Note: badly named as exception, it is really always been 'traceback' # NOTE: Badly named as exception, it really always has been a traceback
if 'exception' not in kwargs and sys.exc_info()[2] and (self._debug or self._verbosity >= 3): if 'exception' not in kwargs and sys.exc_info()[2] and (self._debug or self._verbosity >= 3):
kwargs['exception'] = ''.join(traceback.format_tb(sys.exc_info()[2])) if PY2:
# On Python 2 this is the last (stack frame) exception and as such may be unrelated to the failure
kwargs['exception'] = 'WARNING: The below traceback may *not* be related to the actual failure.\n' +\
''.join(traceback.format_tb(sys.exc_info()[2]))
else:
kwargs['exception'] = ''.join(traceback.format_tb(sys.exc_info()[2]))
self.do_cleanup_files() self.do_cleanup_files()
self._return_formatted(kwargs) self._return_formatted(kwargs)