Skip to content

Commit

Permalink
Revise device tests to use improved framework.
Browse files Browse the repository at this point in the history
Signed-off-by: mulhern <amulhern@redhat.com>
  • Loading branch information
mulkieran committed Aug 5, 2016
1 parent 1838be2 commit b5c845e
Showing 1 changed file with 114 additions and 103 deletions.
217 changes: 114 additions & 103 deletions tests/_device_tests/_devices_tests.py
Expand Up @@ -43,10 +43,13 @@
from pyudev import DeviceNotFoundByNumberError
from pyudev import DeviceNotFoundInEnvironmentError

from .._constants import _CONTEXT
from .._constants import _CONTEXT_STRATEGY
from .._constants import _DEVICE_DATA
from .._constants import _DEVICES
from .._constants import _SUBSYSTEM_STRATEGY
from .._constants import _UDEV_TEST
from .._constants import DEVICE_STRATEGY

from ..utils import failed_health_check_wrapper


class TestDevices(object):
Expand All @@ -55,39 +58,43 @@ class TestDevices(object):
"""
# pylint: disable=invalid-name

@given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA))
@given(_CONTEXT_STRATEGY, DEVICE_STRATEGY())
@settings(max_examples=5)
def test_from_path(self, a_context, device_datum):
device = Devices.from_path(a_context, device_datum.device_path)
assert device is not None
assert device == \
Devices.from_sys_path(a_context, device_datum.sys_path)
assert device == Devices.from_path(a_context, device_datum.sys_path)

@given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA))
def test_from_path(self, a_context, a_device):
"""
from_path() method yields correct device.
"""
assert a_device == Devices.from_path(a_context, a_device.device_path)

@given(_CONTEXT_STRATEGY, DEVICE_STRATEGY())
@settings(max_examples=5)
def test_from_path_strips_leading_slash(self, a_context, device_datum):
path = device_datum.device_path
def test_from_path_strips_leading_slash(self, a_context, a_device):
"""
from_path() yields the same value, even if initial '/' is missing.
"""
path = a_device.device_path
assert Devices.from_path(a_context, path[1:]) == \
Devices.from_path(a_context, path)

@given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA))
@given(_CONTEXT_STRATEGY, DEVICE_STRATEGY())
@settings(max_examples=5)
def test_from_sys_path(self, a_context, device_datum):
device = Devices.from_sys_path(a_context, device_datum.sys_path)
assert device is not None
assert device.sys_path == device_datum.sys_path
def test_from_sys_path(self, a_context, a_device):
"""
from_sys_path() yields the correct device.
"""
assert a_device == Devices.from_sys_path(a_context, a_device.sys_path)

@given(_CONTEXT_STRATEGY)
def test_from_sys_path_device_not_found(self, a_context):
def test_from_sys_path_device_not_found(self):
"""
Verify that a non-existant sys_path causes an exception.
"""
sys_path = 'there_will_not_be_such_a_device'
with pytest.raises(DeviceNotFoundAtPathError) as exc_info:
Devices.from_sys_path(a_context, sys_path)
Devices.from_sys_path(_CONTEXT, sys_path)
error = exc_info.value
assert error.sys_path == sys_path
assert str(error) == 'No device at {0!r}'.format(sys_path)

@given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICES))
@given(_CONTEXT_STRATEGY, DEVICE_STRATEGY())
@settings(max_examples=5)
def test_from_name(self, a_context, a_device):
"""
Expand All @@ -101,55 +108,57 @@ def test_from_name(self, a_context, a_device):
)
assert new_device == a_device

@given(_CONTEXT_STRATEGY)
def test_from_name_no_device_in_existing_subsystem(self, a_context):
@given(_CONTEXT_STRATEGY, _SUBSYSTEM_STRATEGY)
@settings(max_examples=5)
def test_from_name_no_device_in_existing_subsystem(self, a_context, subsys):
"""
Verify that a real subsystem and non-existant name causes an
exception to be raised.
"""
with pytest.raises(DeviceNotFoundByNameError) as exc_info:
Devices.from_name(a_context, 'block', 'foobar')
Devices.from_name(a_context, subsys, 'foobar')
error = exc_info.value
assert error.subsystem == 'block'
assert error.subsystem == subsys
assert error.sys_name == 'foobar'
assert str(error) == 'No device {0!r} in {1!r}'.format(
error.sys_name, error.subsystem)

