-
-
Notifications
You must be signed in to change notification settings - Fork 41
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* Test all Python versions * Extensive changes to make the the plugin easier to use * Do not disable the socket automatically. * Add @pytest.mark.disable_socket and @pytest.mark.enable_socket to conveniently mark tests without importing the package * Add socket_disabled and socket_enabled fixtures. * Simplify socket blocking code. * Remove printed messages. * Relax py.test version requirement * Add a command-line option, create a custom exception * Fix Python 2 incompatibility * Fix tests unintentionally modifying the socket status for other tests * Formatting Make flake8 happy * Fix CI issues * Fix pypy's HTTPS error
- Loading branch information
1 parent
45df1ca
commit ed0305a
Showing
6 changed files
with
223 additions
and
47 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,45 +1,64 @@ | ||
# -*- coding: utf-8 -*- | ||
import socket | ||
import sys | ||
|
||
import pytest | ||
|
||
_module = sys.modules[__name__] | ||
_true_socket = socket.socket | ||
|
||
|
||
def pytest_runtest_setup(): | ||
""" disable the internet. test-cases can explicitly re-enable """ | ||
class SocketBlockedError(RuntimeError): | ||
def __init__(self, *args, **kwargs): | ||
super(SocketBlockedError, self).__init__("A test tried to use socket.socket.") | ||
|
||
|
||
def pytest_addoption(parser): | ||
group = parser.getgroup('socket') | ||
group.addoption( | ||
'--disable-socket', | ||
action='store_true', | ||
dest='disable_socket', | ||
help='Disable socket.socket by default to block network calls.' | ||
) | ||
|
||
|
||
@pytest.fixture(autouse=True) | ||
def _socket_marker(request): | ||
if request.node.get_marker('disable_socket'): | ||
request.getfixturevalue('socket_disabled') | ||
if request.node.get_marker('enable_socket'): | ||
request.getfixturevalue('socket_enabled') | ||
|
||
if request.config.getoption('--disable-socket'): | ||
request.getfixturevalue('socket_disabled') | ||
|
||
|
||
@pytest.fixture | ||
def socket_disabled(): | ||
""" disable socket.socket for duration of this test function """ | ||
disable_socket() | ||
yield | ||
enable_socket() | ||
|
||
|
||
@pytest.fixture(scope='function') | ||
def socket_enabled(request): | ||
""" re-enable socket.socket for duration of this test function """ | ||
@pytest.fixture | ||
def socket_enabled(): | ||
""" enable socket.socket for duration of this test function """ | ||
enable_socket() | ||
request.addfinalizer(disable_socket) | ||
yield | ||
disable_socket() | ||
|
||
|
||
def disable_socket(): | ||
""" disable socket.socket to disable the Internet. useful in testing. | ||
""" | ||
setattr(_module, u'_socket_disabled', True) | ||
|
||
def guarded(*args, **kwargs): | ||
if getattr(_module, u'_socket_disabled', False): | ||
raise RuntimeError( | ||
u"A test tried to use socket.socket without explicitly un-blocking it.") | ||
else: | ||
# SocketType is a valid, public alias of socket.socket, | ||
# we use it here to avoid namespace collisions | ||
return socket.SocketType(*args, **kwargs) | ||
raise SocketBlockedError() | ||
|
||
socket.socket = guarded | ||
|
||
print(u'[!] socket.socket is now blocked. The network should be inaccessible.') | ||
|
||
|
||
def enable_socket(): | ||
""" re-enable socket.socket to enable the Internet. useful in testing. | ||
""" | ||
setattr(_module, u'_socket_disabled', False) | ||
print(u'[!] socket.socket is UN-blocked, and the network can be accessed.') | ||
socket.socket = _true_socket |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters