X-Git-Url: https://code.delx.au/pymsnt/blobdiff_plain/c82ae883c8c1a236e80013c734fb56725b3c535c..89a1109f8981cd7ff33f9ce2d974b712c9c4bb6c:/src/debug.py diff --git a/src/debug.py b/src/debug.py index d284ee9..74c52cb 100644 --- a/src/debug.py +++ b/src/debug.py @@ -1,76 +1,120 @@ -# Copyright 2004 James Bunton +# Copyright 2004-2005 James Bunton # Licensed for distribution under the GPL version 2, check COPYING for details -import os -import sys -import config -import utils -import time - -""" A simple logging module. Use as follows. - -> import debug -> debug.log("text string") - -If debugging is enabled then the data will be dumped to a file -or the screen (whichever the user chose) -""" +from twisted.python import log +import sys, time -file = None -rollingStack = None -if(config.debugSmart): - rollingStack = utils.RollingStack(100) +import config -def reopenFile(first=False): - global file - if(file or first): - if(file): file.close() +def observer(eventDict): + try: + observer2(eventDict) + except Exception, e: + printf("CRITICAL: Traceback in debug.observer2 - " + str(e)) + + +def observer2(eventDict): + edm = eventDict['message'] + if isinstance(edm, LogEvent): + if edm.category == INFO and config._debugLevel < 3: + return + if (edm.category == WARN or edm.category == ERROR) and config._debugLevel < 2: + return + text = str(edm) + elif edm: + if config._debugLevel < 3: return + text = ' '.join(map(str, edm)) + else: + if eventDict['isError'] and eventDict.has_key('failure'): + if config._debugLevel < 1: return + text = eventDict['failure'].getTraceback() + elif eventDict.has_key('format'): + if config._debugLevel < 3: return + text = eventDict['format'] % eventDict + else: + return + + # Now log it! + timeStr = time.strftime("[%Y-%m-%d %H:%M:%S]", time.localtime(eventDict['time'])) + text = text.replace("\n", "\n\t") + global debugFile + debugFile.write("%s %s\n" % (timeStr, text)) + debugFile.flush() + +def printf(text): + sys.__stdout__.write(text + "\n") + sys.__stdout__.flush() + + +debugFile = None +def reloadConfig(): + global debugFile + if debugFile: + debugFile.close() + + try: + config._debugLevel = int(config.debugLevel.strip()) + except ValueError: + config._debugLevel = 0 + config.debugLevel = "0" + + if config._debugLevel > 0: + if len(config.debugFile) > 0: + try: + debugFile = open(config.debugFile, "a") + log.msg("Reopened log file.") + except IOError: + log.discardLogs() # Give up + debugFile = sys.__stdout__ + return + else: + debugFile = sys.__stdout__ try: - file = open(utils.doPath(config.debugLog), 'a') - except: - print "Error opening debug log file. Exiting..." - os.abort() - - -def flushDebugSmart(): - global rollingStack - if(config.debugSmart): - file.write(rollingStack.grabAll()) - rollingStack.flush() - file.flush() - - -if(config.debugOn): - if(len(config.debugLog) > 0): - reopenFile(True) - def log(data, wtime=True): - text = "" - if(wtime): - text += time.strftime("%D - %H:%M:%S - ") - text += utils.latin1(data) + "\n" - if(config.debugSmart): - rollingStack.push(text) - else: - file.write(text) - file.flush() + log.removeObserver(observer) + except ValueError: + pass + log.startLoggingWithObserver(observer) else: - def log(data, wtime=True): - if(wtime): - print time.strftime("%D - %H:%M:%S - "), - print utils.latin1(data) - sys.stdout.flush() - log("Debug logging enabled.") -else: - def log(data): - pass - - -def write(data): - # So that I can pass this module to twisted.python.failure.Failure.printDetailedTraceback() as a file - data = data.rstrip() - log(data) + log.discardLogs() + +class INFO : pass +class WARN : pass +class ERROR: pass + +class LogEvent: + def __init__(self, category=INFO, ident="", msg="", log=True): + self.category, self.ident, self.msg = category, ident, msg + frame = sys._getframe(1) + # Get the class name + s = str(frame.f_locals.get("self", frame.f_code.co_filename)) + self.klass = s[s.find(".")+1:s.find(" ")] + self.method = frame.f_code.co_name + self.args = frame.f_locals + if log: + self.log() + + def __str__(self): + args = {} + for key in self.args.keys(): + if key == "self": + args["self"] = "instance" + continue + val = self.args[key] + args[key] = val + try: + if len(val) > 128: + args[key] = "Oversize arg" + except: + # If its not an object with length, assume that it can't be too big. Hope that's a good assumption. + pass + category = str(self.category).split(".")[1] + return "%s :: %s :: %s :: %s :: %s :: %s" % (category, str(self.ident), self.msg, self.method, str(self.klass), str(args)) + + def log(self): + log.msg(self) +