pvl/syslog/args.py
author Tero Marttila <tero.marttila@aalto.fi>
Mon, 28 Jul 2014 13:32:41 +0300
changeset 35 4c7905e1cad7
parent 2 5a8a32cbc944
permissions -rw-r--r--
version 0.5.1: bugfix for working around conflicting -c/--config options
import optparse, sys

from pvl.syslog.parser import SyslogParser
from pvl.syslog.filter import SyslogFilter
from pvl.syslog.syslog import SyslogSource
from pvl.syslog import fifo, tail, file

# XXX: use optparse parser.error()?
import logging; log = logging.getLogger('pvl.syslog.args')

def parser (parser, prog=None) :
    """
        Optparse option group

            prog        - filter to only process lines from given process
    """
    
    syslog = optparse.OptionGroup(parser, 'Syslog collector')

    syslog.add_option('--syslog-fifo',          metavar='PATH',
            help="Read syslog messages from given fifo")

    syslog.add_option('--syslog-file',          metavar='FILE',
            help="Read syslog messages from given file")

    syslog.add_option('--syslog-tail',          metavar='FILE',
            help="Continuously poll syslog messages given file")

    syslog.add_option('--syslog-stdin',         action='store_true',
            help="Read syslog messages from stdin")

    syslog.add_option('--syslog-raw',           action='store_true',
            help="Parse raw syslog lines without timestamp/etc")

    syslog.add_option('--syslog-facility',      metavar='FACILITY',
            help="Set/filter by given facility")

    syslog.add_option('--syslog-severity',      metavar='SEVERITY',
            help="Set given facility")

    syslog.add_option('--syslog-prog',          metavar='PROG',     default=prog,
            help="Filter by given prog: %default")

    return syslog

def apply (options, optional=False) :
    """
        Handle options, returning a SyslogSource, if any.

        May log.error/sys.exit
    """
    
    # XXX: this belongs in pvl.syslog.source
    if options.syslog_fifo :
        # fifo pipe
        source = fifo.Fifo(options.syslog_fifo)
        poll = True # select(source)

    elif options.syslog_tail :
        # tail file
        source = tail.Tail(options.syslog_tail, skip=True)
        poll = tail.Tail.POLL # select(float)

    elif options.syslog_file :
        # read file
        source = file.File(open(options.syslog_file))
        poll = False # do not loop, just read up to EOF

    elif options.syslog_stdin :
        # read pipe
        source = fifo.Pipe.file(sys.stdin) # puts stdin into non-blocking mode
        poll = True # select(source)

    elif optional :
        return None

    else :
        # from stdin
        if sys.stdin.isatty() :
            log.warning("Reading syslog messages from TTY?")
        
        source = file.File(sys.stdin)
        poll = False # XXX: tty vs pipe vs file? False -> just block
    
    # options
    parser = SyslogParser(
        raw         = options.syslog_raw,
        facility    = options.syslog_facility,
        severity    = options.syslog_severity,
    )
    
    # TODO: filter optional
    filter = SyslogFilter.build(
        # glob pattern
        prog        = options.syslog_prog,
        facility    = options.syslog_facility,
        #severity   = options.sylog_severity,   # XXX: match as greater-than?
    )

    # polling
    return SyslogSource(source, parser, filter, poll)