4

I'm trying to use the following jq command to return a true output, if any of one of the condition is true in the list.

.Tags[] as $t| "aws:cloudformation:stack-name"| IN($t[])   

Input

 {
    "Tags": [{
            "Value": "INF-D-XX-SEC-OPNV-UW1",
            "Key": "Name"
        },
        {
            "Value": "INF-D-XX-CFS-StandardInfrastructure-UW1",
            "Key": "aws:cloudformation:stack-name"
        },
        {
            "Value": "sgOpenVPNAccess",
            "Key": "aws:cloudformation:logical-id"
        },
        {
            "Value": "UW1",
            "Key": "Location"
        },
        {
            "Value": "INF",
            "Key": "Application"
        },
        {
            "Value": "D",
            "Key": "Parent Environment"
        },
        {
            "Value": "arn:aws:cloudformation:us-west-1:111111:stack/INF-D-XX-CFS-StandardInfrastructure-UW1/1111-11-11e8-96fe-11",
            "Key": "aws:cloudformation:stack-id"
        },
        {
            "Value": "OPNV",
            "Key": "ResourceType"
        }
    ]
}

This gave me a list of returned boolean values back as the following,

--output--

true
false
false
false
false
false
false

I would like to return a single value true if one of the

Key="aws:cloudformation:stack-name" 

is detected and without given me a list of value back.

peak
  • 105,803
  • 17
  • 152
  • 177
Fang
  • 151
  • 1
  • 11

3 Answers3

6

A very efficient solution (both with respect to time and space) is easy thanks to any/2:

any(.Tags[]; .Key == "aws:cloudformation:stack-name")

This of course evaluates either to true or false. If you want true or nothing at all, you could tack on // empty to the above.

peak
  • 105,803
  • 17
  • 152
  • 177
  • This is a good solution. To add more context on my initial questions, if the above jq return "false" I would like to continue on and evaluate the json statement or else just break out of it. Is that possible? `any(.Tags[]; .Key == "aws:cloudformation:stack-name") | **continue to evaluate json if no result found**` – Fang Mar 20 '19 at 17:24
  • 1
    That's what `//` is for, as in the example in the response. – peak Mar 20 '19 at 18:18
1

Building on the previous answer by @peak, as can't post comments, you can use the '-e' flag to jq to set the exit status so you can easily chain shell commands together. This avoids having to test for the returned string.

jq -e 'any(.Tags[]; .Key == "aws:cloudformation:stack-name")' json >/dev/null && echo 'Exists' || echo 'Missing'
LennyLenny
  • 11
  • 1
0

A solution , that build a array of boolean from the .tags , and after use any to agregate all the booleans

jq '.Tags | map( .Key == "aws:cloudformation:stack-name" ) |  any ' 
EchoMike444
  • 1,513
  • 1
  • 9
  • 8