将JSON格式化输出转换为单行输出

24

我有一个命令需要运行,运行后输出如下:

{
"endpointApplications": {
    "App_Name": {
        "connectionState": "Disconnected",
        "connectionTime": "No connection was established",
        "linkAttributes": {
            "ackSettings": {
                "dataAckEnabled": "true",
                "dataAckTimeout": "5000",
                "dataNakRetryLimit": "0",
                "retransmitDelay": "500"
            },
            "keepAliveSettings": {
                "keepAliveAckTimeout": "5000",
                "keepAliveInterval": "30000"
            },
            "logTraffic": "false",
            "port": "9999",
            "role": "server"
        },
        "protocol": "snmp"
    }
},
"queueStats": {}
}
我希望输出结果像下面这样只有一行:

I would need the output to be in one line like below:

{"endpointApplications": {"app_name": {"connectionState": "Disconnected","connectionTime": "No connection was established","linkAttributes": {"ackSettings":{"dataAckEnabled": "true","dataAckTimeout": "5000","dataNakRetryLimit": "0","retransmitDelay": "500"},"keepAliveSettings":{"keepAliveAckTimeout": "5000","keepAliveInterval": "30000"},"logTraffic": "false","port": "9999","role": "server"},"protocol": "snmp"}},"queueStats":{}}

我尝试使用awk和sed结合不同的参数,但无法在不丢失JSON格式的情况下使其正常工作。


2
考虑使用 jq 来处理每一行的结果 :) - chepner
2个回答

39

你应该使用jq来处理类似的东西:

jq -c . input.txt

另一种快速而简单的解决方案是使用sedtr

sed -e 's/^ *//' < input.txt | tr -d '\n'

虽然我建议使用专门用于操作JSON的jqjq就像JSON的sed一样。使用sed/awk/等文本方式操作JSON不能保证生成具有相同语义的JSON。


您可以在基于 Debian 的 Linux(例如 Ubuntu)上通过简单的 sudo apt-get install jq 命令获取 jq - B--rian
替代方案对我有用,因为我处理了包含特殊数据类型的mongodb中的json数据。 - RCalaf

17

jq 或其他支持 json 文件操作的工具最适合处理 json 文件。不过这里提供一种基于 awk 的解决方案。

awk -v RS= '{$1=$1}1' input.json
{ "endpointApplications": { "App_Name": { "connectionState": "Disconnected", "connectionTime": "No connection was established", "linkAttributes": { "ackSettings": { "dataAckEnabled": "true", "dataAckTimeout": "5000", "dataNakRetryLimit": "0", "retransmitDelay": "500" }, "keepAliveSettings": { "keepAliveAckTimeout": "5000", "keepAliveInterval": "30000" }, "logTraffic": "false", "port": "9999", "role": "server" }, "protocol": "snmp" } }, "queueStats": {} }

注意:此解决方案主要针对没有像jq这样的工具并且由于某些原因无法安装它们的传统系统。


你能否帮我进一步解释一下awk动作部分{$1=$1}1?我写了自己的一些东西,例如awk -v ORS= '{ print $0 } END { printf "\n" }',但是你的更好! - Grijesh Chauhan
1
{$1=$1}1 是 awk 世界中著名的语句构造。它被用来强制/伪造 Awk 使用我们传递的 RS 值重构记录。如果没有重构记录,我们传递的 RS 值就不会在结果中显示。顺便说一下,你可以使用任何重构记录的方式,比如 $8=$8。最后的1是为了强制条件成立以便于打印结果。 - P....
此外,为了更有意义,在awk中,默认情况下记录等于一行。例如,由新行分隔。 - P....

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接