從文字流中刪除 ANSI 顏色代碼

從文字流中刪除 ANSI 顏色代碼

檢查輸出

perl -e 'use Term::ANSIColor; print color "white"; print "ABC\n"; print color "reset";'

在文字編輯器(例如vi)中顯示以下內容:

^[[37mABC
^[[0m

如何從輸出檔中刪除 ANSI 顏色代碼?我認為最好的方法是透過某種流編輯器傳輸輸出。

以下不起作用

perl -e 'use Term::ANSIColor; print color "white"; print "ABC\n"; print color "reset";' | perl -pe 's/\^\[\[37m//g' | perl -pe 's/\^\[\[0m//g'

答案1

字元^[[37m^[[0mANSI 轉義序列(CSI 程式碼)。也可以看看這些規格

使用GNUsed

sed -e 's/\x1b\[[0-9;]*m//g'
  • \x1b(或\x1B)是逃脫特殊字元
    (GNUsed不支援替代字元\e\033
  • \[是轉義序列的第二個字符
  • [0-9;]*是顏色值正規表示式
  • m是轉義序列的最後一個字符

使用 macOS 預設值sed

麥克風建議:

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

macOS 預設sed不支援特殊字符,\e如所指出的永續發展管理蒸籠25在評論中。

安裝gsed

brew install gnu-sed

OP 命令列範例

(OP是指原創海報)

perl -e 'use Term::ANSIColor; print color "white"; print "ABC\n"; print color "reset";' | 
      sed 's/\x1b\[[0-9;]*m//g'

改進

標誌-e對於 GNU 是可選的sed,但對於 macOS 預設是必需的sed

sed 's/\x1b\[[0-9;]*m//g'           # Remove color sequences only

湯姆·黑爾建議也使用而不是僅使用特定於圖形模式轉義序列(顏色)的[a-zA-Z]字母來刪除所有其他轉義序列:m

sed 's/\x1b\[[0-9;]*[a-zA-Z]//g'    # Remove all escape sequences

[a-zA-Z]可能太寬,可能會刪除太多內容。米哈烏·法倫斯基米格爾·莫塔建議分別使用[mGKH][mGKF]來刪除一些轉義序列。

sed 's/\x1b\[[0-9;]*[mGKH]//g'      # Remove color and move sequences
sed 's/\x1b\[[0-9;]*[mGKF]//g'      # Remove color and move sequences
sed 's/\x1b\[[0-9;]*[mGKHF]//g'     # Remove all
Last escape
sequence
character   Purpose
---------   -------------------------------
m           Graphics Rendition Mode (including color)
G           Horizontal cursor move
K           Horizontal deletion
H           New cursor position
F           Move cursor to previous n lines

布里頓·克林指示K(除了)從錯誤/警告m中刪除顏色。gcc不要忘記重定向gcc 2>&1 | sed...

使用perl

sed某些作業系統上安裝的版本可能受到限制(例如 macOS)。該命令perl的優點是通常更容易在更多作業系統上安裝/更新。亞當·卡茨建議使用\e(與 相同\x1b)聚合酶鍊式反應

根據您要過濾的命令數量選擇正規表示式:

perl -pe 's/\e\[[0-9;]*m//g'          # Remove colors only
perl -pe 's/\e\[[0-9;]*[mG]//g'
perl -pe 's/\e\[[0-9;]*[mGKH]//g'
perl -pe 's/\e\[[0-9;]*[a-zA-Z]//g'
perl -pe 's/\e\[[0-9;]*m(?:\e\[K)?//g' # Adam Katz's trick

OP 命令列範例:

perl -e 'use Term::ANSIColor; print color "white"; print "ABC\n"; print color "reset";' \
      | perl -pe 's/\e\[[0-9;]*m//g'

用法

正如所指出的史都華·卡德爾的註釋,該sed命令列是項目使用的終極 Nginx 壞機器人(1000 顆星)清理電子郵件報告;-)

答案2

如果您使用的是 MacOS,我已經找到了更好的轉義序列刪除器。檢查一下:

perl -pe 's/\x1b\[[0-9;]*[mG]//g'

答案3

ANSI2txt

https://unix.stackexchange.com/a/527259/116915

cat typescript | ansi2txt | col -b
  • ansi2txt:刪除 ANSI 顏色代碼
  • col -b:刪除^H^M


更新:關於 col 句柄製表符和空格 //@DanielF 提到

〇.關於col句柄空格和製表符

col -bx將 '\t' 替換為 ' ', col -bh將 ' ' 替換為 '\t'。

// 似乎col不能保持空格/製表符原樣,很遺憾。


0. 原始字串

$ echo -e '        ff\tww' | hd
00000000  20 20 20 20 20 20 20 20  66 66 09 77 77 0a        |        ff.ww.|

1. -h 將空格替換為製表符

$ echo -e '        ff\tww' | col -b | hd
00000000  09 66 66 09 77 77 0a                              |.ff.ww.|
$ echo -e '        ff\tww' | col -bh | hd
00000000  09 66 66 09 77 77 0a                              |.ff.ww.|
$ echo -e '        ff\tww' | col -bxh | hd
00000000  09 66 66 09 77 77 0a                              |.ff.ww.|

2. -x 將製表符替換為空格

$ echo -e '        ff\tww' | col -bx | hd
00000000  20 20 20 20 20 20 20 20  66 66 20 20 20 20 20 20  |        ff      |
00000010  77 77 0a                                          |ww.|
$ echo -e '        ff\tww' | col -bhx | hd
00000000  20 20 20 20 20 20 20 20  66 66 20 20 20 20 20 20  |        ff      |
00000010  77 77 0a                                          |ww.|

3. 似乎col無法保持空格和製表符原樣。

答案4

^[照原樣顯示什麼不是 ^[;它是 ASCII字符,由orESC生成(該符號表示 Ctrl 鍵)。EscCtrl[^

ESC是 0x1B 十六進位或 033 八進制,因此您必須在正規表示式中使用\x1Bor :\033

perl -pe 's/\033\[37m//g; s/\033[0m//g'

perl -pe 's/\033\[\d*(;\d*)*m//g'

相關內容