Permalink
Browse files

BF: allow newlines in action specifications

Based from yarikoptic/_bf/multiline_action_options
  • Loading branch information...
kwirk committed Jun 23, 2014
1 parent c7de888 commit abc0756dd96015324d18fc869a863b65b4ad86a5
Showing with 50 additions and 7 deletions.
  1. +10 −7 fail2ban/client/jailreader.py
  2. +40 −0 fail2ban/tests/clientreadertestcase.py
@@ -37,9 +37,13 @@
class JailReader(ConfigReader):
optionCRE = re.compile("^((?:\w|-|_|\.)+)(?:\[(.*)\])?$")
optionSplitRE = re.compile(
r'^((?:\w|-|_|\.)+(?:\[.*?\])?)$', re.DOTALL | re.MULTILINE)
optionCRE = re.compile(
r'^((?:\w|-|_|\.)+)(?:\[(.*?)\])?$', re.DOTALL | re.MULTILINE)
optionExtractRE = re.compile(
r'([\w\-_\.]+)=(?:"([^"]*)"|\'([^\']*)\'|([^,]*))(?:,|$)')
r'([\w\-_\.]+)=(?:"([^"]*)"|\'([^\']*)\'|([^,]*))(?:,|$)',
re.DOTALL | re.MULTILINE)
def __init__(self, name, force_enable=False, **kwargs):
ConfigReader.__init__(self, **kwargs)
@@ -123,9 +127,9 @@ def getOptions(self):
logSys.warning("No filter set for jail %s" % self.__name)
# Read action
for act in self.__opts["action"].split('\n'):
for act in JailReader.optionSplitRE.split(self.__opts["action"]):
try:
if not act: # skip empty actions
if not act.strip(): # skip empty actions
continue
actName, actOpt = JailReader.extractOptions(act)
if actName.endswith(".py"):
@@ -149,7 +153,7 @@ def getOptions(self):
else:
raise AttributeError("Unable to read action")
except Exception, e:
logSys.error("Error in action definition " + act)
logSys.error("Error in action definition %r", act)
logSys.debug("Caught exception: %s" % (e,))
return False
if not len(self.__actions):
@@ -224,8 +228,7 @@ def convert(self, allow_no_files=False):
def extractOptions(option):
match = JailReader.optionCRE.match(option)
if not match:
# TODO proper error handling
return None, None
raise ValueError("Invalid definition: %r" % option)
option_name, optstr = match.groups()
option_opts = dict()
if optstr:
@@ -237,6 +237,12 @@ def testSplitOption(self):
result = JailReader.extractOptions(option)
self.assertEqual(expected, result)
def testSplitOptionMultiline(self):
action = "mail-whois-lines[logpath=/a/b\n/c/d]"
expected = ('mail-whois-lines', {'logpath': '/a/b\n/c/d'})
result = JailReader.extractOptions(action)
self.assertEquals(expected, result)
def testGlob(self):
d = tempfile.mkdtemp(prefix="f2b-temp")
# Generate few files
@@ -558,3 +564,37 @@ def testMultipleSameAction(self):
self.assertEqual(add_actions[-1][-1], "{}")
shutil.rmtree(basedir)
def testMultipleLineAction(self):
basedir = tempfile.mkdtemp("fail2ban_conf")
os.mkdir(os.path.join(basedir, "filter.d"))
os.mkdir(os.path.join(basedir, "action.d"))
open(os.path.join(basedir, "action.d", "testaction1.conf"), 'w').close()
open(os.path.join(basedir, "action.d", "testaction2.conf"), 'w').close()
open(os.path.join(basedir, "action.d", "testaction3.conf"), 'w').close()
open(os.path.join(basedir, "filter.d", "testfilter1.conf"), 'w').close()
jailfd = open(os.path.join(basedir, "jail.conf"), 'w')
jailfd.write("""
[testjail1]
enabled = true
filter = testfilter1
logpath_ = string1
string2
action = testaction1[logpath=%(logpath_)s]
testaction2
testaction3[logpath=%(logpath_)s]
""")
jailfd.close()
jails = JailsReader(basedir=basedir)
self.assertTrue(jails.read())
self.assertTrue(jails.getOptions())
comm_commands = jails.convert(allow_no_files=True)
self.assertTrue(
['set', 'testjail1', 'action', 'testaction1', 'logpath', 'string1\nstring2'] in comm_commands)
self.assertTrue(
['set', 'testjail1', 'addaction', 'testaction2'] in comm_commands)
self.assertTrue(
['set', 'testjail1', 'action', 'testaction3', 'logpath', 'string1\nstring2'] in comm_commands)
shutil.rmtree(basedir)

0 comments on commit abc0756

Please sign in to comment.