from twisted.internet import protocol, reactor
from twisted.python import log
import sys
import api
import logwatch_config as config
class TailProcessProtocol (protocol.ProcessProtocol) :
def __init__ (self, module, name, filters) :
self.module = module
self.name = name
self.filters = filters
self.buf = ""
def errReceived (self, data) :
self.module.error("tail for %s: %s" % (self.name, data))
def outReceived (self, data) :
data = self.buf + data
while "\n" in data :
line, data = data.split("\n", 1)
log.msg("Matching line `%s'..." % line)
for filter in self.filters :
out = filter.test(line)
if out :
log.msg("\t%s: %s" % (filter.event_type, out))
self.module.sendEvent(filter.event_type, out)
self.buf = data
def processEnded (self, reason) :
msg = "tail process for %s quit: %s" % (self.name, reason.getErrorMessage())
log.err(msg)
self.module.error(msg)
class LogWatchModule (api.Module) :
name = "logs"
version = 0x0001
event_types = [
"error",
"sudo",
"ssh",
]
log_files = config.log_files
log_objs = None
def handleConnect (self) :
log.msg("Spawning tail processes...")
self.log_objs = dict()
for name, file, filters in self.log_files :
log.msg("\t%s - %s..." % (name, file))
p = self.log_objs[name] = TailProcessProtocol(self, name, filters)
reactor.spawnProcess(p, "/usr/bin/tail", ["tail", "-n0", "--follow=name", file])
def error (self, msg) :
self.sendEvent("error", msg)
if __name__ == '__main__' :
LogWatchModule().run()