← Back to team overview

duplicity-team team mailing list archive

[Merge] lp:~mterry/duplicity/levelName into lp:duplicity

 

Michael Terry has proposed merging lp:~mterry/duplicity/levelName into lp:duplicity.

Requested reviews:
  duplicity-team (duplicity-team)

For more details, see:
https://code.launchpad.net/~mterry/duplicity/levelName/+merge/62226

I found this while messing with the Ubuntu One backend, because apparently one of the ubuntuone modules sets a log level using logging.addLevelName (as duplicity does).

While that's probably not something the ubuntuone module should be doing, reading the documentation for the logging module (http://docs.python.org/library/logging.html), I realized that any old piece of code anywhere could add level names, overriding ours (as ubuntuone did).

That's not wise, so I adjusted the logging code to be more careful of that and use our own mapping always.
-- 
https://code.launchpad.net/~mterry/duplicity/levelName/+merge/62226
Your team duplicity-team is requested to review the proposed merge of lp:~mterry/duplicity/levelName into lp:duplicity.
=== modified file 'duplicity/log.py'
--- duplicity/log.py	2011-03-06 15:12:33 +0000
+++ duplicity/log.py	2011-05-25 01:32:27 +0000
@@ -3,6 +3,7 @@
 # Copyright 2002 Ben Escoto <ben@xxxxxxxxxxx>
 # Copyright 2007 Kenneth Loafman <kenneth@xxxxxxxxxxx>
 # Copyright 2008 Michael Terry <mike@xxxxxxxxxxx>
+# Copyright 2011 Canonical Ltd
 #
 # This file is part of duplicity.
 #
@@ -46,6 +47,14 @@
        more severe"""
     return DupToLoggerLevel(verb)
 
+def LevelName(level):
+    level = LoggerToDupLevel(level)
+    if   level >= 9: return "DEBUG"
+    elif level >= 5: return "INFO"
+    elif level >= 3: return "NOTICE"
+    elif level >= 1: return "WARNING"
+    else:            return "ERROR"
+
 def Log(s, verb_level, code=1, extra=None, force_print=False):
     """Write s to stderr if verbosity level low enough"""
     global _logger
@@ -201,6 +210,7 @@
         global _logger
         logging.LogRecord.__init__(self, *args, **kwargs)
         self.controlLine = controlLine
+        self.levelName = LevelName(args[1]) # args[1] is lvl
 
 class DupLogger(logging.Logger):
     """Custom logger that creates special code-bearing records"""
@@ -229,18 +239,6 @@
     logging.setLoggerClass(DupLogger)
     _logger = logging.getLogger("duplicity")
 
-    # Set up our special level names
-    logging.addLevelName(DupToLoggerLevel(0), "ERROR")
-    logging.addLevelName(DupToLoggerLevel(1), "WARNING")
-    logging.addLevelName(DupToLoggerLevel(2), "WARNING")
-    logging.addLevelName(DupToLoggerLevel(3), "NOTICE")
-    logging.addLevelName(DupToLoggerLevel(4), "NOTICE")
-    logging.addLevelName(DupToLoggerLevel(5), "INFO")
-    logging.addLevelName(DupToLoggerLevel(6), "INFO")
-    logging.addLevelName(DupToLoggerLevel(7), "INFO")
-    logging.addLevelName(DupToLoggerLevel(8), "INFO")
-    logging.addLevelName(DupToLoggerLevel(9), "DEBUG")
-
     # Default verbosity allows notices and above
     setverbosity(NOTICE)
 
@@ -258,7 +256,11 @@
        processes."""
     def __init__(self):
         # 'message' will be appended by format()
-        logging.Formatter.__init__(self, "%(levelname)s %(controlLine)s")
+        # Note that we use our own, custom-created 'levelName' instead of the
+        # standard 'levelname'.  This is because the standard 'levelname' can
+        # be adjusted by any library anywhere in our stack without us knowing.
+        # But we control 'levelName'.
+        logging.Formatter.__init__(self, "%(levelName)s %(controlLine)s")
 
     def format(self, record):
         s = logging.Formatter.format(self, record)


Follow ups