Merge pull request #2005 from sebres/0.10

Stability fix for fail2banclienttestcase, avoid sporadic coverage decrease.
pull/2014/head
Serg G. Brester 2017-12-22 14:27:20 +01:00 committed by GitHub
commit b104da2800
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 130 additions and 101 deletions

View File

@ -276,8 +276,10 @@ class Actions(JailThread, Mapping):
exc_info=logSys.getEffectiveLevel()<=logging.DEBUG)
while self.active:
if self.idle:
logSys.debug("Actions: enter idle mode")
Utils.wait_for(lambda: not self.active or not self.idle,
self.sleeptime * 10, self.sleeptime)
lambda: False, self.sleeptime)
logSys.debug("Actions: leave idle mode")
continue
if not Utils.wait_for(lambda: not self.active or self.__checkBan(), self.sleeptime):
self.__checkUnBan()

View File

@ -122,7 +122,9 @@ def loop(active, timeout=None, use_poll=False):
if timeout is None:
timeout = Utils.DEFAULT_SLEEP_TIME
poll = asyncore.poll
if use_poll and asyncore.poll2 and hasattr(asyncore.select, 'poll'): # pragma: no cover
if callable(use_poll):
poll = use_poll
elif use_poll and asyncore.poll2 and hasattr(asyncore.select, 'poll'): # pragma: no cover
logSys.debug('Server listener (select) uses poll')
# poll2 expected a timeout in milliseconds (but poll and loop in seconds):
timeout = float(timeout) / 1000

View File

@ -30,9 +30,10 @@ import time
import unittest
from ..server.action import CommandAction, CallingMap, substituteRecursiveTags
from ..server.actions import OrderedDict
from ..server.actions import OrderedDict, Actions
from ..server.utils import Utils
from .dummyjail import DummyJail
from .utils import LogCaptureTestCase
from .utils import pid_exists
@ -568,3 +569,19 @@ class CommandActionTest(LogCaptureTestCase):
self.assertIn("'b': 11", s)
self.assertIn("'c': ", s) # presents as callable
self.assertNotIn("'c': ''", s) # but not empty
def testActionsIdleMode(self):
a = Actions(DummyJail())
a.sleeptime = 0.0001; # don't need to wait long
# enter idle mode right now (start idle):
a.idle = True;
# start:
a.start()
# wait for enter/leave of idle mode:
self.assertLogged("Actions: enter idle mode", wait=10)
# leave idle mode:
a.idle = False
self.assertLogged("Actions: leave idle mode", wait=10)
# stop it:
a.active = False
a.join()

View File

