Как очистить вывод команды linux 'script'

35

Я использую команду linux 'script' http://www.linuxcommand.org/man_pages/script1.html для отслеживания некоторых интерактивных сессий. Выходные файлы этого содержат непечатаемые символы, в том числе мои нажатия клавиш возврата.

Есть ли способ привести в порядок эти выходные файлы, чтобы они содержали только то, что отображалось на экране?

Или есть другой способ записи сеанса интерактивной оболочки (ввод и вывод)?

Эндрю
источник
«Или есть другой способ записи сеанса интерактивной оболочки (ввод и вывод)?» Вы знаете asciinema.org ?
masterxilo

Ответы:

34

Если вы хотите просмотреть файл, вы можете отправить вывод через col -bp; это интерпретирует управляющие символы. Тогда вы можете пройти через меньшее, если хотите.

col -bp typescript | less -R

В некоторых системах colне принимают аргумент имени файла, используйте этот синтаксис:

col -bp <typescript | less -R
Arcege
источник
1
в моей системе colне принимал имя файла, поэтому я сделал col -bp < typescript и получил то, что хотел.
Андрей
У меня не работает, разбирается с некоторыми результатами.
Алекс
1
В моей системе less -Rсамо по себе обеспечивает лучшую производительность, чем в col -bpпервую очередь.
Брайан Хокинс
@BrianHawkins Я согласен. Использование col -bp <typescript | less -Rне отображает цветную консоль. Использование less -R typescriptотображает раскрашенную консоль!
Тревор Бойд Смит
Это хорошо, только если вы хотите просмотреть скрипт в интерактивном режиме less.
Тревор Бойд Смит
18
cat typescript | perl -pe 's/\e([^\[\]]|\[.*?[a-zA-Z]|\].*?\a)//g' | col -b > typescript-processed

Вот некоторая интерпретация ввода строки в perl:

  • s/pattern//gозначает сделать подстановку для всей ( gопция означает сделать всю вещь вместо остановки на первой замене) входной строки

Вот некоторая интерпретация шаблона регулярных выражений:

  • \e соответствует специальному управляющему символу «escape» (ASCII 0x1A)
  • (и )являются началом и концом группы
  • |означает, что группа может соответствовать одному из N шаблонов. где N моделей
    • [^\[\]] или
    • \[.*?[a-zA-Z] или
    • \].*?\a
  • [^\[\]] средства
    • совпадать с набором символов НЕ, где символы не являются [и]
  • \[.*?[a-zA-Z] средства
    • сопоставьте строку, начинающуюся с, [затем сделайте не жадный .*?до первого альфа-символа
  • \].*?\a средства
    • сопоставьте строку, которая начинается с, ]затем делайте не жадный, .*?пока вы не нажмете специальный управляющий символ, называемый «символ предупреждения (колокол)»
Питер Нор
источник
1
Мне все еще нужно выяснить как, но это действительно работает;)
asdmin
@asdmin - В основном, это отголоски выход из typescriptк perlпрограмме , которая удаляет некоторые управляющие символы с выхода, затем трубы на выходе в UNIX colкоманды, чей -bпараметр удаляет «Delete» ключевые артефакты в стенограмме. Затем он передает данные в текстовый файл.
Питер Нор
Это зашифровывает вывод в первой строке машинописи для меня, но это лучший ответ.
Алекс
Это, кажется, работает очень хорошо с некоторыми машинописными текстами; это, безусловно, более читабельно, чем результат, полученный в результате принятого ответа.
Fakedad
легендарный ответ!
Зак
2

Для большого количества scriptвывода я бы итеративно взламывал Perl-скрипт. В противном случае отредактируйте вручную с помощью хорошего редактора.

Маловероятно, чтобы существовал автоматизированный метод удаления управляющих символов из scriptвывода способом, который воспроизводит то, что отображалось на экране в определенные важные моменты (например, когда хост ожидал этого первого символа некоторого пользовательского ввода).

