107 lines
3.6 KiB
Python
107 lines
3.6 KiB
Python
# -*- test-case-name: twisted.python.test.test_syslog -*-
|
|
# Copyright (c) Twisted Matrix Laboratories.
|
|
# See LICENSE for details.
|
|
|
|
"""
|
|
Classes and utility functions for integrating Twisted and syslog.
|
|
|
|
You probably want to call L{startLogging}.
|
|
"""
|
|
|
|
syslog = __import__('syslog')
|
|
|
|
from twisted.python import log
|
|
|
|
# These defaults come from the Python syslog docs.
|
|
DEFAULT_OPTIONS = 0
|
|
DEFAULT_FACILITY = syslog.LOG_USER
|
|
|
|
|
|
|
|
class SyslogObserver:
|
|
"""
|
|
A log observer for logging to syslog.
|
|
|
|
See L{twisted.python.log} for context.
|
|
|
|
This logObserver will automatically use LOG_ALERT priority for logged
|
|
failures (such as from C{log.err()}), but you can use any priority and
|
|
facility by setting the 'C{syslogPriority}' and 'C{syslogFacility}' keys in
|
|
the event dict.
|
|
"""
|
|
openlog = syslog.openlog
|
|
syslog = syslog.syslog
|
|
|
|
def __init__(self, prefix, options=DEFAULT_OPTIONS,
|
|
facility=DEFAULT_FACILITY):
|
|
"""
|
|
@type prefix: C{str}
|
|
@param prefix: The syslog prefix to use.
|
|
|
|
@type options: C{int}
|
|
@param options: A bitvector represented as an integer of the syslog
|
|
options to use.
|
|
|
|
@type facility: C{int}
|
|
@param facility: An indication to the syslog daemon of what sort of
|
|
program this is (essentially, an additional arbitrary metadata
|
|
classification for messages sent to syslog by this observer).
|
|
"""
|
|
self.openlog(prefix, options, facility)
|
|
|
|
|
|
def emit(self, eventDict):
|
|
"""
|
|
Send a message event to the I{syslog}.
|
|
|
|
@param eventDict: The event to send. If it has no C{'message'} key, it
|
|
will be ignored. Otherwise, if it has C{'syslogPriority'} and/or
|
|
C{'syslogFacility'} keys, these will be used as the syslog priority
|
|
and facility. If it has no C{'syslogPriority'} key but a true
|
|
value for the C{'isError'} key, the B{LOG_ALERT} priority will be
|
|
used; if it has a false value for C{'isError'}, B{LOG_INFO} will be
|
|
used. If the C{'message'} key is multiline, each line will be sent
|
|
to the syslog separately.
|
|
"""
|
|
# Figure out what the message-text is.
|
|
text = log.textFromEventDict(eventDict)
|
|
if text is None:
|
|
return
|
|
|
|
# Figure out what syslog parameters we might need to use.
|
|
priority = syslog.LOG_INFO
|
|
facility = 0
|
|
if eventDict['isError']:
|
|
priority = syslog.LOG_ALERT
|
|
if 'syslogPriority' in eventDict:
|
|
priority = int(eventDict['syslogPriority'])
|
|
if 'syslogFacility' in eventDict:
|
|
facility = int(eventDict['syslogFacility'])
|
|
|
|
# Break the message up into lines and send them.
|
|
lines = text.split('\n')
|
|
while lines[-1:] == ['']:
|
|
lines.pop()
|
|
|
|
firstLine = True
|
|
for line in lines:
|
|
if firstLine:
|
|
firstLine = False
|
|
else:
|
|
line = '\t' + line
|
|
self.syslog(priority | facility,
|
|
'[%s] %s' % (eventDict['system'], line))
|
|
|
|
|
|
|
|
def startLogging(prefix='Twisted', options=DEFAULT_OPTIONS,
|
|
facility=DEFAULT_FACILITY, setStdout=1):
|
|
"""
|
|
Send all Twisted logging output to syslog from now on.
|
|
|
|
The prefix, options and facility arguments are passed to
|
|
C{syslog.openlog()}, see the Python syslog documentation for details. For
|
|
other parameters, see L{twisted.python.log.startLoggingWithObserver}.
|
|
"""
|
|
obs = SyslogObserver(prefix, options, facility)
|
|
log.startLoggingWithObserver(obs.emit, setStdout=setStdout)
|