@ -96,6 +96,9 @@ class FailExitException(fail2bancmdline.ExitException):
pass
SUCCESS = ExitException
FAILED = FailExitException
INTERACT = []
@ -299,35 +302,40 @@ def with_foreground_server_thread(startextra={}):
)
th.daemon = True
th.start()
try:
# wait for start thread:
Utils.wait_for(lambda: phase.get('start', None) is not None, MAX_WAITTIME)
self.assertTrue(phase.get('start', None))
# wait for server (socket and ready):
self._wait_for_srv(tmp, True, startparams=startparams)
DefLogSys.info('=== within server: begin ===')
self.pruneLog()
# several commands to server in body of decorated function:
return f(self, tmp, startparams, *args, **kwargs)
finally:
DefLogSys.info('=== within server: end. ===')
self.pruneLog()
# to wait for end of server, default accept any exit code, because multi-threaded,
# thus server can exit in-between...
def _stopAndWaitForServerEnd(code=(SUCCESS, FAILED)):
# if seems to be down - try to catch end phase (wait a bit for end:True to recognize down state):
if not phase.get('end', None) and not os.path.exists(pjoin(tmp, "f2b.pid")):
Utils.wait_for(lambda: phase.get('end', None) is not None, MID_WAITTIME)
# stop (if still running):
if not phase.get('end', None):
self.execSuccess(startparams, "stop")
# wait for end:
self.execCmd(code, startparams, "stop")
# wait for end sign:
Utils.wait_for(lambda: phase.get('end', None) is not None, MAX_WAITTIME)
self.assertTrue(phase.get('end', None))
self.assertLogged("Shutdown successful", "Exiting Fail2ban", all=True)
self.stopAndWaitForServerEnd = _stopAndWaitForServerEnd
# wait for start thread:
Utils.wait_for(lambda: phase.get('start', None) is not None, MAX_WAITTIME)
self.assertTrue(phase.get('start', None))
# wait for server (socket and ready):
self._wait_for_srv(tmp, True, startparams=startparams)
DefLogSys.info('=== within server: begin ===')
self.pruneLog()
# several commands to server in body of decorated function:
return f(self, tmp, startparams, *args, **kwargs)
finally:
if th:
# wait for server end (if not yet already exited):
DefLogSys.info('=== within server: end. ===')
self.pruneLog()
self.stopAndWaitForServerEnd()
# we start client/server directly in current process (new thread),
# so don't kill (same process) - if success, just wait for end of worker:
if phase.get('end', None):
th.join()
self.stopAndWaitForServerEnd = None
return wrapper
return _deco_wrapper
@ -388,11 +396,9 @@ class Fail2banClientServerBase(LogCaptureTestCase):
logSys.debug("No log file %s to examine details of error", log)
raise
def execSuccess(self, startparams, *args):
raise NotImplementedError("To be defined in subclass")
def execFailed(self, startparams, *args):
raise NotImplementedError("To be defined in subclass")
def execCmd(self, exitType, startparams, *args):
self.assertRaises(exitType, self.exec_command_line[0],
(self.exec_command_line[1:] + startparams + args))
#
# Common tests
@ -401,7 +407,7 @@ class Fail2banClientServerBase(LogCaptureTestCase):
# start and wait to end (foreground):
logSys.debug("start of test worker")
phase['start'] = True
self.execSuccess(("-f",) + startparams, "start")
self.execCmd(SUCCESS, ("-f",) + startparams, "start")
# end :
phase['end'] = True
logSys.debug("end of test worker")
@ -409,46 +415,40 @@ class Fail2banClientServerBase(LogCaptureTestCase):
@with_foreground_server_thread()
def testStartForeground(self, tmp, startparams):
# several commands to server:
self.execSuccess(startparams, "ping")
self.execFailed(startparams, "~~unknown~cmd~failed~~")
self.execSuccess(startparams, "echo", "TEST-ECHO")
self.execCmd(SUCCESS, startparams, "ping")
self.execCmd(FAILED, startparams, "~~unknown~cmd~failed~~")
self.execCmd(SUCCESS, startparams, "echo", "TEST-ECHO")
class Fail2banClientTest(Fail2banClientServerBase):
def execSuccess(self, startparams, *args):
self.assertRaises(ExitException, _exec_client,
((CLIENT,) + startparams + args))
def execFailed(self, startparams, *args):
self.assertRaises(FailExitException, _exec_client,
((CLIENT,) + startparams + args))
exec_command_line = (_exec_client, CLIENT,)
def testConsistency(self):
self.assertTrue(isfile(pjoin(BIN, CLIENT)))
self.assertTrue(isfile(pjoin(BIN, SERVER)))
def testClientUsage(self):
self.execSuccess((), "-h")
self.execCmd(SUCCESS, (), "-h")
self.assertLogged("Usage: " + CLIENT)
self.assertLogged("Report bugs to ")
self.pruneLog()
self.execSuccess((), "-vq", "-V")
self.execCmd(SUCCESS, (), "-vq", "-V")
self.assertLogged("Fail2Ban v" + fail2bancmdline.version)
self.pruneLog()
self.execSuccess((), "--str2sec", "1d12h30m")
self.execCmd(SUCCESS, (), "--str2sec", "1d12h30m")
self.assertLogged("131400")
@with_tmpdir
def testClientDump(self, tmp):
# use here the stock configuration (if possible)
startparams = _start_params(tmp, True)
self.execSuccess(startparams, "-vvd")
self.execCmd(SUCCESS, startparams, "-vvd")
self.assertLogged("Loading files")
self.assertLogged("['set', 'logtarget',")
self.pruneLog()
# pretty dump:
self.execSuccess(startparams, "--dp")
self.execCmd(SUCCESS, startparams, "--dp")
self.assertLogged("['set', 'logtarget',")
@with_tmpdir
@ -457,28 +457,28 @@ class Fail2banClientTest(Fail2banClientServerBase):
# use once the stock configuration (to test starting also)
startparams = _start_params(tmp, True)
# start:
self.execSuccess(("-b",) + startparams, "start")
self.execCmd(SUCCESS, ("-b",) + startparams, "start")
# wait for server (socket and ready):
self._wait_for_srv(tmp, True, startparams=startparams)
self.assertLogged("Server ready")
self.assertLogged("Exit with code 0")
try:
self.execSuccess(startparams, "echo", "TEST-ECHO")
self.execFailed(startparams, "~~unknown~cmd~failed~~")
self.execCmd(SUCCESS, startparams, "echo", "TEST-ECHO")
self.execCmd(FAILED, startparams, "~~unknown~cmd~failed~~")
self.pruneLog()
# start again (should fail):
self.execFailed(("-b",) + startparams, "start")
self.execCmd(FAILED, ("-b",) + startparams, "start")
self.assertLogged("Server already running")
finally:
self.pruneLog()
# stop:
self.execSuccess(startparams, "stop")
self.execCmd(SUCCESS, startparams, "stop")
self.assertLogged("Shutdown successful")
self.assertLogged("Exit with code 0")
self.pruneLog()
# stop again (should fail):
self.execFailed(startparams, "stop")
self.execCmd(FAILED, startparams, "stop")
self.assertLogged("Failed to access socket path")
self.assertLogged("Is fail2ban running?")
@ -489,7 +489,7 @@ class Fail2banClientTest(Fail2banClientServerBase):
startparams = _start_params(tmp, logtarget=pjoin(tmp, "f2b.log"))
# if fast, start server process from client started direct here:
if unittest.F2B.fast: # pragma: no cover
self.execSuccess(startparams + ("start",))
self.execCmd(SUCCESS, startparams + ("start",))
else:
# start (in new process, using the same python version):
cmd = (sys.executable, pjoin(BIN, CLIENT))
@ -503,12 +503,12 @@ class Fail2banClientTest(Fail2banClientServerBase):
self.pruneLog()
try:
# echo from client (inside):
self.execSuccess(startparams, "echo", "TEST-ECHO")
self.execCmd(SUCCESS, startparams, "echo", "TEST-ECHO")
self.assertLogged("TEST-ECHO")
self.assertLogged("Exit with code 0")
self.pruneLog()
# test ping timeout:
self.execSuccess(startparams, "ping", "0.1")
self.execCmd(SUCCESS, startparams, "ping", "0.1")
self.assertLogged("Server replied: pong")
self.pruneLog()
# python 3 seems to bypass such short timeouts also,
@ -519,7 +519,7 @@ class Fail2banClientTest(Fail2banClientServerBase):
os.kill(pid, signal.SIGSTOP); # or SIGTSTP?
time.sleep(Utils.DEFAULT_SHORT_INTERVAL)
# test ping with short timeout:
self.execFailed(startparams, "ping", "1e-10")
self.execCmd(FAILED, startparams, "ping", "1e-10")
finally:
# resume:
os.kill(pid, signal.SIGCONT)
@ -531,7 +531,7 @@ class Fail2banClientTest(Fail2banClientServerBase):
"status",
"exit"
]
self.execSuccess(startparams, "-i")
self.execCmd(SUCCESS, startparams, "-i")
self.assertLogged("INTERACT-ECHO")
self.assertLogged("Status", "Number of jail:")
self.assertLogged("Exit with code 0")
@ -542,7 +542,7 @@ class Fail2banClientTest(Fail2banClientServerBase):
"restart",
"exit"
]
self.execSuccess(startparams, "-i")
self.execCmd(SUCCESS, startparams, "-i")
self.assertLogged("Reading config files:")
self.assertLogged("Shutdown successful")
self.assertLogged("Server ready")
@ -553,18 +553,18 @@ class Fail2banClientTest(Fail2banClientServerBase):
"reload ~~unknown~jail~fail~~",
"exit"
]
self.execSuccess(startparams, "-i")
self.execCmd(SUCCESS, startparams, "-i")
self.assertLogged("Failed during configuration: No section: '~~unknown~jail~fail~~'")
self.pruneLog()
# test reload missing jail (direct):
self.execFailed(startparams, "reload", "~~unknown~jail~fail~~")
self.execCmd(FAILED, startparams, "reload", "~~unknown~jail~fail~~")
self.assertLogged("Failed during configuration: No section: '~~unknown~jail~fail~~'")
self.assertLogged("Exit with code -1")
self.pruneLog()
finally:
self.pruneLog()
# stop:
self.execSuccess(startparams, "stop")
self.execCmd(SUCCESS, startparams, "stop")
self.assertLogged("Shutdown successful")
self.assertLogged("Exit with code 0")
@ -575,33 +575,33 @@ class Fail2banClientTest(Fail2banClientServerBase):
startparams = _start_params(tmp, logtarget="INHERITED")
## wrong config directory
self.execFailed((),
self.execCmd(FAILED, (),
"--async", "-c", pjoin(tmp, "miss"), "start")
self.assertLogged("Base configuration directory " + pjoin(tmp, "miss") + " does not exist")
self.pruneLog()
## wrong socket
self.execFailed((),
self.execCmd(FAILED, (),
"--async", "-c", pjoin(tmp, "config"), "-s", pjoin(tmp, "miss/f2b.sock"), "start")
self.assertLogged("There is no directory " + pjoin(tmp, "miss") + " to contain the socket file")
self.pruneLog()
## not running
self.execFailed((),
self.execCmd(FAILED, (),
"-c", pjoin(tmp, "config"), "-s", pjoin(tmp, "f2b.sock"), "reload")
self.assertLogged("Could not find server")
self.pruneLog()
## already exists:
open(pjoin(tmp, "f2b.sock"), 'a').close()
self.execFailed((),
self.execCmd(FAILED, (),
"--async", "-c", pjoin(tmp, "config"), "-s", pjoin(tmp, "f2b.sock"), "start")
self.assertLogged("Fail2ban seems to be in unexpected state (not running but the socket exists)")
self.pruneLog()
os.remove(pjoin(tmp, "f2b.sock"))
## wrong option:
self.execFailed((), "-s")
self.execCmd(FAILED, (), "-s")
self.assertLogged("Usage: ")
self.pruneLog()
@ -611,13 +611,13 @@ class Fail2banClientTest(Fail2banClientServerBase):
startparams = _start_params(tmp, logtarget="INHERITED")
# not started:
self.execFailed(startparams,
self.execCmd(FAILED, startparams,
"reload", "jail")
self.assertLogged("Could not find server")
self.pruneLog()
# unexpected arg:
self.execFailed(startparams,
self.execCmd(FAILED, startparams,
"--async", "reload", "--xxx", "jail")
self.assertLogged("Unexpected argument(s) for reload:")
self.pruneLog()
@ -637,16 +637,10 @@ class Fail2banClientTest(Fail2banClientServerBase):
class Fail2banServerTest(Fail2banClientServerBase):
def execSuccess(self, startparams, *args):
self.assertRaises(ExitException, _exec_server,
((SERVER,) + startparams + args))
def execFailed(self, startparams, *args):
self.assertRaises(FailExitException, _exec_server,
((SERVER,) + startparams + args))
exec_command_line = (_exec_server, SERVER,)
def testServerUsage(self):
self.execSuccess((), "-h")
self.execCmd(SUCCESS, (), "-h")
self.assertLogged("Usage: " + SERVER)
self.assertLogged("Report bugs to ")
@ -666,12 +660,12 @@ class Fail2banServerTest(Fail2banClientServerBase):
self.assertLogged("Server ready")
self.pruneLog()
try:
self.execSuccess(startparams, "echo", "TEST-ECHO")
self.execFailed(startparams, "~~unknown~cmd~failed~~")
self.execCmd(SUCCESS, startparams, "echo", "TEST-ECHO")
self.execCmd(FAILED, startparams, "~~unknown~cmd~failed~~")
finally:
self.pruneLog()
# stop:
self.execSuccess(startparams, "stop")
self.execCmd(SUCCESS, startparams, "stop")
self.assertLogged("Shutdown successful")
self.assertLogged("Exit with code 0")
@ -682,20 +676,20 @@ class Fail2banServerTest(Fail2banClientServerBase):
startparams = _start_params(tmp, logtarget="INHERITED")
## wrong config directory
self.execFailed((),
self.execCmd(FAILED, (),
"-c", pjoin(tmp, "miss"))
self.assertLogged("Base configuration directory " + pjoin(tmp, "miss") + " does not exist")
self.pruneLog()
## wrong socket
self.execFailed((),
self.execCmd(FAILED, (),
"-c", pjoin(tmp, "config"), "-x", "-s", pjoin(tmp, "miss/f2b.sock"))
self.assertLogged("There is no directory " + pjoin(tmp, "miss") + " to contain the socket file")
self.pruneLog()
## already exists:
open(pjoin(tmp, "f2b.sock"), 'a').close()
self.execFailed((),
self.execCmd(FAILED, (),
"-c", pjoin(tmp, "config"), "-s", pjoin(tmp, "f2b.sock"))
self.assertLogged("Fail2ban seems to be in unexpected state (not running but the socket exists)")
self.pruneLog()
@ -710,7 +704,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# test configuration is correct:
self.pruneLog("[test-phase 0]")
self.execSuccess(startparams, "--test")
self.execCmd(SUCCESS, startparams, "--test")
self.assertLogged("OK: configuration test is successful")
# append one wrong configured jail:
@ -719,14 +713,14 @@ class Fail2banServerTest(Fail2banClientServerBase):
# first try test config:
self.pruneLog("[test-phase 0a]")
self.execFailed(startparams, "--test")
self.execCmd(FAILED, startparams, "--test")
self.assertLogged("Unable to read the filter 'broken-jail-filter'",
"Errors in jail 'broken-jail'.",
"ERROR: test configuration failed", all=True)
# failed to start with test config:
self.pruneLog("[test-phase 0b]")
self.execFailed(startparams, "-t", "start")
self.execCmd(FAILED, startparams, "-t", "start")
self.assertLogged("Unable to read the filter 'broken-jail-filter'",
"Errors in jail 'broken-jail'.",
"ERROR: test configuration failed", all=True)
@ -857,7 +851,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
self.pruneLog("[test-phase 1a]")
if unittest.F2B.log_level < logging.DEBUG: # pragma: no cover
_out_file(test1log)
self.execSuccess(startparams, "reload")
self.execCmd(SUCCESS, startparams, "reload")
self.assertLogged(
"Reload finished.",
"1 ticket(s) in 'test-jail1", all=True, wait=MID_WAITTIME)
@ -886,7 +880,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
_write_file(test1log, "w+")
if unittest.F2B.log_level < logging.DEBUG: # pragma: no cover
_out_file(test1log)
self.execSuccess(startparams, "reload")
self.execCmd(SUCCESS, startparams, "reload")
self.assertLogged("Reload finished.", all=True, wait=MID_WAITTIME)
# test not unbanned / banned again:
self.assertNotLogged(
@ -918,7 +912,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
start= " echo '[<name>] %s: started.'" % "test-action1",
reload=" echo '[<name>] %s: reloaded.'" % "test-action1",
stop= " echo '[<name>] %s: stopped.'" % "test-action1")
self.execSuccess(startparams, "reload")
self.execCmd(SUCCESS, startparams, "reload")
self.assertLogged("Reload finished.", all=True, wait=MID_WAITTIME)
# test not unbanned / banned again:
self.assertNotLogged(
@ -979,7 +973,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# restart jail without unban all:
self.pruneLog("[test-phase 2c]")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"restart", "test-jail2")
self.assertLogged(
"Reload finished.",
@ -1007,9 +1001,9 @@ class Fail2banServerTest(Fail2banClientServerBase):
# ban manually to test later flush by unban all:
self.pruneLog("[test-phase 2d]")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"set", "test-jail2", "banip", "192.0.2.21")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"set", "test-jail2", "banip", "192.0.2.22")
self.assertLogged(
"stdout: '[test-jail2] test-action3: ++ ban 192.0.2.22",
@ -1017,7 +1011,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# restart jail with unban all:
self.pruneLog("[test-phase 2e]")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"restart", "--unban", "test-jail2")
self.assertLogged(
"Reload finished.",
@ -1050,7 +1044,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# reload jail1 without restart (without ban/unban):
self.pruneLog("[test-phase 3]")
self.execSuccess(startparams, "reload", "test-jail1")
self.execCmd(SUCCESS, startparams, "reload", "test-jail1")
self.assertLogged(
"Reload finished.", all=True, wait=MID_WAITTIME)
self.assertLogged(
@ -1065,7 +1059,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# whole reload, but this time with jail1 only (jail2 should be stopped via configuration):
self.pruneLog("[test-phase 4]")
_write_jail_cfg(enabled=[1])
self.execSuccess(startparams, "reload")
self.execCmd(SUCCESS, startparams, "reload")
self.assertLogged("Reload finished.", all=True, wait=MID_WAITTIME)
# test both jails should be reloaded:
self.assertLogged(
@ -1102,7 +1096,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# unban single ips:
self.pruneLog("[test-phase 6]")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"--async", "unban", "192.0.2.5", "192.0.2.6")
self.assertLogged(
"192.0.2.5 is not banned",
@ -1111,7 +1105,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# reload all (one jail) with unban all:
self.pruneLog("[test-phase 7]")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"reload", "--unban")
self.assertLogged("Reload finished.", all=True, wait=MID_WAITTIME)
# reloads unbanned all:
@ -1134,7 +1128,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# unban all (just to test command, already empty - nothing to unban):
self.pruneLog("[test-phase 7b]")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"--async", "unban", "--all")
self.assertLogged(
"Flush ban list",
@ -1143,7 +1137,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# backend-switch (restart instead of reload):
self.pruneLog("[test-phase 8a]")
_write_jail_cfg(enabled=[1], backend="xxx-unknown-backend-zzz")
self.execFailed(startparams, "reload")
self.execCmd(FAILED, startparams, "reload")
self.assertLogged("Reload finished.", all=True, wait=MID_WAITTIME)
self.assertLogged(
"Restart jail 'test-jail1' (reason: 'polling' != ",
@ -1151,18 +1145,18 @@ class Fail2banServerTest(Fail2banClientServerBase):
self.pruneLog("[test-phase 8b]")
_write_jail_cfg(enabled=[1])
self.execSuccess(startparams, "reload")
self.execCmd(SUCCESS, startparams, "reload")
self.assertLogged("Reload finished.", all=True, wait=MID_WAITTIME)
# several small cases (cover several parts):
self.pruneLog("[test-phase end-1]")
# wrong jail (not-started):
self.execFailed(startparams,
self.execCmd(FAILED, startparams,
"--async", "reload", "test-jail2")
self.assertLogged("the jail 'test-jail2' does not exist")
self.pruneLog()
# unavailable jail (but exit 0), using --if-exists option:
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"--async", "reload", "--if-exists", "test-jail2")
self.assertNotLogged(
"Creating new jail 'test-jail2'",
@ -1170,7 +1164,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
# restart all jails (without restart server):
self.pruneLog("[test-phase end-2]")
self.execSuccess(startparams,
self.execCmd(SUCCESS, startparams,
"--async", "reload", "--restart", "--all")
self.assertLogged(
"Jail 'test-jail1' stopped",
@ -1215,7 +1209,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
"[nginx-blck-lst] Ban 125-000-003",
"[nginx-blck-lst] Ban 125-000-004",
"[nginx-blck-lst] Ban 125-000-005",
"Banned 5 / 5, 5 ticket(s)",
"5 ticket(s)",
all=True, wait=MID_WAITTIME
)
_out_file(mpfn)
@ -1227,7 +1221,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
self.assertIn('\\125-000-005 1;\n', mp)
# unban 1, 2 and 5:
self.execSuccess(startparams, 'unban', '125-000-001', '125-000-002', '125-000-005')
self.execCmd(SUCCESS, startparams, 'unban', '125-000-001', '125-000-002', '125-000-005')
_out_file(mpfn)
# check really unbanned but other sessions are still present (blacklisted in map-file):
mp = _read_file(mpfn)
@ -1238,8 +1232,7 @@ class Fail2banServerTest(Fail2banClientServerBase):
self.assertIn('\\125-000-004 1;\n', mp)
# stop server and wait for end:
self.execSuccess(startparams, 'stop')
self.assertLogged("Shutdown successful", "Exiting Fail2ban", all=True, wait=MID_WAITTIME)
self.stopAndWaitForServerEnd(SUCCESS)
# check flushed (all sessions were deleted from map-file):
self.assertLogged("[nginx-blck-lst] Flush ticket(s) with nginx-block-map")

View File

@ -31,8 +31,10 @@ import threading
import time
import unittest
from .utils import LogCaptureTestCase
from .. import protocol
from ..server.asyncserver import AsyncServer, AsyncServerException
from ..server.asyncserver import AsyncServer, AsyncServerException, loop
from ..server.utils import Utils
from ..client.csocket import CSocket
@ -126,7 +128,20 @@ class Socket(unittest.TestCase):
self.assertFalse(os.path.exists(self.sock_name))
class ClientMisc(unittest.TestCase):
class ClientMisc(LogCaptureTestCase):
def testErrorsInLoop(self):
phase = {'cntr': 0}
def _active():
return phase['cntr'] < 40
def _poll(*args):
phase['cntr'] += 1
raise Exception('test *%d*' % phase['cntr'])
# test errors "catched" and logged:
loop(_active, use_poll=_poll)
self.assertLogged("test *1*", "test *10*", "test *20*", all=True)
self.assertLogged("Too many errors - stop logging connection errors")
self.assertNotLogged("test *21*", "test *22*", "test *23*", all=True)
def testPrintFormattedAndWiki(self):
# redirect stdout to devnull