Например, экран может быть пустым, за исключением того Andrew $, что если вы затем набрали rm /*и нажали клавишу Backspace двенадцать раз (гораздо больше, чем нужно), то, что будет показано на экране в конце, зависит от того, какая оболочка была запущена, каковы ваши текущие sttyнастройки ( который вы могли бы изменить на полпути через сеанс) и, возможно, некоторые другие факторы.

Вышесказанное относится к любому автоматизированному способу непрерывного захвата ввода и вывода. Основной альтернативой является создание «снимков экрана» или вырезание и вставка экрана в подходящее время во время сеанса (что я и делаю для руководств пользователя, заметок для дневника и т. Д.).

RedGrittyBrick
источник
2

Ответом на вторую часть моего вопроса является использование средства ведения журнала в gnu screen: ^A Hиз сеанса работающего экрана. Документация находится по адресу http://www.gnu.org/software/screen/manual/screen.html#Logging.

Эндрю
источник
2

Я использовал cat filenameкоторый удаляет управляющие символы :-)

Peeyush
источник
IMO, это более хороший ответ, так как он действительно удаляет все управляющие символы.
Натанаэль Фарли
на OSX кошка не удаляет символы управления цветом ...
Ник
9
На самом деле cat вообще не удаляет управляющие символы, а выводит их дословно, а затем терминал их интерпретирует. Это может сработать для вас, если ваша машинопись является короткой относительно буфера терминала, и вы можете просто копировать и вставлять из терминала. Не так хорошо, если ваш машинопись большая.
mc0e
1
Согласовано. Это ничего не удаляет. Это просто позволяет оболочке интерпретировать их. Они все еще присутствуют.
Кентграв
2

Если вам нужно записать ваши команды (например, чтобы потом превратить их в скрипт bash), тогда разумный хак - запустить script(1), а затем запустить

bash -x

После grepэтого выходной файл (обычно «машинопись») ищет строки, начинающиеся с «+». Регулярное выражение ^\+сделает свое дело.

Ярон
источник
2

Если вы хотите записать вывод в файл:

col -bp < typescript >>newfile

используйте команду unix2dos для преобразования файла в формат Windows, если хотите

амара
источник
1
В Ubuntu 14.04, это оставляет много мусора в начале и конце строк. Вполне читабельно, но не очень чисто.
mc0e
2

col-bp обрабатывает возвраты по желанию (AFAIK). Но это мешает цветовой последовательности побега. Возможно, было бы хорошо сначала удалить последовательности цветов, а затем обработать возвраты, если это возможно.

Это очень распространенная потребность, и я удивлен, что нет больше решений для этого. Сценарий сеанса чрезвычайно распространен, тогда кто-то должен пересмотреть процедуру. Вы хотите вырезать все мелкие ошибки при наборе и цветовые escape-последовательности, чтобы создать «чистый» сценарий процедуры для дальнейшего использования. Простой текст ASCII предпочтителен. Я думаю, что это то, что подразумевается под «читабельным человеком», и это очень разумная вещь.

Аарон
источник
1

Я обнаружил, что ответ, предложенный dewtall на аналогичный вопрос на плате Unix, более эффективен при удалении управляющих символов из вывода скрипта, если вы находитесь в среде, где вам доступен Perl.

сценарий dewtall:

#!/usr/bin/perl
while (<>) {
    s/ \e[ #%()*+\-.\/]. |
       \r | # Remove extra carriage returns also
       (?:\e\[|\x9b) [ -?]* [@-~] | # CSI ... Cmd
       (?:\e\]|\x9d) .*? (?:\e\\|[\a\x9c]) | # OSC ... (ST|BEL)
       (?:\e[P^_]|[\x90\x9e\x9f]) .*? (?:\e\\|\x9c) | # (DCS|PM|APC) ... ST
       \e.|[\x80-\x9f] //xg;
       1 while s/[^\b][\b]//g;  # remove all non-backspace followed by backspace
    print;
}

Чтобы удалить управляющие символы:

./dewtalls-script.pl < output-from-script-that-needs-control-characters-removed
rynemccall
источник
1

https://github.com/RadixSeven/typescript2txt был написан для решения этой проблемы.

Прошло 4 года с тех пор, как я последний раз обновлял / использовал его, но я не помню, чтобы я делал что-то необычное, что не должно работать сегодня.

Одноименный
источник
0

Я нашел хороший способ сделать это. В моей системе длинные выходные строки посыпаются символом «^ M» (пробел, за которым следует возврат каретки). Символ «^ M» может быть заменен нулевым символом «^ @», который вообще не отображается при просмотре файла.

Я также фиксирую время, поэтому, чтобы воспроизвести файл идеально, я не могу просто полностью удалить «^ M», используя команды ниже (потому что скрипт запускает подсчет байтов):

tr '\r' '\0' | sed 's/ \x0//g'

Я запускаю команду сценария следующим образом:

script -t -f session.log 2>timing

Итак, что я делаю потом:

cat session.log | tr '\r' '\0' > typescript 
scriptreplay -t timing | sed 's/ \x0//g'

Первое редактирование (до воспроизведения) сохраняет количество байтов в файле. Второе редактирование (после воспроизведения) избавляет от пробелов в случайных местах. (Обратите внимание, что по умолчанию scriptreplay ищет входной файл с именем «typcript», поэтому я не предоставил его после «хронометража».)

Ханан
источник
-1

DOS2UNIX на выходе также сделает свое дело

альберт
источник
7
Не могли бы вы объяснить, как использовать его для выполнения задачи?
Бен Н
-1

Еще одно решение заключается в использовании strings печатать только печатные символы из файла (или из стандартного ввода):

strings -n 1 filename

-n 1Опция устанавливает минимальную длину последовательностей должны быть сохранены в одной и тем самым гарантирует , что даже единичные печатные символы , окруженные непечатаемых символов сохраняются.

Одним из возможных недостатков этого подхода является stringsдобавление разрывов строк между смежными строками печатаемых символов. Например, файл с содержанием

Foo<SOMECONTROLCHAR>Bar

(где <SOMECONTROLCHAR>контрольный символ или любой другой непечатаемый символ) будет возвращен как

Foo
Bar

Другая проблема, поднятая в комментариях, состоит в том, что некоторые последовательности управляющих символов состоят из комбинации как печатных, так и непечатных символов, и этот подход удалит только часть из них.

Тем stringsне менее, делает хорошую работу по удалению управляющих символов, таких как Backspace, упомянутый в вопросе.

justfortherec
источник
stringsне удаляет все непечатаемые символы Он идентифицирует и печатает последовательности печатных символов . Это не одно и то же.
CVn
@ MichaelKjörling, вы правы, по умолчанию stringsпечатаются только последовательности минимальной длины 4. Я исправил свой ответ, добавив -n 1опцию, которая устанавливает минимальную длину равной 1. Спасибо за указание на это.
Justfortherec
Ответ по-прежнему делает то же самое утверждение, что stringsудаляет все непечатаемые символы, поэтому он все равно не так, как до редактирования. Это также очевидно нарушено, потому что «некоторый цветовой код» (и управляющие коды в целом) часто состоит из печатных и непечатных символов. Например, последовательность управляющих кодов для изменения цвета текста может быть ESC[01;52mгде ESCесть один управляющий символ (значение байта 27). Использование, stringsкак вы предлагаете, оставит [01;52mв выводе, что не имеет смысла.
CVn
Хороший вопрос, @ MichaelKjörling. Особенно пример с цветовым кодом был очень неудачным. Спасибо за помощь в улучшении моего ответа. Соответствуют ли изменения вашим проблемам? stringsможет не выполнять ту же работу, что и некоторые другие ответы, но ИМХО это правильный подход к решению проблемы, описанной в вопросе.
Justfortherec