Wie verwende ich "jq" in einer Shell-Pipeline?

195

Ich kann mich jqin einer Shell-Pipeline nicht "normal" verhalten. Beispielsweise:

$ curl -s https://api.github.com/users/octocat/repos | jq | cat

führt dazu jq, dass der Hilfetext * einfach ausgedruckt wird. Das gleiche passiert, wenn ich versuche, die jqAusgabe in eine Datei umzuleiten :

$ curl -s https://api.github.com/users/octocat/repos | jq > /tmp/stuff.json

Wird jqabsichtlich gerettet, wenn festgestellt wird, dass es nicht von einem tty ausgeführt wird? Wie kann ich dieses Verhalten verhindern, damit ich es jqin einer Pipeline verwenden kann?


* (Mir ist klar, dass dieses Beispiel eine nutzlose Verwendung von Katze enthält ; es dient nur zu Illustrationszwecken)

mgalgs
quelle

Antworten:

323

Sie müssen einen Filter als Argument angeben. jqVerwenden Sie den Identitätsfilter, um den JSON unverändert durch andere als die hübschen Druckfunktionen zu leiten .:

curl -s https://api.github.com/users/octocat/repos | jq '.' | cat
chepner
quelle
23
Ich habe es belassen, weil das OP es hatte; Ich nehme an, es ist nur ein Platzhalter, der angibt, dass jqsowohl aus einer Pipe gelesen als auch in eine andere Pipe geschrieben wird. Wenn der Wunsch besteht, einfach die Ausgabe von zu sehen jq, dann ist catselbst unnötig.
Chepner
3
(1) jq version 1.5 wurde so erweitert, dass die. ist in solchen Fällen nicht erforderlich. (2) Das "." Muss nicht angegeben werden.
Höhepunkt
6
@peak Es ist möglicherweise nicht für eine Pipeline erforderlich, aber ich habe 1.5 und musste das "." um die Ausgabe in eine Datei umzuleiten.
MHarris
2
Ich zitiere die .Gewohnheit, da meine Standardpraxis darin besteht, zuerst zu sehen, wie der JSON aussieht, und dann zurück zu gehen und dem Filter etwas hinzuzufügen, das meistens zitiert werden muss.
Chepper
6
@WalterTross Ja, und ich habe vor 18 Monaten in einem Kommentar erklärt, warum ich es zitiere.
Chepner
15

Ein Anwendungsfall, den ich auch häufig gemacht habe, ist "Wie konstruiere ich JSON-Daten, um sie beispielsweise in andere Shell-Befehle zu übertragen curl?" Ich mache das mit der --null-input/-nOption:

Lies überhaupt keine Eingabe! Stattdessen wird der Filter einmal ausgeführt und nullals Eingabe verwendet. Dies ist nützlich, wenn Sie es jqals einfachen Taschenrechner verwenden oder JSON-Daten von Grund auf neu erstellen.

Und ein Beispiel, das es weitergibt an curl:

jq -n '{key: "value"}' | curl -d @- \
  --url 'https://some.url.com' \
  -H 'Content-Type: application/json' \
  -H 'Accept: application/json'
mkobit
quelle
9
Das ist cool, aber nicht sicher, wie es für diese Frage relevant ist?
mgalgs
2
@mgalgs Ich wollte jqam Anfang einer Shell-Pipeline generieren / verwenden und nicht in der Mitte / am Ende, um einige Daten herauszufiltern . Das curlBeispiel ist curleinfach , aber ich habe häufig JSON-Daten von Hand eingegeben und versucht, die richtigen Zitate zu erstellen. Daher dachte ich, dass dies auch für andere nützlich sein könnte.
mkobit