匹配孩子时,仅从相关父母那里获得价值

时间:2019-05-03 06:25:44

标签: match parent-child jq

我试图通过匹配子数组中的值来从数组中获取值,但是我尝试的所有操作都不返回任何值,也不返回父数组的所有成员。我只想要孩子匹配的父母的信息。

具体地说,我想列出其中具有端口22规则的所有AWS安全组。

这是我尝试解析的aws命令行的减少的示例输出:

{
    "SecurityGroups": [
        {
            "Description": "ssh and web group",
            "IpPermissions": [
                {
                    "FromPort": 22,
                    "ToPort": 22
                },
                {
                    "FromPort": 80,
                    "ToPort": 80
                }
            ],
            "GroupName": "ssh-web",
            "GroupId": "sg-11111111"
        },
        {
            "Description": "https group",
            "IpPermissions": [
                {
                    "FromPort": 443,
                    "ToPort": 443
                },
                {
                    "FromPort": 8443,
                    "ToPort": 8443
                }
            ],
            "GroupName": "https",
            "GroupId": "sg-22222222"
        }
    ]
}

我已经尝试过了:

aws ec2 describe-security-groups |
    jq '.SecurityGroups[] as $top |
        .SecurityGroups[].IpPermissions[] |
        select(.FromPort == 22) |
        $top'

这:

aws ec2 describe-security-groups |
    jq '. as $top |
        .SecurityGroups[].IpPermissions[] |
        select(.FromPort == 22) |
        $top'

这两个命令都显示了两个顶级数组条目,而不只是一个包含端口22条目的条目。它们只是显示了aws命令的整个输出。

下面回答这个问题的人专门提到了我实际上遇到的潜在范围界定问题,但是他对如何处理这个问题的简短描述不足以让我理解:

jq - How do I print a parent value of an object when I am already deep into the object's children?

我想看这个:

GroupName: "https"
GroupID: "sg-22222222"

我认为我不完全理解使用“ as”的方式,这可能是我的绊脚石。

2 个答案:

答案 0 :(得分:1)

如果您需要父母,不要沦为孩子。

.SecurityGroups[]
| select(any(.IpPermissions[]; .FromPort == 22))
| .GroupName, .GroupId

应该工作。

答案 1 :(得分:0)

这是一个基于用于JSON的步行路径unix工具的解决方案: jtc -在这里,您可以将查询逻辑“编码”到路径中:

bash $ <file.json jtc -x'[FromPort]:<22>d:[-3]' -y'[GroupId]' -y'[GroupName]' -l
"GroupId": "sg-11111111"
"GroupName": "ssh-web"
bash $ 

说明: 该命令中有两个步行路径(仅在-x-y部分中给出,其中公共部分(-x)附加了每个唯一部分(-y) ,它们共同构成了一条路径(相当于-w):

  • [FromPort]:<22>d: [-3]找到每条记录"FromPort": 22,并在JSON树中提升3个JSON级别(层),选择组
  • [GroupId][GroupName]-选择相应的值(每个值都在自己的步行路径中)。

-l只是为步行条目打印标签

如果您只想查找任何端口eq。 22中的FromPort(而不仅仅是IpPermissions),请改用此名称:

bash $ <file.json jtc -x'<IpPermissions>l:<22>d [-3]' -y'[GroupId]' -y'[GroupName]' -l
"GroupId": "sg-11111111"
"GroupName": "ssh-web"
bash $ 

PS>披露:我是jtc工具的创建者