diff --git a/lib/bb/ui/knotty.py b/lib/bb/ui/knotty.py index 3799018..70d7df5 100644 --- a/lib/bb/ui/knotty.py +++ b/lib/bb/ui/knotty.py @@ -31,11 +31,56 @@ import time import fcntl import struct import copy +import datetime from bb.ui import uihelper logger = logging.getLogger("BitBake") interactive = sys.stdout.isatty() +class TeamCityLogFormatter(bb.msg.BBLogFormatter): + """Formatter that outputs TeamCity compatible messages""" + + levelnames = { + # TeamCity: NORMAL, WARNING, FAILURE, ERROR + bb.msg.BBLogFormatter.DEBUG3 : 'NORMAL', + bb.msg.BBLogFormatter.DEBUG2 : 'NORMAL', + bb.msg.BBLogFormatter.DEBUG : 'NORMAL', + bb.msg.BBLogFormatter.VERBOSE : 'NORMAL', + bb.msg.BBLogFormatter.NOTE : 'NORMAL', + bb.msg.BBLogFormatter.PLAIN : 'NORMAL', + bb.msg.BBLogFormatter.WARNING : 'WARNING', + bb.msg.BBLogFormatter.ERROR : 'ERROR', + bb.msg.BBLogFormatter.CRITICAL: 'ERROR', + } + + quote = {"'": "|'", "|": "||", "\n": "|n", "\r": "|r", ']': '|]'} + + def escapeValue(self, value): + return "".join([self.quote.get(x, x) for x in value]) + + def getLevelName(self, levelno): + try: + return self.levelnames[levelno] + except KeyError: + self.levelnames[levelno] = value = 'FAILURE' + return value + + def format(self, record): + record.levelname = self.getLevelName(record.levelno) + + msg = "timestamp='%s'" % datetime.datetime.now().isoformat()[:-3] + msg += " text='%s'" % self.escapeValue(record.getMessage()) + + if hasattr(record, 'bb_exc_info'): + etype, value, tb = record.bb_exc_info + formatted = bb.exceptions.format_exception(etype, value, tb, limit=5) + msg += " errorDetails='%s'" % self.escapeValue(''.join(formatted)) + msg += " status='ERROR'" + elif record.levelname != "NORMAL": + msg += " status='%s'" % record.levelname + + return "##teamcity[message " + msg + "]" + class BBProgress(progressbar.ProgressBar): def __init__(self, msg, maxval): self.msg = msg @@ -228,7 +273,10 @@ def main(server, eventHandler, tf = TerminalFilter): helper = uihelper.BBUIHelper() console = logging.StreamHandler(sys.stdout) - format = bb.msg.BBLogFormatter("%(levelname)s: %(message)s") + if "TEAMCITY_VERSION" in os.environ: + format = TeamCityLogFormatter("%(message)s") + else: + format = bb.msg.BBLogFormatter("%(levelname)s: %(message)s") bb.msg.addDefaultlogFilter(console) console.setFormatter(format) logger.addHandler(console)