--- a/bin/pvl.verkko-syslog Thu Jan 03 00:56:28 2013 +0200
+++ b/bin/pvl.verkko-syslog Thu Jan 03 13:04:51 2013 +0200
@@ -31,15 +31,8 @@
# options
parser.add_option_group(pvl.args.parser(parser))
-
- ## syslog
parser.add_option_group(pvl.syslog.args.parser(parser))
- # defaults
- parser.set_defaults(
-
- )
-
# parse
options, args = parser.parse_args(argv[1:])
@@ -48,6 +41,15 @@
return options, args
+# prototype
+import pvl.syslog.rule
+
+sudo = pvl.syslog.rule.SyslogRule('sudo',
+ program = 'sudo',
+ pattern = r'\s*(?P<login>\S+) : TTY=(?P<tty>\S+) ; PWD=(?P<pwd>.+?) ; USER=(?P<user>\S+) ; (?:ENV=(?P<env>.+?) ; )?COMMAND=(?P<command>.*)',
+ format = "{login}:{tty} - {user}@{host}:{pwd} - {env}{command!r}",
+)
+
def main (argv) :
options, args = parse_options(argv)
@@ -56,7 +58,7 @@
log.info("Start processing syslog messages...")
for item in syslog.loop() :
- print item
+ print sudo.apply(item)
# done
log.info("Exiting...")
--- a/pvl/syslog/filter.py Thu Jan 03 00:56:28 2013 +0200
+++ b/pvl/syslog/filter.py Thu Jan 03 13:04:51 2013 +0200
@@ -2,14 +2,16 @@
class SyslogFilter (object) :
"""
- Filter syslog messages.
+ Match syslog messages.
+
+ XXX: do we need more than just prog?
"""
def __init__ (self, prog=None) :
"""
prog - match tag (process name)
"""
-
+
self.prog = prog
def match_prog (self, prog) :
@@ -17,6 +19,9 @@
Match given prog?
"""
+ if not self.prog :
+ return
+
# normalize
prog = prog.lower()
@@ -41,12 +46,26 @@
Match given item?
"""
- if self.prog and not self.match_prog(item['prog']) :
- log.debug("prog: %s: %r", self.prog, item['prog'])
+ for attr, func in (
+ ( 'prog', self.match_prog),
+ ) :
+ match = func(item[attr])
+ if match :
+ continue
+
+ elif match is None :
+ pass
+
+ else :
+ break
+
+ # ok
+ if match is None :
+ # XXX: empty filter!?
+ return True
else :
- # ok
- return True
+ return match
def __call__ (self, items) :
for item in items:
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/pvl/syslog/rule.py Thu Jan 03 13:04:51 2013 +0200
@@ -0,0 +1,54 @@
+from pvl.syslog.filter import SyslogFilter
+
+import re
+
+import logging; log = logging.getLogger('pvl.syslog.rule')
+
+class SyslogRule (object) :
+ """
+ A rule matches syslog lines, and formats them.
+
+ tag - apply given tag to matches
+ """
+
+ def __init__ (self, tag, program=None, pattern=None, format=None, flags=0) :
+ pattern = re.compile(pattern, flags)
+
+ self.filter = SyslogFilter(prog=program)
+
+ self.tag = tag
+ self.format = format
+ self.pattern = pattern
+
+ def apply (self, item) :
+ """
+ Apply rule against given item.
+ """
+
+ # filter
+ match = self.filter.filter(item)
+
+ log.debug("filter: %s", match)
+
+ if not match :
+ # ignore
+ return None
+
+ if self.pattern :
+ match = self.pattern.match(item['msg'])
+
+ if not match :
+ # ignore
+ return None
+
+ # apply
+ item.update(match.groupdict())
+
+ if self.tag is False :
+ # drop
+ return False
+
+ if self.format :
+ # return
+ return self.tag, self.format.format(**item)
+