2016-03-09 25 views
6

Così ho un blob JSON, come di seguito:Utilizzo di jq per estrarre i valori nell'array JSON con una chiave particolare booleano == true?

[ 
    { 
    'id': 'something', 
    'isSparse': true 
    }, 
    ... 
] 

Come faccio a scrivere un comando jq che ti filtrare questo JSON blob e mi stampare gli ID di tutte le voci della matrice che hanno isSparse == vero?

ho provato la seguente:

cat <blob> | jq -c '.[] | select(.operational | contains("true"))'

ma ottengo il seguente, perché ovviamente true è un valore booleano e non una stringa:

jq: error: boolean and string cannot have their containment checked.

risposta

2

Suppongo vogliate dire isSparse. Il filtro select accetta qualcosa che valuta un valore booleano. isSparse è già un valore booleano, quindi è sufficiente selezionarlo. contains viene utilizzato per verificare se qualcosa si trova in un altro contenitore (una stringa, una matrice, un oggetto, ecc.).

$ jq -c '.[] | select(.isSparse)' <blob> 
8

Se il compito è quello di "stampare gli ID di tutte le voci della matrice che hanno isSparse == true", un filtro JQ appropriato sarebbe:

.[] | select(.isSparse == true) | .id 

Se non v'è alcuna possibilità di duplicare valori .id, allora quanto segue potrebbe essere usato per assicurare che solo i valori distinti sono emessi:

map(select(.isSparse == true) | .id) | unique[] 

Come @JeffMercado sottolineato, se .isSparse è strettamente booleana, quindi selezionare (.isSparse) sarebbe sufficiente.

4

Aggiungo questa risposta in quanto potrebbe essere utile in futuro per uno scenario correlato. - Un esempio specifico di questo sarebbe l'accesso a un'API scritta male che restituisce la stessa coppia chiave/valore in modo diverso a seconda dell'endpoint o dei filtri utilizzati. Questo è molto fastidioso quando interfacciamento, e il valore è una stringa volte ed un booleano altre volte (Inoltre, a volte anche un numero o un numero come stringa: |)


calcolata | tostring confronterà il valore come desiderato;

cat <blob> | jq -c '.[] | select(.isSparse | tostring | contains("true"))'

o una corrispondenza esatta, piccola variante:

cat <blob> | jq -c '.[] | select((.isSparse | tostring) == "true")'