7

I have input coming from pipe which contains special escape characters. For illustration, the stream looks like this:

printf "foo.bar\033[00m" > file
cat file

How can I remove the trailing .bar\033[00m? I have tried the following, but that does not work:

cat file | sed 's/\.bar\033[00m//'

2 Answers 2

9

If your file contains control characters such as

printf "foo.bar\033[00m" > file

then to remove the specific, single occurrence of .bar\033[00m write the following:

sed $'s/\.bar\033\[00m//'

To remove all kinds of escape sequences in the entire file:

sed $'s/\033\[[0-9;]*m//g'

The dollar-before-single-quoted-string ($'some text') instructs the shell to apply ANSI C quoting to the string's content, like printf does. This is required to produce the "escape" ASCII character (0x1B/033/...).

The character can also be produced via keyboard shortcuts (no $' necessary):

sed 's/\.barCtrl-vESC\[00m//'

After hitting Ctrl-vESC you should see ^[ on the screen, but not literal ^ and [ (two characters), but one single control character.


Original answer

If you want in the output just foo then

printf '%s' 'foo.bar\033[00m' | sed 's/\.bar\\033\[00m//'

Notice that both \ and [ has to escaped by another \. Additionally I've added '%s' to printf to print the input characters as literal string, otherwise \033[ could be interpreted as escape code followed by ANSI colour.

6
  • This is right. Adding '%s' is crucial in this case to avoid the special interpretation of \033[.
    – Ketan
    Commented Dec 7, 2014 at 20:01
  • but the printf was just for illustration. As I said, my input is coming from pipe, not from printf. I need a solution which will work even without printf, such as: cat file | sed 's/\.bar\\033\[00m//' Commented Dec 7, 2014 at 20:07
  • And what is the problem? sed 's/\.bar\\033\[00m//' file should work just fine, doesn't it? Perhaps you should add g just before final ' to replace all occurrences of such pattern.
    – jimmij
    Commented Dec 7, 2014 at 20:14
  • I have used cat file | sed ... as an example to show why printf does not work. But I need to use sed not on file, but on input coming from pipe. Sorry if my example was confusing. Commented Dec 7, 2014 at 20:30
  • @MartinVegter From the edit of your question I believe that your file (or input stream) in fact doesn't have a string \033[, but rather control character. In such case write the following: cat file | sed 's/\.bar Ctrl-v ESC \[00m//'. Here Ctrl-v ESC inputs escape control character, you should see ^[ on the screen. Please report if this is the case so I will modify the answer.
    – jimmij
    Commented Dec 7, 2014 at 20:41
1

You need to escape the [ and \ characters with a backslash:

printf '%s' "foo.bar\033[00m" | sed 's/\.bar\\033\[00m//'

Alternatively, if you want to remove everything after the dot character in the string:

printf "foo.bar\033[00m" | sed 's/\..*//'
6
  • this actually does not work. It does not remove anything. Commented Dec 7, 2014 at 20:02
  • @MartinVegter I edited the answer with '%s' inspired by the answer from jimmij for correctness.
    – Ketan
    Commented Dec 7, 2014 at 20:09
  • thanks, but unfortunately this does not help me. My input is coming from pipe, not from printf. I need a sed command which will work like this: cat file | sed 's/\.bar\\033\[00m//'. The currect sed syntax does not work for this. Commented Dec 7, 2014 at 20:10
  • @MartinVegter Would this work: cat file | sed 's/\.bar.*//'
    – Ketan
    Commented Dec 7, 2014 at 20:16
  • no. I don't want to remove any occurrence of \.bar.*. I only need to remove if it is at the end (followed by ANSI color code) Commented Dec 7, 2014 at 20:18

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .