我正在处理一些在 Linux 上使用 log4j 创建的配置单元日志。使用的正则表达式是
(%d{ISO8601} %-5p [%t]: %c{2} (%F:%M(%L)) - %m%n)
.我意识到有些行被分解成几行。例如
2017-02-10 10:03:29,933 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(185)) - Parsing command:
create table my_table
(std_id STRING, std_number STRING)
2017-02-10 10:03:31,296 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(209)) - Parse Completed
linux 中是否有一个命令,我可以使用它来组合虚线以提供这样的输出;
2017-02-10 10:03:29,933 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(185)) - Parsing command: create table my_table (std_id STRING, std_number STRING)
2017-02-10 10:03:31,296 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(209)) - Parse Completed
最佳答案
这应该有效。
<myfile.log sed -nr \
-e '/^.{4}-.{2}-.{2} .{2}:.{2}:.{2},.{3} [A-Z]+ /{x;1!{s/\n/ /g;p};${g;p};d}' \
-e 'H' \
-e '${g;s/\n/ /g;p}'
解释
让 /^.{4}-.{2}-.{2} .{2}:.{2}:.{2},.{3} [A-Z]+
是指示新日志记录的模式,例如2017-03-17 03:20:19,372 警告
第一个 -e
当当前行指示一条新的日志记录时
x
:交换模式空间(保存当前行)和保持空间的内容。1!{s/\n//g;p}
:如果这不是文件的第一行,(在模式空间内)用空格替换新行并打印它${g;p}
如果这是文件的最后一行,从保留空间中获取它并打印它d
:删除模式空间并开始新的循环(忽略后面的命令)
第二个-e
- 'H':将模式空间附加到保持空间(仅当不是新日志记录时)
第三个-e
如果这是文件的最后一行 ($
) 而不是新的日志记录
g
:用保持空间的内容覆盖模式空间s/\n//g;p
: 将新行替换为空格并打印
演示
$ cat>myfile.log
2017-02-10 10:03:27,374 INFO [main]: ql.Driver (Driver.java:compile(463)) - Semantic Analysis Completed
2017-02-10 10:03:29,933 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(185)) - Parsing command:
create table my_table
(std_id STRING, std_number STRING)
2017-02-10 10:03:31,296 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(209)) - Parse Completed
2017-03-17 03:04:09,297 INFO [main]: ql.Driver (SessionState.java:printInfo(927)) - OK
2017-03-17 03:20:19,372 WARN [Driver]: client.SparkClientImpl (SparkClientImpl.java:run(451)) - Child process exited with code 1.
2017-03-17 03:03:55,282 ERROR [main]: ql.Driver (SessionState.java:printError(936)) - FAILED: ParseException line 1:14 cannot recognize input near 'valeus' '(' '1' in statement
org.apache.hadoop.hive.ql.parse.ParseException: line 1:14 cannot recognize input near 'valeus' '(' '1' in statement
at org.apache.hadoop.hive.ql.parse.ParseDriver.parse(ParseDriver.java:204)
$ <myfile.log sed -nr -e '/^.{4}-.{2}-.{2} .{2}:.{2}:.{2},.{3} [A-Z]+ /{x;1!{s/\n/ /g;p};${g;p};d}' -e 'H' -e '${g;s/\n/ /g;p}'
2017-02-10 10:03:27,374 INFO [main]: ql.Driver (Driver.java:compile(463)) - Semantic Analysis Completed
2017-02-10 10:03:29,933 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(185)) - Parsing command: create table my_table (std_id STRING, std_number STRING)
2017-02-10 10:03:31,296 INFO [main]: parse.ParseDriver (ParseDriver.java:parse(209)) - Parse Completed
2017-03-17 03:04:09,297 INFO [main]: ql.Driver (SessionState.java:printInfo(927)) - OK
2017-03-17 03:20:19,372 WARN [Driver]: client.SparkClientImpl (SparkClientImpl.java:run(451)) - Child process exited with code 1.
2017-03-17 03:03:55,282 ERROR [main]: ql.Driver (SessionState.java:printError(936)) - FAILED: ParseException line 1:14 cannot recognize input near 'valeus' '(' '1' in statement org.apache.hadoop.hive.ql.parse.ParseException: line 1:14 cannot recognize input near 'valeus' '(' '1' in statement at org.apache.hadoop.hive.ql.parse.ParseDriver.parse(ParseDriver.java:204)
关于linux - 合并 log4j 日志行,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42838328/