Verwenden Sie jq, um einen JSON-String zu analysieren

87

Ich versuche, jqeine JSON-Struktur wie folgt zu analysieren:

{
  "a" : 1,
  "b" : 2,
  "c" : "{\"id\":\"9ee ...\",\"parent\":\"abc...\"}\n"
}

Das heißt, ein Element im JSON ist eine Zeichenfolge mit maskiertem json.

Also habe ich etwas in der Art von $ jq [.c] myFile.json | jq [.id]

Aber das stürzt mit ab jq: error: Cannot index string with string

Dies liegt daran, dass die Ausgabe von .c eine Zeichenfolge ist, nicht mehr JSON. Wie bringe ich jq dazu, diesen String zu analysieren?

Meine anfängliche Lösung besteht darin, sed zu verwenden, um alle Escape-Zeichen ( \":\", \",\"und \") zu ersetzen , aber das ist chaotisch. Ich nehme an, es gibt einen eingebauten Weg jq, um dies zu tun.

Vielen Dank!

edit: Die hier verfügbare jq-Version ist außerdem:

$ jq --version
jq version 1.3

Ich denke, ich könnte es bei Bedarf aktualisieren.

Colin Grogan
quelle
Diese Frage hilft auch, wenn Sie suchen: "Wie entferne ich einen JSON-String mit JQ?"
k0pernikus

Antworten:

164

jq hat das fromjsoneingebaute dafür:

jq '.c | fromjson | .id' myFile.json

fromjson wurde in Version 1.4 hinzugefügt.

jwodder
quelle
2
Vielen Dank. Das funktioniert. Ich werde diese Antwort akzeptieren, da ich mich eher "idiomaitisch" fühle. Prost.
Colin Grogan
@ColinGrogan bitte tun.
Vbence
@ColinGrogan: Ich sehe keinen Grund, die akzeptierte Antwort zu ändern, da Sie in Ihrer Frage klar geschrieben haben, dass Sie die Version 1.3 von jq verwendet haben, in der die fromjsonFunktion nicht verfügbar ist. Mit anderen Worten, selbst wenn diese Antwort interessant ist, beantwortet sie die Frage nicht.
Casimir et Hippolyte
Ist es möglich, dies nur für eine gesamte JSON-Datei zu verwenden (ohne Angabe der Eigenschaft .id)?
Florian Castelain
1
@FlorianCastelain ja, entweder weglassen oder Punkt verwenden jq 'fromjson | .' myfile:, wo myfile enthält"{\"key\":1, \"word\":\"cat\"}"
41

Sie können die Rohausgabe (-r) verwenden, mit der Zeichen entfernt werden:

jq -r .c myfile.json | jq .id

ADDENDUM: Dies hat den Vorteil, dass es in jq 1.3 und höher funktioniert; In der Tat sollte es in jeder Version von jq funktionieren, die die Option -r hat.

Casimir et Hippolyte
quelle