Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
920 views
in Technique[技术] by (71.8m points)

bash - How to strip ANSI escape sequences from a variable?

Weird question. When I set a variable in Bash to display as a certain color, I don't know how to reset it. Here is an example:

First define the color code:

YELLOW=$(tput setaf 3)
RESET=$(tput sgr0)    

Now set the error message variable and color part of it.

ERROR="File not found: "$YELLOW"Length.db$RESET"

This sets the variable ERROR as the error message to be returned from a function that will eventually be displayed on the terminal. The error will be all white with the exception of the file name. The file name is highlighted yellow for the user.

This works great except when logging with rsyslog. When the error message gets logged, it comes out something like this:

File not found: #033[33mLength.db#033(B#033[m

This obviously makes log files very difficult to read. At first I figured I could process using sed the error message immediately after outputting to the terminal but before logging, but there is nothing to search for and replace. ie, I thought I could use sed to do something similar to this:

ERROR=$(echo "$ERROR" | sed -r 's%#033[33m%%')

But those characters are not present when you echo the variable (which makes sense since you dont see it on the terminal). So im stuck. I dont know how to reset the color of the variable after setting it. I also tried to reverse the process somehow using $RESET but maybe my syntax is wrong or something.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

You almost had it. Try this instead:

ERROR=$(echo "$ERROR" | sed 's%o033[33m%%g')

Note, however, that the use of the oNNN escape sequence in sed is a GNU extension, and thus not POSIX compliant. If that is an issue, you should be able to do something more like:

ERROR=$(echo "$ERROR" | sed 's%'$(echo -en "33")'[33m%%g')

Obviously, this will only work for this one specific color (yellow), and a regex to remove any escape sequence (such as other colors, background colors, cursor positioning, etc) would be somewhat more complicated.

Also note that the -r is not required, since nothing here is using the extended regular expression syntax. I'm guessing you already know that, and that you just included the -r out of habit, but I mention it anyway just for the sake of clarity.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...