Comment utiliser `jq` dans un pipeline shell?

195

Je n'arrive pas à me jqcomporter "normalement" dans un pipeline shell. Par exemple:

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

entraîne jqsimplement l'impression de son texte d'aide *. La même chose se produit si j'essaie de rediriger jqla sortie de vers un fichier:

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

Est-ce qu'il jqrenonce délibérément s'il détermine qu'il n'est pas exécuté à partir d'un terminal? Comment puis-je empêcher ce comportement afin de pouvoir l'utiliser jqdans un pipeline?


* (Je me rends compte que cet exemple contient une utilisation inutile de chat ; c'est à des fins d'illustration uniquement)

mgalgs
la source

Réponses:

323

Vous devez fournir un filtre comme argument. Pour passer le JSON à travers non modifié autre que la jolie impression jqfournit par défaut, utilisez le filtre d'identité .:

curl -s https://api.github.com/users/octocat/repos | jq '.' | cat
chepner
la source
23
Je l'ai laissé parce que le PO en avait; Je suppose que c'est juste un espace réservé pour indiquer que jqc'est à la fois la lecture d'un tuyau et l'écriture sur un autre tuyau. Si le désir est simplement de voir la sortie de jq, alors catlui-même n'est pas nécessaire.
chepner
3
(1) jq version 1.5 a été amélioré afin que le. est inutile dans des cas comme celui-ci. (2) Il n'est pas nécessaire de citer le ".".
pic
6
@peak Ce n'est peut-être pas nécessaire pour un pipeline, mais j'en ai 1.5 et j'ai dû fournir le "." pour rediriger la sortie vers un fichier.
MHarris
2
Je cite l' .habitude, car ma pratique standard consiste à voir d'abord à quoi ressemble le JSON, puis à revenir en arrière et à commencer à ajouter au filtre, qui devra le plus souvent être cité.
chepner
6
@WalterTross Oui, et j'ai expliqué dans un commentaire il y a 18 mois pourquoi je le cite.
chepner
15

Un cas d'utilisation que je me suis retrouvé à faire fréquemment est également "Comment puis-je construire des données JSON à fournir dans d'autres commandes shell, par exemple curl?" Pour ce faire, j'utilise l' --null-input/-noption:

Ne lisez aucune entrée! Au lieu de cela, le filtre est exécuté une fois en utilisant nullcomme entrée. Ceci est utile lors de l'utilisation jqcomme une simple calculatrice ou pour construire des données JSON à partir de zéro.

Et un exemple en le passant curl:

jq -n '{key: "value"}' | curl -d @- \
  --url 'https://some.url.com' \
  -H 'Content-Type: application/json' \
  -H 'Accept: application/json'
mkobit
la source
9
C'est cool, mais vous ne savez pas en quoi cela est pertinent pour cette question?
mgalgs
2
@mgalgs Je me suis retrouvé à vouloir générer / utiliser jqau début d'un pipeline shell plutôt qu'au milieu / fin pour filtrer certaines données. L' curlexemple est basique, mais je me suis souvent retrouvé à taper à la main des données JSON curlet à essayer de bien citer, alors j'ai pensé que cela pourrait être utile à d'autres également.
mkobit