Wenn ich einen Befehl über ein Terminal ausführe, das eine farbige Ausgabe druckt (z. B. ls
oder gcc
), wird die farbige Ausgabe gedruckt. Nach meinem Verständnis gibt der Prozess tatsächlich ANSI-Escape-Codes aus , und das Terminal formatiert die Farbe.
Wenn ich jedoch denselben Befehl von einem anderen Prozess (z. B. einer benutzerdefinierten C-Anwendung) ausführe und die Ausgabe auf die Ausgabe der Anwendung umleitung, bleiben diese Farben nicht erhalten.
Wie entscheidet ein Programm, ob Text im Farbformat ausgegeben wird oder nicht? Gibt es eine Umgebungsvariable?
Ja. Es ist die
TERM
Umgebungsvariable. Dies liegt daran, dass im Rahmen des Entscheidungsprozesses mehrere Dinge verwendet werden.Eine Verallgemeinerung ist hier schwierig, da sich nicht alle Programme auf ein einziges Entscheidungsflussdiagramm einigen. In der Tat ist GNU
grep
, wie in M. Kitts Antwort erwähnt, ein gutes Beispiel für einen Ausreißer, der einen etwas ungewöhnlichen Entscheidungsprozess mit unerwarteten Ergebnissen anwendet. Ganz allgemein gesagt:isatty()
.TERM
Umgebungsvariable muss vorhanden sein und ihr Wert muss mit einem Datenbankdatensatz übereinstimmen.TERMCAP
Umgebungsvariablen angegeben werden. Daher gibt es bei einigen Implementierungen eine zweite Umgebungsvariable.max_colors
Feld in terminfo. Es ist nicht für Terminaltypen festgelegt, die nicht über Farbfunktionen verfügen. In der Tat gibt es eine Terminfo-Konvention, die besagt, dass für jeden farbbaren Terminaltyp ein weiterer Datensatz mit-m
oder-mono
an den Namen angehängt wird, der keine Farbfähigkeit angibt.set_a_foreground
undset_a_background
Felder in terminfo.Es ist ein bisschen komplexer als nur zu überprüfen
isatty()
. Es wird durch verschiedene Dinge noch komplizierter:isatty()
Prüfung außer Kraft setzen , sodass das Programm immer oder nie davon ausgeht, dass es ein (färbbares) Terminal als Ausgabe hat. Zum Beispiel:ls
hat die--color
Befehlszeilenoption.ls
untersucht die UmgebungsvariablenCLICOLOR
(Abwesenheit bedeutet nie ) undCLICOLOR_FORCE
(Anwesenheit bedeutet immer ) und bietet auch die-G
Befehlszeilenoption an.TERM
.Wie bereits erwähnt,
grep
weist GNU tatsächlich einige dieser zusätzlichen Komplexitäten auf. Es konsultiert nicht termcap / terminfo, verkabelt die auszugebenden Steuersequenzen und verkabelt eine Antwort auf dieTERM
Umgebungsvariable.Der Linux / Unix-Port hat diesen Code , der die Einfärbung nur ermöglicht, wenn die
TERM
Umgebungsvariable existiert und ihr Wert nicht mit dem festverdrahteten Namen übereinstimmtdumb
:Selbst wenn dies der Fall
TERM
istxterm-mono
, wird GNUgrep
beschließen, Farben auszugeben, obwohl andere Programme diesvim
nicht tun.Der Win32-Port hat diesen Code , der die Einfärbung entweder dann aktiviert, wenn die
TERM
Umgebungsvariable nicht vorhanden ist oder wenn sie vorhanden ist und ihr Wert nicht mit dem festverdrahteten Namen übereinstimmtdumb
:GNU
grep
Probleme mit Farbegrep
Die Färbung von GNU ist eigentlich berüchtigt. Da die Terminal-Ausgabe nicht ordnungsgemäß erstellt wird, sondern nur einige festverdrahtete Steuersequenzen an verschiedenen Stellen der Ausgabe ausgeführt werden, in der vergeblichen Hoffnung, dass dies ausreichend ist, wird unter bestimmten Umständen tatsächlich eine falsche Ausgabe angezeigt.Unter diesen Umständen muss etwas am rechten Rand des Terminals eingefärbt werden. Programme, die Terminalausgaben korrekt ausführen, müssen automatische rechte Ränder berücksichtigen. Zusätzlich zu der geringen Möglichkeit, dass das Terminal möglicherweise nicht über sie verfügt (dh das
auto_right_margin
Feld in terminfo), folgt das Verhalten von Terminals, die über automatische rechte Ränder verfügen, häufig dem DEC VT-Präzedenzfall des Zeilenumbruchs . GNUgrep
berücksichtigt dies nicht und erwartet naiv einen sofortigen Zeilenumbruch , und seine farbige Ausgabe geht schief.Farbausgabe ist keine einfache Sache.
Weitere Lektüre
grep --color
msgstr " zeigt nicht die richtige Ausgabe ". xterm FAQ . Unsichtbare Insel.quelle
$TERM
erklärt das nicht. (Ihre Antwort ist im Allgemeinen interessant, aber ich glaube nicht, dass sie die Frage beantwortet ...)Der
unbuffer
Befehl aus dem Expect- Paket entkoppelt die Ausgabe aus dem ersten Programm und die Eingabe in das zweite Programm.Du würdest es so benutzen:
Ich benutze es die ganze Zeit mit Ansible und einem Homebrewed- Ctee- Skript, damit ich die Farbausgabe auf dem Terminal sehen kann, während ich die Protokolldatei mit normaler (nicht colorierter) Ausgabe lasse.
quelle