@given(_CONTEXT_STRATEGY)
def test_from_name_nonexisting_subsystem(self, a_context):
def test_from_name_nonexisting_subsystem(self):
"""
Verify that a non-existant subsystem causes an exception.
"""
with pytest.raises(DeviceNotFoundByNameError) as exc_info:
Devices.from_name(a_context, 'no_such_subsystem', 'foobar')
Devices.from_name(_CONTEXT, 'no_such_subsystem', 'foobar')
error = exc_info.value
assert error.subsystem == 'no_such_subsystem'
assert error.sys_name == 'foobar'
assert str(error) == 'No device {0!r} in {1!r}'.format(
error.sys_name, error.subsystem)

_device_data = [d for d in _DEVICE_DATA if d.device_node]
@pytest.mark.skipif(
len(_device_data) == 0,
reason='no device with a device node'
@failed_health_check_wrapper
@given(
_CONTEXT_STRATEGY,
DEVICE_STRATEGY(filter_func=lambda x: x.device_node is not None)
)
@given(_CONTEXT_STRATEGY, strategies.sampled_from(_device_data))
@settings(max_examples=5, min_satisfying_examples=1)
def test_from_device_number(self, a_context, device_datum):
mode = os.stat(device_datum.device_node).st_mode
@settings(max_examples=5)
def test_from_device_number(self, a_context, a_device):
"""
Verify that from_device_number() yields the correct device.
"""
mode = os.stat(a_device.device_node).st_mode
typ = 'block' if stat.S_ISBLK(mode) else 'char'
device = Devices.from_device_number(
a_context, typ, device_datum.device_number)
assert device.device_number == device_datum.device_number
# make sure, we are really referring to the same device
assert device.device_path == device_datum.device_path

_device_data = [d for d in _DEVICE_DATA if d.device_node]
@pytest.mark.skipif(
len(_device_data) == 0,
reason='no device with a device node'
device = \
Devices.from_device_number(a_context, typ, a_device.device_number)
assert a_device == device

@failed_health_check_wrapper
@given(
_CONTEXT_STRATEGY,
DEVICE_STRATEGY(filter_func=lambda x: x.device_node is not None)
)
@given(_CONTEXT_STRATEGY, strategies.sampled_from(_device_data))
@settings(max_examples=5, min_satisfying_examples=1)
def test_from_device_number_wrong_type(
self,
a_context,
device_datum
):
mode = os.stat(device_datum.device_node).st_mode
@settings(max_examples=5)
def test_from_device_number_wrong_type(self, a_context, a_device):
"""
Verify appropriate behavior on real device number but swapped
subsystems.
"""
mode = os.stat(a_device.device_node).st_mode
# deliberately use the wrong type here to cause either failure
# or at least device mismatch
typ = 'char' if stat.S_ISBLK(mode) else 'block'
Expand All @@ -158,43 +167,45 @@ def test_from_device_number_wrong_type(
# raised, or succeeds, but returns a wrong device
# (device numbers are not unique across device types)
device = Devices.from_device_number(
a_context, typ, device_datum.device_number)
a_context,
typ,
a_device.device_number
)
# if it succeeds, the resulting device must not match the
# one, we are actually looking for!
assert device.device_path != device_datum.device_path
assert device != a_device
except DeviceNotFoundByNumberError as error:
# check the correctness of the exception attributes
assert error.device_type == typ
assert error.device_number == device_datum.device_number
assert error.device_number == a_device.device_number

@given(_CONTEXT_STRATEGY)
def test_from_device_number_invalid_type(self, a_context):
def test_from_device_number_invalid_type(self):
"""
Verify that a non-existant subsystem always results in an exception.
"""
with pytest.raises(DeviceNotFoundByNumberError):
Devices.from_device_number(a_context, 'foobar', 100)
Devices.from_device_number(_CONTEXT, 'foobar', 100)

_device_data = [d for d in _DEVICE_DATA if d.device_node]
@pytest.mark.skipif(
len(_device_data) == 0,
reason='no device with a device node'
@failed_health_check_wrapper
@given(
_CONTEXT_STRATEGY,
DEVICE_STRATEGY(filter_func=lambda x: x.device_node is not None)
)
@given(_CONTEXT_STRATEGY, strategies.sampled_from(_device_data))
@settings(max_examples=5, min_satisfying_examples=1)
def test_from_device_file(self, a_context, device_datum):
device = Devices.from_device_file(
a_context,
device_datum.device_node
)
assert device.device_node == device_datum.device_node
assert device.device_path == device_datum.device_path
@settings(max_examples=5)
def test_from_device_file(self, a_context, a_device):
"""
Verify that from_device_file() yields correct device.
"""
device = Devices.from_device_file(a_context, a_device.device_node)
assert a_device == device

_device_data = [d for d in _DEVICE_DATA if list(d.device_links)]
@pytest.mark.skipif(
len(_device_data) == 0,
reason='no device with a device node'
@failed_health_check_wrapper
@given(
_CONTEXT_STRATEGY,
DEVICE_STRATEGY(filter_func=lambda x: any(x.device_links))
)
@given(_CONTEXT_STRATEGY, strategies.sampled_from(_device_data))
@settings(max_examples=5, min_satisfying_examples=1)
def test_from_device_file_links(self, a_context, device_datum):
@settings(max_examples=5)
def test_from_device_file_links(self, a_context, a_device):
"""
For each link in DEVLINKS, test that the constructed device's
path matches the orginal devices path.
Expand All @@ -205,39 +216,39 @@ def test_from_device_file_links(self, a_context, device_datum):
See: https://bugzilla.redhat.com/show_bug.cgi?id=1263441.
"""
device = Devices.from_path(a_context, device_datum.device_path)
assume(not 'DM_MULTIPATH_TIMESTAMP' in device.properties)
assume(not 'DM_MULTIPATH_TIMESTAMP' in a_device.properties)

for link in device_datum.device_links:
for link in a_device.device_links:
link = os.path.join(a_context.device_path, link)

device = Devices.from_device_file(a_context, link)
assert device.device_path == device_datum.device_path
assert device == a_device
assert link in device.device_links

@given(a_context=_CONTEXT_STRATEGY)
def test_from_device_file_no_device_file(self, tmpdir, a_context):
def test_from_device_file_no_device_file(self, tmpdir):
"""
Verify that a file that is not a device file will cause an exception
to be raised.
"""
filename = tmpdir.join('test')
filename.ensure(file=True)
with pytest.raises(DeviceNotFoundByFileError) as excinfo:
Devices.from_device_file(a_context, str(filename))
message = 'not a device file: {0!r}'.format(str(filename))
assert str(excinfo.value) == message
with pytest.raises(DeviceNotFoundByFileError):
Devices.from_device_file(_CONTEXT, str(filename))

@given(a_context=_CONTEXT_STRATEGY)
def test_from_device_file_non_existing(self, tmpdir, a_context):
def test_from_device_file_non_existing(self, tmpdir):
"""
Test that an OSError is raised when constructing a ``Device`` from
a file that does not actually exist.
"""
filename = tmpdir.join('test_from_device_file_non_existing')
assert not tmpdir.check(file=True)
with pytest.raises(DeviceNotFoundByFileError):
Devices.from_device_file(a_context, str(filename))
Devices.from_device_file(_CONTEXT, str(filename))

@_UDEV_TEST(152, "test_from_environment")
@given(_CONTEXT_STRATEGY)
def test_from_environment(self, a_context):
# there is no device in a standard environment
def test_from_environment(self):
"""
there is no device in a standard environment
"""
with pytest.raises(DeviceNotFoundInEnvironmentError):
Devices.from_environment(a_context)
Devices.from_environment(_CONTEXT)

0 comments on commit b5c845e

Please sign in to comment.