Мне трудно использовать jq (1.5)
для анализа глубоко вложенных структур JSON, и я чувствую, что использую это неправильно. Возьмите этот пример ввода JSON:
{
"a":[],
"b":[
{"x":"bar", "s":"FX", "f":["blorg","blarg","blurb"], "v":true},
{"x":"bar", "s":"EX", "f":["blorg","blarg","bloob"], "v":false},
{"x":"bar", "s":"XT", "f":["blorg","blart","bloop"], "v":true},
{"x":"bar", "s":"IJ", "f":["blorg","bleep","glarp"], "v":true},
{"x":"foo", "s":"IX", "f":["porg","parg","pork","peep"], "v":true},
{"x":"baz", "s":"AB", "f":["zing","zang","zoop"], "v":false}
],
"c":[]
}
Извлечь объекты из списка b
, где x
- это "бар", это просто:
jq '.["b"][] | select(.x == "bar")' < file.json
Дальнейшее ограничение на объект с определенным значением s
также просто:
jq '.["b"][] | select(.x == "bar" and .s == "FX")' < file.json
Если я хочу применить тест регулярного выражения или любой другой тест, который требует строкового ввода (учитывая, что мне все еще нужны выходные данные объекта), я думаю, что у меня нет другого выбора, кроме как связывать фильтры. Например ...
Чтобы ограничиться объектами, где s
оканчивается на "X", к сожалению, в jq
нет ничего особенного:
jq '.["b"][] | select(.x == "bar" and .s.endswith("X"))' < file.json
Вместо этого я думаю, что должен сделать это:
jq '.["b"][] | select(.x == "bar") | select(.s | endswith("X"))' < file.json
Аналогично s
содержит "X":
jq '.["b"][] | select(.x == "bar") | select(.s | test("X"))' < file.json
Что хорошо, если я всегда делаю логические AND
с, но что, если я хочу сделать OR
? Например, что это за программа jq
для получения объектов, где x
означает "бар" OR
s
оканчивается на "X"? jq
имеет |OR|
фильтр?
jq '.["b"][] | select(.x == "bar") |OR| select(.s | endswith("X"))' < file.json
Или я просто делаю это неправильно? Пытаюсь ли я изобрести какой-нибудь стандартный jq
алгоритм выбора объектов?