Drucken auf STDOUT und Logfile während ANSI-Farbcodes zu entfernen
-
04-10-2019 - |
Frage
Ich habe folgende Funktionen für die LCD-Display-Meldungen Einfärben:
def error(string):
return '\033[31;1m' + string + '\033[0m'
def standout(string):
return '\033[34;1m' + string + '\033[0m'
Ich benutze sie wie folgt:
print error('There was a problem with the program')
print "This is normal " + standout("and this stands out")
Ich mag die Ausgabe in eine Datei protokollieren (zusätzlich zu STDOUT), ohne die Farbcodes ANSI, hoffentlich ohne einen zweiten hinzufügen zu müssen Leitung zu jeder print
Anweisung „Anmeldung“.
Der Grund dafür ist, dass, wenn Sie einfach python program.py > out
dann die Datei out
den ANSI-Farbcodes haben wird, die schrecklich aussehen, wenn Sie in einem Texteditor öffnen.
Jede Beratung?
Lösung
Die sys.stdout.isatty
Funktion könnte in der Lage sein, zu helfen:
from sys import stdout
def error(string, is_tty=stdout.isatty()):
return ('\033[31;1m' + string + '\033[0m') if is_tty else string
def standout(string, is_tty=stdout.isatty()):
return ('\033[34;1m' + string + '\033[0m') if is_tty else string
Das ist eigentlich eine der wenige Anwendungen ich denken kann ein Standard-Argument zu verwenden, das nicht auf None
gesetzt, weil Standardargumente bei der Kompilierung in Python ausgewertet werden, anstatt zur Laufzeit wie in C ++ ...
Auch kann das Verhalten ausdrücklich außer Kraft gesetzt werden, wenn Sie wirklich brauchen, auch wenn das nicht Sie stdout selbst manipulieren nicht lassen, wenn es umgeleitet wird. Gibt es einen Grund, warum Sie nicht die logging
Modul (vielleicht haben Sie nicht wissen es)?
Andere Tipps
Wenn Sie sowohl an das Terminal und in eine Protokolldatei drucken möchten, dann würde ich vorschlagen, die Logging-Modul. Sie können sogar eine benutzerdefinierte Formatter definieren, so die Protokollierung in die Datei die Terminal-Codes löschen können:
import optparse
import logging
def error(string):
return '\033[31;1m' + string + '\033[0m'
def standout(string):
return '\033[34;1m' + string + '\033[0m'
def plain(string):
return string.replace('\033[34;1m','').replace('\033[31;1m','').replace('\033[0m','')
if __name__=='__main__':
logging.basicConfig(level=logging.DEBUG,
format='%(message)s',
filemode='w')
logger=logging.getLogger(__name__)
def parse_options():
usage = 'usage: %prog [Options]'
parser = optparse.OptionParser()
parser.add_option('-l', '--logfile', dest='logfile',
help='use log file')
opt,args = parser.parse_args()
return opt,args
opt,args=parse_options()
if opt.logfile:
class MyFormatter(logging.Formatter):
def format(self,record):
return plain(record.msg)
fh = logging.FileHandler(opt.logfile)
fh.setLevel(logging.INFO)
formatter = MyFormatter('%(message)s')
fh.setFormatter(formatter)
logging.getLogger('').addHandler(fh)
logger.info(error('There was a problem with the program'))
logger.info("This is normal " + standout("and this stands out"))
test.py
druckt nur an das Terminal.
test.py -l test.out
druckt sowohl das Terminal und in die Datei test.out
.
In allen Fällen wird der Text an das Terminal hat Farbcodes, während der Protokollierung keine hat.
unubtu Antwort unten ist groß, aber ich denke, MyFormatter eine geringfügige Änderung muss im Format () -Methode zur Durchsetzung der Formatierung
class MyFormatter(logging.Formatter):
def format(self,record):
msg = super(MyFormatter, self).format(record)
return plain(msg)