summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorArthur de Jong <arthur@arthurdejong.org>2013-02-23 17:02:14 +0100
committerArthur de Jong <arthur@arthurdejong.org>2013-02-23 17:25:53 +0100
commitc75599db1ab14c9a4e502ff767a6f588f74f03be (patch)
tree85520ece5e88bc664a8df90cd7cfbe5ade6ef221
parentefca5ca5599bbad982ac4f259047c7f07337951a (diff)
handle the log configuration option in pynslcd
-rw-r--r--pynslcd/cfg.py19
-rwxr-xr-xpynslcd/pynslcd.py33
2 files changed, 37 insertions, 15 deletions
diff --git a/pynslcd/cfg.py b/pynslcd/cfg.py
index 132cf91..ab6668b 100644
--- a/pynslcd/cfg.py
+++ b/pynslcd/cfg.py
@@ -33,6 +33,8 @@ threads = 5
uid = None
# the group id nslcd should be run as
gid = None
+# the configured loggers
+logs = []
# the LDAP server to use
# FIXME: support multiple servers and have a fail-over mechanism
@@ -79,7 +81,6 @@ tls_ciphers = None
tls_cert = None
tls_key = None
-
# other options
pagesize = 0
nss_initgroups_ignoreusers = set()
@@ -93,6 +94,12 @@ pam_password_prohibit_message = None
_boolean_options = {'on': True, 'yes': True, 'true': True, '1': True,
'off': False, 'no': False, 'false': False, '0': False}
+# allowed log levels (we log notice which is unsupported in Python to warning)
+_log_levels = {'crit': logging.CRITICAL, 'error': logging.ERROR,
+ 'err': logging.ERROR, 'warning': logging.WARNING,
+ 'notice': logging.WARNING, 'info': logging.INFO,
+ 'debug': logging.DEBUG, 'none': logging.INFO}
+
# allowed values for scope option
if not hasattr(ldap, 'SCOPE_CHILDREN') and ldap.VENDOR_VERSION >= 20400:
ldap.SCOPE_CHILDREN = 3 # OpenLDAP extension
@@ -187,6 +194,13 @@ def read(filename):
if m:
globals()[m.group('keyword').lower()] = m.group('value')
continue
+ # log <SCHEME> [<LEVEL>]
+ m = re.match('log\s+(?P<scheme>syslog|/\S*)(\s+(?P<level>%s))?' %
+ '|'.join(_log_levels.keys()),
+ line, re.IGNORECASE)
+ if m:
+ logs.append((m.group('scheme'), _log_levels[str(m.group('level')).lower()]))
+ continue
# uri <URI>
m = re.match('uri\s+(?P<uri>\S+)', line, re.IGNORECASE)
if m:
@@ -299,6 +313,9 @@ def read(filename):
continue
# unrecognised line
raise ParseError(filename, lineno, 'error parsing line %r' % line)
+ # if logging is not configured, default to syslog
+ if not logs:
+ log.append('syslog', logging.INFO)
# dump config (debugging code)
for k, v in globals().items():
if not k.startswith('_'):
diff --git a/pynslcd/pynslcd.py b/pynslcd/pynslcd.py
index f06ac11..bdd3a96 100755
--- a/pynslcd/pynslcd.py
+++ b/pynslcd/pynslcd.py
@@ -2,7 +2,7 @@
# pynslcd.py - main daemon module
#
-# Copyright (C) 2010, 2011, 2012 Arthur de Jong
+# Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong
#
# This library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Lesser General Public
@@ -50,10 +50,8 @@ checkonly = False
class MyFormatter(logging.Formatter):
def format(self, record):
- msg = super(MyFormatter, self).format(record)
- if record.levelno == logging.DEBUG:
- msg = 'DEBUG: %s' % msg
- return msg
+ record.prefix = 'DEBUG: ' if record.levelno == logging.DEBUG else ''
+ return super(MyFormatter, self).format(record)
class MySysLogHandler(logging.Handler):
@@ -78,11 +76,8 @@ class MySysLogHandler(logging.Handler):
# configure logging
-formatter = MyFormatter('%(message)s')
stderrhandler = logging.StreamHandler(sys.stderr)
-stderrhandler.setFormatter(formatter)
-sysloghandler = MySysLogHandler()
-sysloghandler.setFormatter(formatter)
+stderrhandler.setFormatter(MyFormatter('pynslcd: %(prefix)s%(message)s'))
logging.getLogger().addHandler(stderrhandler)
logging.getLogger().setLevel(logging.INFO)
@@ -91,7 +86,7 @@ def display_version(fp):
fp.write('%(PACKAGE_STRING)s\n'
'Written by Arthur de Jong.\n'
'\n'
- 'Copyright (C) 2010-2012 Arthur de Jong\n'
+ 'Copyright (C) 2010-2013 Arthur de Jong\n'
'This is free software; see the source for copying conditions. There is NO\n'
'warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n'
% {'PACKAGE_STRING': constants.PACKAGE_STRING, })
@@ -320,11 +315,21 @@ if __name__ == '__main__':
})
# start daemon
with daemon:
- # start normal logging to syslog
- if not debugging:
- logging.getLogger().addHandler(sysloghandler)
- logging.info('version %s starting', constants.VERSION)
try:
+ # start normal logging as configured
+ if not debugging:
+ for method, level in cfg.logs:
+ if method == 'syslog':
+ handler = MySysLogHandler()
+ handler.setFormatter(MyFormatter('%(prefix)s%(message)s'))
+ else:
+ handler = logging.FileHandler(method, encoding='utf-8')
+ handler.setFormatter(MyFormatter('%(asctime)s %(prefix)s%(message)s'))
+ handler.setLevel(level)
+ logging.getLogger().addHandler(handler)
+ logging.getLogger().setLevel(min(level for method, level in cfg.logs))
+ logging.getLogger().removeHandler(stderrhandler)
+ logging.info('version %s starting', constants.VERSION)
# create socket
nslcd_serversocket = create_socket()
# load supplementary groups