Linux чтение файла журнала и фильтра, чтобы получить один и тот же тип сообщений журнала только один раз - PullRequest
1 голос
/ 12 марта 2020

В моем файле журнала у меня есть три типа сообщений журнала: информация, предупреждение и ошибка. Я хочу получить только сообщения об ошибках, но поскольку сообщения об ошибках различного типа и одно и то же сообщение об ошибке может появляться в файле журнала более одного раза, я хочу получить каждый тип ошибки только один раз. Какую команду я могу использовать в терминале Ubuntu? Я попытался:

grep -E 'level=error' server.log | sort --unique

Но это также дает мне сообщения «информация» и «предупреждение».

Затем я использовал эту команду, но все равно получаю все три типа сообщений, не только сообщения об ошибках.

grep 'error' server.log | uniq -f 1

аргумент -f 1 должен пропускать поле отметки времени, поскольку оно всегда будет уникальным.

Например, мои сообщения журнала:

.
.
.
11-03-2020 11:53:32" level=info msg="Starting up" file="etc/load/startwith.txt"
11-03-2020 11:53:33" level=info msg="Started" file="etc/load/startwith.txt"
11-03-2020 11:54:29" level=warning msg="Some fields missing" file="etc/load/startwith.php" 
11-03-2020 11:54:47" level=info msg="Started the process" file="etc/load/startwith.php" 
11-03-2020 11:54:51" level=info msg="Connecting to database" file="etc/db/dbinfo.php" 
11-03-2020 11:54:53" level=error msg="Database connection failed" file="etc/db/dbinfo.php"  
11-03-2020 13:26:22" level=info msg="Started back-up process" file="etc/load/startwith.php" 
11-03-2020 13:26:23" level=info msg="Starting up" file="etc/load/startwith.txt"
11-03-2020 13:26:26" level=error msg="Start up failed" file="etc/db/startwith.php" 
11-03-2020 13:26:27" level=info msg="Starting up" file="etc/load/startwith.txt"
11-03-2020 13:26:31" level=error msg="Start up failed" file="etc/db/startwith.php"
11-03-2020 13:26:32" level=info msg="Starting up" file="etc/load/startwith.txt"
11-03-2020 13:26:35" level=warning msg="Duplicate fields found" file="etc/load/startwith.php" 
11-03-2020 13:26:36" level=info msg="Started the process" file="etc/load/startwith.php" 
11-03-2020 13:26:37" level=info msg="Connecting to database" file="etc/db/dbinfo.php"
11-03-2020 13:26:38" level=info msg="Success. Connected to the database" file="etc/db/db-success.php"
11-03-2020 13:26:38" level=info msg="Inserting data to database" file="etc/db/dboperation.php"
11-03-2020 13:26:39" level=warning msg="Null fields found" file="etc/db/dboperation.php"
11-03-2020 13:26:39" level=info msg="Data inserted" file="etc/db/dboperation.php"
11-03-2020 13:26:39" level=info msg="Disconnected" file="etc/db/dboperation.php"
11-03-2020 13:26:43" level=info msg="Inserting data to database" file="etc/db/dboperation.php"
11-03-2020 13:26:43" level=error msg="Required data missing" file="etc/db/dboperation.php"
11-03-2020 13:26:44" level=info msg="Inserting data to database" file="etc/db/dboperation.php"
11-03-2020 13:26:44" level=error msg="Required data missing" file="etc/db/dboperation.php"
.
.
.

Ожидаемый результат для ошибок из вышеуказанных журналов (3 различных типа ошибок, а не общее количество ошибок) будет:

11-03-2020 11:54:53" level=error msg="Database connection failed" file="etc/db/dbinfo.php" 
11-03-2020 13:26:31" level=error msg="Start up failed" file="etc/db/startwith.php"
11-03-2020 13:26:44" level=error msg="Required data missing" file="etc/db/dboperation.php"

Поэтому, по сути, мне нужно отфильтровать файл журнала, чтобы получить ошибку сообщения и имеющие только одну ошибку для каждого типа.

Ответы [ 2 ]

0 голосов
/ 12 марта 2020

Just:

awk '/error/ && !seen[$4]++'

Или используйте кавычки в качестве разделителя для включения полного msg="this text" сообщения, например:

awk -F'"' '/error/ && !seen[$3]++'

Вы можете сделать это без awk - grep error затем nl номеров строк, затем sort -u сортировка уникальных в поле с помощью msg=, затем повторная сортировка по номерам строк и удаление номеров строк с помощью cut. В качестве альтернативы msg="part" может быть извлечено с помощью sed для упрощения sort токенизации. Как это:

grep error | sed 's/.* msg="\([^"]*\)"/\1\t&/' | nl -w1 |
sort -t $'\t' -u -k2,2 | sort -n -k1 | cut -f3-
0 голосов
/ 12 марта 2020

Команда uniq -f 1 разделяется пробелами. Это не имеет никакого эффекта, потому что строка после первого пробела, времени, является уникальной.

Используйте взамен uniq -s 20. При этом игнорируются первые 20 символов.

Это работает для отметок времени, поскольку в большинстве случаев они имеют фиксированную длину.

...