У меня есть json с повторяющимися родительскими объектами. Мне нужно объединить все дочерние элементы под одним родителем, используя jq в bash

У меня есть json с повторяющимися родительскими объектами. Мне нужно объединить все дочерние элементы под одним родителем, используя jq в bash. Ниже представлен массив json. Ниже источника находятся родители. Мне нужно взять один родительский элемент и объединить его со всеми дочерними элементами. Возможно ли это с jq?

 [
        {
            "source": null,
            "target": {
                "id": 1
            }
        },
        {
            "source": {
                "id": 1
            },
            "target": {
                "id": 2
            }
        },
        {
            "source": {
                "id": 1
            },
            "target": {
                "id": 3
            }
        },
        {
            "source": {
                "id": 1
            },
            "target": {
                "id": 10
            }
        },
        {
            "source": {
                "id": 1
            },
            "target": {
                "id": 11
            }
        }
    ]

Ожидаемый результат: -

 [
        {
            "source": null,
            "target": {
                "id": 1
            }
        },
        {
            "source": {
                "id": 1
            },
            "target-1": {
                "id": 2
            },
            "target-2": {
                "id": 3
            },
            "target-3": {
                "id": 10
            },
            "target-4": {
                "id": 11
            }
        }
    ]

Это было бы немного проще, если бы вы хотели {"source-null": [1], "source-1": [1, 2, 3, 10, 11]} в качестве вывода. Есть ли причина для выбранного формата?

Charles Duffy 15.12.2020 15:03

Кроме того, почему именно "target", а не "target-1" в качестве идентификатора первой цели для "source": null?

Charles Duffy 15.12.2020 15:04

[{"source": [1]}, {"source":1, "target": [ 2, 3, 10, 11]}}] Это тоже нормально. Я должен сделать запрос API с этими идентификаторами и должен показать результат исходного идентификатора в качестве родительского и целевого идентификатора в качестве дочернего.

Srinivas B 15.12.2020 15:08

Эээ, вы имеете в виду [{"source": null, "target": [1]}, {"source": 1, "target": [2,3,10,11]}], конечно?

Charles Duffy 15.12.2020 15:13

Думаю, я могу перебирать эти идентификаторы с помощью cat stack.json | jq .[1].target[2] и делать вызовы API.

Srinivas B 15.12.2020 15:16

Я не понимаю, зачем вам это нужно, но ведь вы не поделились своим API.

Charles Duffy 15.12.2020 15:17

И кстати, вообще никогда не бегайте cat somefile | ...; более эффективно запускать ... <somefile (или его эквивалент <somefile ...), который дает программе ... прямой дескриптор файла на somefile, вместо того, чтобы давать ей только FIFO для чтения с выводом из отдельного исполняемого файла cat (который не является частью оболочки ). FIFO менее гибкие - они не доступны для поиска и могут быть прочитаны только один раз от начала до конца, поэтому программы, которые в противном случае могли бы захотеть распараллелить или заранее узнать общий размер ввода (или просто пропустить до конца ввода) не может этого сделать, когда им дают только FIFO.

Charles Duffy 15.12.2020 15:20

Это требование, а API — внутренняя вещь. О кошке.... просто для понимания я использовал. Обычно jq .[1].target[2] stack.json я так и использую.

Srinivas B 15.12.2020 15:26

Вы наверняка ищете что-то подобное jqplay.org/s/i-KJ7v2ee-

oguz ismail 15.12.2020 15:41

@oguzismail точно. Большое спасибо

Srinivas B 15.12.2020 16:13
Как сделать HTTP-запрос в Javascript?
Как сделать HTTP-запрос в Javascript?
В JavaScript вы можете сделать HTTP-запрос, используя объект XMLHttpRequest или более новый API fetch. Вот пример для обоих методов:
0
10
372
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

jq имеет удобный оператор группировки.

Поскольку вы ясно дали понять в комментариях, что цель этого вопроса - узнать, как выполнить группировку, а точный формат вывода является второстепенным, примером такой группировки может быть:

jq 'group_by(.source?.id // "") | [.[] | {"\(.[0].source?.id)": [.[].target.id]}] | add'

... генерация вывода (для вашего ввода):

{
  "1": [
    2,
    3,
    10,
    11
  ],
  "null": [
    1
  ]
}

Вывод не является массивом, будет несколько родителей и дочерних элементов, а между объектами отсутствуют ,. Непосредственно число, поскольку приходит ключ json, который трудно отследить с помощью автоматизации. Спасибо за быстрый ответ. Я буду работать отсюда.

Srinivas B 15.12.2020 15:30

Другие вопросы по теме