Анализ лог-файлов: команды grep, awk, sed.
Life-Hack - Linux/Хакинг/Хакер/ИБ/OsintНе обладая навыками обработки текста, мы не можем с уверенностью считать себя экспертами по управлению файлами Linux. Три наиболее известных инструмента командной строки - grep, sed и awk - приобрели репутацию надежных текстовых процессоров в мире Linux. Они уже предустановлены во всех основных дистрибутивах операционных систем Linux, поэтому не требуется дополнительной установки.
Каждая из команд - grep, sed и awk - обладает уникальными функциональными возможностями по обработке текста, однако в некоторых простых сценариях их функции могут перекрываться.
Например, все три команды могут легко выполнять поиск по шаблону в файле и выводить результаты запроса.
В данной статье мы рассмотрим основные различия между этими командами и в каких ситуациях целесообразно использовать ту или иную команду.
Рассмотрим следующий созданный текстовый файл с именем SysLog.txt, в котором указаны различные системные действия на основе отметки времени.
$ cat SysLog.txt Timestamp Category Message 2597743202 INFO System Boot up started 2597743402 INFO Critical services boot up: Autorization 2597743502 INFO Successful system boot up 2597753502 INFO Userlist access request by user admin 2597763777 ERROR User annonymus access attempt on protected resource without credentials 2597763792 INFO System health check status: passed 2597763902 ERROR Requested resource not found 2597764422 INFO User admin logged out
По определению, команда grep находит и печатает текст из файла на основе шаблона регулярного выражения. Это быстрое решение для получение или определения строки в целевом файле.
Синтаксис команды следующий:
grep [OPTION...] PATTERNS [FILE...]
Допустим из файла, который мы создали ранее, мы хотим выделить все события ERROR, наша команда grep будет выглядеть следующим образом:
$ grep "ERROR" SysLog.txt 2597763777 ERROR User annonymus access attempt on protected resource without credentials 2597763902 ERROR Requested resource not found
Команда grep выполняет поиск строки "ERROR" в файле SysLog.txt и выводит результаты на стандартный вывод.
Если мы хотим, чтобы были напечатаны все строки файла, кроме тех, которые содержат указанную строку, мы можем использовать опцию -v. Например:
$ grep -v "ERROR" SysLog.txt Timestamp Category Message 2597743202 INFO System Boot up started 2597743402 INFO Critical services boot up: Autorization 2597743502 INFO Successful system boot up 2597753502 INFO Userlist access request by user admin 2597763792 INFO System health check status: passed 2597764422 INFO User admin logged out
Чтобы напечатать 4 строки после совпадения строки ERROR:
$ grep -A 4 "ERROR" SysLog.txt
Для печати 4 строк до совпадения строки ERROR:
$ grep -B 4 "ERROR" SysLog.txt
Команда sed имеет преимущество перед grep благодаря дополнительным функциям обработки текста.
Ее синтаксис следующий:
$ sed [OPTION]... {script-only-if-no-other-script} [input_file]
Эквивалент команды grep для поиска и печати записей файла, связанных со строкой ERROR, выглядит следующим образом:
$ sed -n '/ERROR/ p' SysLog.txt 2597763777 ERROR User annonymus access attempt on protected resource without credentials 2597763902 ERROR Requested resource not found
Опция -n запрещает sed печатать каждую отсканированную строку.
Предположим, мы хотим заменить строку ERROR на строку CRITICAL в нашем текстовом файле, реализация команды sed будет выглядеть следующим образом:
$ sed 's/ERROR/CRITICAL/' SysLog.txt Timestamp Category Message 2597743202 INFO System Boot up started 2597743402 INFO Critical services boot up: Autorization 2597743502 INFO Successful system boot up 2597753502 INFO Userlist access request by user admin 2597763777 CRITICAL User annonymus access attempt on protected resource without credentials 2597763792 INFO System health check status: passed 2597763902 CRITICAL Requested resource not found 2597764422 INFO User admin logged out
Использование флага -i вместе с определяемым пользователем суффиксом позволяет sed создать резервную копию входного файла перед применением постоянных изменений.
Например, мы можем переименовать строку CRITICAL обратно в ERROR только после создания резервной копии исходного состояния файла.
$ sed -ibackup 's/CRITICAL/ERROR/' SysLog.txt
Исходный файл будет переименован в резервную копию SysLog.txt.
Чтобы ограничить операции sed строкой номер 6 текстового файла, можно использовать следующую команду:
$ sed '6 s/ERROR/CRITICAL/' SysLog.txt
Для указания диапазона от 2 до 4, выполните:
$ sed '2,4 s/INFO/NOTE/' SysLog.txt
Чтобы напечатать совпадения с шаблоном, начиная с определенной строки, например, строки 5, выполните:
$ sed -n '5,/INFO/ p' SysLog.txt
Команду awk можно использовать для выполнения операций со временем, арифметических операций, а также для манипуляций со строками благодаря множеству встроенных функций. Пользователям также предоставляется возможность определять собственные пользовательские функции.
Синтаксис команды awk выглядит следующим образом:
awk [options] script file
С помощью команды awk можно эффективно обрабатывать данные в текстовых файлах и выполнять различные операции с ними, используя мощные возможности этого инструмента.
awk-эквивалент команды grep для поиска строки в файле выглядит следующим образом:
$ awk '/ERROR/{print $0}' SysLog.txt 2597763777 ERROR User annonymus access attempt on protected resource without credentials 2597763902 ERROR Requested resource not found
Команда awk использует gsub (встроенный метод) для операций замены строк.
$ awk '{gsub(/ERROR/, "CRITICAL")}{print}' SysLog.txt Timestamp Category Message 2597743202 INFO System Boot up started 2597743402 INFO Critical services boot up: Autorization 2597743502 INFO Successful system boot up 2597753502 INFO Userlist access request by user admin 2597763777 CRITICAL User annonymus access attempt on protected resource without credentials 2597763792 INFO System health check status: passed 2597763902 CRITICAL Requested resource not found 2597764422 INFO User admin logged out
Мы можем добавлять верхние и нижние колонтитулы во входные файлы, используя блоки BEGIN и END awk, как показано ниже:
$ awk 'BEGIN {print "SYS LOG SUMMARY\n--------------"} {print} END {print "--------------\nEND OF LOG SUMMARY"}' SysLog.txt SYS LOG SUMMARY -------------- Timestamp Category Message 2597743202 INFO System Boot up started 2597743402 INFO Critical services boot up: Autorization 2597743502 INFO Successful system boot up 2597753502 INFO Userlist access request by user admin 2597763777 ERROR User annonymus access attempt on protected resource without credentials 2597763792 INFO System health check status: passed 2597763902 ERROR Requested resource not found 2597764422 INFO User admin logged out -------------- END OF LOG SUMMARY
Для таких документов, как файлы CSV состоящими из строк и столбцов, мы можем указать только определенные столбцы для вывода. Например, выведем 1-й и 2-й столбец нашего файла.
$ awk '{print $1, $2}' SysLog.txt
По умолчанию, awk признает пробелы в качестве разделителей. Если в обрабатываемом тексте в качестве разделителей используются такие символы, как запятые или точки с запятой, вы можете указать их следующим образом:
$ awk -F "," '{print $1, $2}' SysLog.txt или $ awk -F ";" '{print $1 $2}' SysLog.txt
С помощью awk можно подсчитать количество появления определенных строк, следующим образом:
$ awk '{count[$2]++} END {print count["INFO"]}' SysLog.txt
Сценарий awk удобно интерпретирует значения как числа, а не просто как строку. Например, мы могли бы получить записи файлов с временными метками старше 2597763777 следующим образом:
$ awk '{ if ($1 > 2597763777) {print $0} }' SysLog.txt Timestamp Category Message 2597763792 INFO System health check status: passed 2597763902 ERROR Requested resource not found 2597764422 INFO User admin logged out
Выбор инструмента обработки текста зависит от уровня сложности задачи, требуемых операций над текстом, а также от удобства использования конкретной команды для решения задачи. Иногда может потребоваться комбинировать несколько инструментов для более сложных операций.