来自应用程序的日志消息符合LogStash期望(JSON),但我们无法在每种情况下启动并运行LogStash,因此我一直在尝试学习使用jq来实现当LogStash不可用时读取输出。当输出是JSON中的XML时,问题变得棘手。我输出像......
{
<SNIP>
"rom_response_body": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<OrderCreateResponse xmlns=\"http://api.example.com/schema/checkout/1.0\">\n <ResponseStatus>Success</ResponseStatus>\n <ResponseDescription>CustomerOrderId = 0005410600539 , OrderUUID = 57c27a87-2f2e-41d1-bc20-afef511b91aa</ResponseDescription>\n</OrderCreateResponse>",
<SNIP>
}
我想得到的是:
<?xml version="1.0" encoding="UTF-8"?>
<OrderCreateResponse xmlns="http://api.example.com/schema/checkout/1.0">
<ResponseStatus>Success</ResponseStatus>
<ResponseDescription>CustomerOrderId = 0005410600541 , OrderUUID = 3bc76558-f5aa-4e2e-866d-5c4707e873db</ResponseDescription>
</OrderCreateResponse>
或者至少是任何原始形式的格式良好的xml(从那时起我可以使用xmllint)。我可以 sorta 用jq到达那里。如果我做
tail system.log | jq "select(.rom_response_body)|.rom_response_body|fromjson"
我得错误输出
jq: error: Invalid numeric literal at line 1, column 6 (while parsing '<?xml version="1.0" encoding="UTF-8"?>
<OrderCreateResponse xmlns="http://api.example.com/schema/checkout/1.0">
<ResponseStatus>Success</ResponseStatus>
<ResponseDescription>CustomerOrderId = 0005410600541 , OrderUUID = 3bc76558-f5aa-4e2e-866d-5c4707e873db</ResponseDescription>
</OrderCreateResponse>')
我认为问题在于输入实际上不是json,它只是一个json转义的字符串文字。如果用{"key": }
包裹它将是有效的。有没有更好的方法来获得我需要的输出,除了手动包装每一行以使其完整JSON?
答案 0 :(得分:2)
默认输出格式是一个或多个有效的JSON值。 XML显然不是JSON。但是字符串本身是有效的,但它代表的值不是。您可以使用原始输出选项(-r
)忽略此限制。这将返回字符串的值。
$ tail system.log | jq -r '.rom_response_body'
<?xml version="1.0" encoding="UTF-8"?>
<OrderCreateResponse xmlns="http://api.example.com/schema/checkout/1.0">
<ResponseStatus>Success</ResponseStatus>
<ResponseDescription>CustomerOrderId = 0005410600539 , OrderUUID = 57c27a87-2f2e-41d1-bc20-afef511b91aa</ResponseDescription>
</OrderCreateResponse>