배열이 포함된 2개의 JSON 파일이 있습니다(bash에서 컬을 사용하여 RestAPI에서 추출됨). 두 파일 모두 .result
상단에 유지해야 하는 개체가 있는 배열입니다. 첫 번째 필드에는 하나의 필드와 빈 필드를 .name
포함하여 많은(100개 이상의) 다른 필드가 있습니다. .ip_address
두 번째 항목에는 인터페이스, IP 주소, 다양한 필드 이름의 이름(키) 등의 추가 정보가 포함되어 있습니다. 첫 번째 파일의 키는 두 번째 파일의 키와 다르지만 관련이 있어야 합니다(물론 이전에 키 필드 이름을 변경할 수 있었고 키에 대한 데이터는 일반적으로 대소문자가 혼합되어 있습니다).
ip_address
.name
첫 번째 JSON을 동일한 필드로 덮어쓰고 추가 데이터를 추가할 수 있도록 병합하고 싶습니다 .
나는 그것이 배열 곱셈 또는 감소 및 덧셈이라는 것을 알고 있지만 내가 찾은 예제에 따르면 올바른 결과를 얻을 수 없습니다. 해결책을 주시면 감사하겠습니다.
섬기는 사람:
{
"result": [
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "SERVER1",
"ip_address": ""
},
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "SERVER2",
"ip_address": ""
},
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "server3",
"ip_address": ""
},
{
"os": "Microsoft Windows Server 2016 Standard",
"name": "server4",
"ip_address": ""
}
]
}
ips.txt
{
"result": [
{
"interface": "Intel Wireless-AC 9560 160MHz",
"cmdb.name": "server1",
"ip_address": "10.0.0.10"
},
{
"interface": "Wi-Fi",
"cmdb.name": "server2",
"ip_address": "10.0.0.10"
},
{
"interface": "Intel Dual Band Wireless-AC 8265",
"cmdb.name": "server4",
"ip_address": "10.0.0.10"
}
]
}
서버 데이터의 예상 출력은 다음과 같습니다.
{
"result": [
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "SERVER1",
"interface": "Intel Wireless-AC 9560 160MHz",
"ip_address": "10.0.0.10"
},
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "SERVER2",
"interface": "Wi-Fi",
"ip_address": "10.0.0.10"
},
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "server3",
"ip_address": ""
},
{
"os": "Microsoft Windows Server 2016 Standard",
"name": "server4",
"interface": "Intel Dual Band Wireless-AC 8265",
"ip_address": "10.0.0.10"
}
]
}
답변1
다음은 관계형 JOIN()
함수를 사용하여 키(서버)와 키(IP)의 소문자 변형에 대해 동일한 jq
두 배열의 요소를 결합합니다 . result
또한 IP 파일 배열에 인덱스를 구축하는 데에도 사용됩니다. 이 함수는 함수를 사용하여 병합된 일치하는 개체(예에서는 쌍)의 배열을 제공합니다. 결합 및 병합 후 및 키를 모두 포함하는 객체가 남으므로 각 객체에서 후자를 제거합니다.name
cmdb.name
INDEX()
result
JOIN()
add
name
cmdb.name
jq '.result = [JOIN(INDEX(input.result[]; ."cmdb.name"|ascii_downcase); .result[]; .name|ascii_downcase) | add | del(."cmdb.name")]' servers.json ips.json
표현식의 jq
형식은 다음과 같습니다.
.result =
[
JOIN(
# index on the second file's .cmdb.name key in each result object
INDEX(
input.result[];
."cmdb.name" | ascii_downcase
);
.result[]; # join on the first file's result objects
.name | ascii_downcase # match using the .name key
)
| add # merge the matched objects
| del(."cmdb.name") # delete that key we don't want
]
결과:
{
"result": [
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "SERVER1",
"ip_address": "10.0.0.10",
"interface": "Intel Wireless-AC 9560 160MHz"
},
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "SERVER2",
"ip_address": "10.0.0.10",
"interface": "Wi-Fi"
},
{
"os": "Microsoft Windows Server 2019 Standard",
"name": "server3",
"ip_address": ""
},
{
"os": "Microsoft Windows Server 2016 Standard",
"name": "server4",
"ip_address": "10.0.0.10",
"interface": "Intel Dual Band Wireless-AC 8265"
}
]
}