Skip to content

Commit

Permalink
hints on the potential signal raised + better tests
Browse files Browse the repository at this point in the history
  • Loading branch information
ederag committed Feb 10, 2018
1 parent 6632a5f commit bf9202a
Show file tree
Hide file tree
Showing 4 changed files with 49 additions and 10 deletions.
5 changes: 4 additions & 1 deletion doc/example/general.rst
Original file line number Diff line number Diff line change
Expand Up @@ -228,8 +228,11 @@ This is why for exit codes larger than 128, an additional hint is given:
ERROR: InvocationError for command
'<command defined in tox.ini>' (exited with code 139)
Note: On unix systems, an exit code larger than 128 often means a fatal error (e.g. 139=128+11: segmentation fault)
Note: On unix systems, an exit code larger than 128 often
means a fatal error signal (e.g. 139=128+11: SIGSEGV)
The example given is based on ``<exit code> - 128``
if it is found in the :py:mod:`signal` module.
The signal numbers (e.g. 11 for a segmentation fault) can be found in the
"Standard signals" section of the `signal man page`_.
Their meaning is described in `POSIX signals`_.
Expand Down
28 changes: 28 additions & 0 deletions tests/test_result.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import signal
import socket
import sys

Expand Down Expand Up @@ -69,3 +70,30 @@ def test_get_commandlog(pkg):
assert envlog.dict["setup"]
setuplog2 = replog.get_envlog("py36").get_commandlog("setup")
assert setuplog2.list == setuplog.list


@pytest.mark.parametrize('exitcode', [None, 0, 5, 128 + signal.SIGTERM, 1234])
def test_InvocationError(exitcode):

This comment has been minimized.

Copy link
@gaborbernat

gaborbernat Feb 12, 2018

let's not break PEP-8 naming convention here 👍

This comment has been minimized.

Copy link
@ederag

ederag Feb 12, 2018

Author Owner

Indeed: exitcode changed to exit_code.

This comment has been minimized.

Copy link
@gaborbernat

gaborbernat Feb 12, 2018

also for test_InvocationError it's fine to have test_invocation_error I think

This comment has been minimized.

Copy link
@ederag

ederag Feb 13, 2018

Author Owner

done

This comment has been minimized.

Copy link
@gaborbernat

gaborbernat Feb 13, 2018

can you open a new PR with this?

if exitcode is None:
exception = tox.exception.InvocationError("<command>")
else:
exception = tox.exception.InvocationError("<command>", exitcode)
result = str(exception)
if exitcode is None:
needle = "(exited with code"
assert needle not in result
else:
needle = "(exited with code %d)" % exitcode
assert needle in result
if exitcode > 128:
needle = ("Note: On unix systems, an exit code larger than 128 often "
"means a fatal error signal")
assert needle in result
if exitcode == 128 + signal.SIGTERM:
eg_number = signal.SIGTERM
eg_name = "SIGTERM"
else:
eg_number = 11
eg_name = "SIGSEGV"
eg_str = "(e.g. {}=128+{}: {})".format(eg_number+128, eg_number, eg_name)
assert eg_str in result
10 changes: 4 additions & 6 deletions tests/test_z_cmdline.py
Original file line number Diff line number Diff line change
Expand Up @@ -906,18 +906,16 @@ def test_tox_cmdline(monkeypatch):
tox.cmdline(['caller_script', '--help'])


@pytest.mark.parametrize('exitcode', [0, 5, 129])
@pytest.mark.parametrize('exitcode', [0, 6])
def test_exitcode(initproj, cmd, exitcode):
""" Check for correct InvocationError, with exit code,
except for zero exit code """
tox_ini_content = "[testenv:foo]\ncommands=python -c 'import sys; sys.exit(%d)'" % exitcode
initproj("foo", filedefs={'tox.ini': tox_ini_content})
result = cmd()
if exitcode:
needle = "(exited with code %d)" % exitcode
assert any(needle in line for line in result.outlines)
if exitcode > 128:
needle = ("Note: On unix systems, an exit code larger than 128 "
"often means a fatal error (e.g. 139=128+11: segmentation fault)")
assert any(needle in line for line in result.outlines)
else:
needle = "(exited with code"
needle = "InvocationError"
assert all(needle not in line for line in result.outlines)
16 changes: 13 additions & 3 deletions tox/__init__.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
import signal

from pkg_resources import DistributionNotFound
from pkg_resources import get_distribution

from .hookspecs import hookimpl
from .hookspecs import hookspec


try:
_full_version = get_distribution(__name__).version
__version__ = _full_version.split('+', 1)[0]
Expand Down Expand Up @@ -41,11 +44,18 @@ def __init__(self, command, exitcode=None):

def __str__(self):
str_ = "%s for command %s" % (self.__class__.__name__, self.command)
if self.exitcode:
if self.exitcode is not None:
str_ += " (exited with code %d)" % (self.exitcode)
if self.exitcode > 128:
str_ += ("\nNote: On unix systems, an exit code larger than 128 "
"often means a fatal error (e.g. 139=128+11: segmentation fault)")
signals = {number: name
for name, number in vars(signal).items()
if name.startswith("SIG")}
number = self.exitcode - 128
name = signals.get(number)
(eg_number, eg_name) = (number, name) if name else (11, "SIGSEGV")
str_ += ("\nNote: On unix systems, an exit code larger than 128 often "
"means a fatal error signal "
"(e.g. {}=128+{}: {})".format(eg_number+128, eg_number, eg_name))
return str_

class MissingFile(Error):
Expand Down

0 comments on commit bf9202a

Please sign in to comment.