如何使用python处理复杂的嵌套JSON数据?

问题描述

我有一条这样的消息。 该消息是在执行 .ParseFromString() 之后派生的。这些消息以 protobuf 格式通过 ZMQ 传输。

ActiveMQResourceAdapter.getWorkManager()

我需要将输出返回为

    summaries {
  key: "node_A"
  value {
    value_A {
      data_1: 29994
      data_2: 0.07402841001749039
      data_3: -6.621330976486206e-05
    }
    some_activity {
      sys_activity {
        key: "arch_prctl"
        value: 174
      }
      sys_activty {
        key: "execve"
        value: 174
      }
      sys_activity {
        key: "fork"
        value: 261
      }
      some_events_A: 174
      some_events_B: 261
    }
    new_activity {
      sys_new_activity {
        key: "close"
        value: 232
      }
      sys_new_activity {
        key: "open"
        value: 116
      }
      some_new_events: 116
    }
    more_activity {
    }
    error_activity {
    }
    some_alerts {
    }
  }
}

我可以通过使用 value_A.data_1 来获取 value_A 字段

但我发现很难返回剩余的嵌套字段。我尝试使用 json.dumps 但它给了我 JSON object is not a serializable 错误

some_activity 中 sys_activty 的数量各不相同,并不总是如下所示的 3 个值。

如果问题不清楚,请告诉我。假设发送此消息的服务不可编辑,我们只能选择在客户端读取和提供所需的输出。提前致谢

解决方法

你可以试试这个,请不要因为这个丑陋的解决方案而打我

import regex as re
import json

jstring = ""
f = open("brokenjson.txt","r")
for x in f:
    a = x.strip()
    if a[-1] != "{":
        a += ","
    else:
        a = a.replace("{",": {") # add `:` to key : value pair

    if ":" in a:
        b = a.split(":")
        if "\"" not in b[0]:
            a = "\"" + b[0].strip() + "\": " + b[1] # key don't have double quotes "
    jstring += a

jstring = jstring.replace(",}","}") # remove trailing commas

if jstring[-1] == ",":
    jstring = jstring[:-1]  # check if trailing commas at the end or not

if jstring[0] != "{" and jstring[0] != "[":
    jstring = "{" + jstring + "}"  # add bracket

result = json.loads(jstring)

distActivity = {}
distEvent = {}
for key,val in result["summaries"]["value"].items():
    if "activity" in key:
        if key not in distActivity:
            distActivity[key] = []
        for k,v in val.items():
            if "activity" in k:
                distActivity[key].append(v["key"])
            if "event" in k:
                distEvent[k] = v

print(distActivity)
print(distEvent)

因为你的样本有一些重复的键,所以我只得到了这个结果

{'some_activity': ['fork'],'new_activity': ['open'],'more_activity': [],'error_activity': []}
{'some_events_A': 174,'some_events_B': 261,'some_new_events': 116}
,

使用 MessageToJson() 转换 protobuf 而不是 ParseFromString() 解决了这个问题