Eu não vejo como seu comando pode funcionar desde (pelo menos no meu sistema) tail -f
não pode ser canalizado duas vezes desde que o segundo programa que você canaliza ( grep
no seu caso) aguarda até que a entrada termine antes resultados de impressão.
De qualquer forma, o método padrão é o que os goldilocks sugeriram, usando sequências de cores de escape ANSI . Como faço isso com muita frequência, escrevi um pequeno script que colore qualquer string que você der:
#!/usr/bin/env perl
use Getopt::Std;
use strict;
use Term::ANSIColor;
my %opts;
getopts('hic:l:',\%opts);
if ($opts{h}){
print<<EoF;
Use -l to specify the pattern(s) to highlight. To specify more than one
pattern use commas.
-l : A Perl regular expression to be colored. Multiple expressions can be
passed as comma separated values: -l foo,bar,baz
-i : makes the search case sensitive
-c : comma separated list of colors;
EoF
exit(0);
}
my $case_sensitive=$opts{i}||undef;
my @color=('bold red','bold blue', 'bold yellow', 'bold green',
'bold magenta', 'bold cyan', 'yellow on_magenta',
'bright_white on_red', 'bright_yellow on_red', 'white on_black');
if ($opts{c}) {
@color=split(/,/,$opts{c});
}
my @patterns;
if($opts{l}){
@patterns=split(/,/,$opts{l});
}
else{
$patterns[0]='\*';
}
# Setting $| to non-zero forces a flush right away and after
# every write or print on the currently selected output channel.
$|=1;
while (my $line=<>)
{
for (my $c=0; $c<=$#patterns; $c++){
if($case_sensitive){
if($line=~/$patterns[$c]/){
$line=~s/($patterns[$c])/color("$color[$c]").$1.color("reset")/ge;
}
}
else{
if($line=~/$patterns[$c]/i){
$line=~s/($patterns[$c])/color("$color[$c]").$1.color("reset")/ige;
}
}
}
print STDOUT $line;
}
Se você salvá-lo como color
em um diretório que esteja em $PATH
e torná-lo executável (chmod + x / usr / bin / color), poderá colorir linhas de seu log de erros da seguinte forma:
tr '#!/usr/bin/env perl
use Getopt::Std;
use strict;
use Term::ANSIColor;
my %opts;
getopts('hic:l:',\%opts);
if ($opts{h}){
print<<EoF;
Use -l to specify the pattern(s) to highlight. To specify more than one
pattern use commas.
-l : A Perl regular expression to be colored. Multiple expressions can be
passed as comma separated values: -l foo,bar,baz
-i : makes the search case sensitive
-c : comma separated list of colors;
EoF
exit(0);
}
my $case_sensitive=$opts{i}||undef;
my @color=('bold red','bold blue', 'bold yellow', 'bold green',
'bold magenta', 'bold cyan', 'yellow on_magenta',
'bright_white on_red', 'bright_yellow on_red', 'white on_black');
if ($opts{c}) {
@color=split(/,/,$opts{c});
}
my @patterns;
if($opts{l}){
@patterns=split(/,/,$opts{l});
}
else{
$patterns[0]='\*';
}
# Setting $| to non-zero forces a flush right away and after
# every write or print on the currently selected output channel.
$|=1;
while (my $line=<>)
{
for (my $c=0; $c<=$#patterns; $c++){
if($case_sensitive){
if($line=~/$patterns[$c]/){
$line=~s/($patterns[$c])/color("$color[$c]").$1.color("reset")/ge;
}
}
else{
if($line=~/$patterns[$c]/i){
$line=~s/($patterns[$c])/color("$color[$c]").$1.color("reset")/ige;
}
}
}
print STDOUT $line;
}
1' '|' < file.log | color -l "\|"
Conforme escrito, o script tem cores predefinidas para 10 padrões diferentes, portanto, dar a ele uma lista separada por vírgulas como no exemplo acima irá colorir cada um dos padrões correspondidos em uma cor diferente.