Search code examples
arraysjsonjqblacklist

Deriving an array from other arrays with jq (cf. Python list comprehensions)


Given the following json containing two arrays:

{"zones":["dev01","dev02","dev03","dev04","dev05","dev06","dev07","dev08","dev09","dev10","dev11","dev12","dev13","dev14","dev15","dev16","dev17","dev18","dev19","dev20"],"disabled_zones":["dev01","dev05","dev06","dev08","dev10","dev11","dev12","dev13","dev14","dev15","dev16","dev17","dev18","dev19","dev20"]}

I wish to derive a third array containing items that occur in the first array but not the second:

{"enabled_zones":["dev02","dev03","dev04","dev07","dev09"]}

I would like to use jq for this task

In python I would use a list comprehension to achieve this:

>>> zones = ["dev01","dev02","dev03","dev04","dev05","dev06","dev07","dev08","dev09","dev10","dev11","dev12","dev13","dev14","dev15","dev16","dev17","dev18","dev19","dev20"]
>>> disabled_zones = ["dev01","dev05","dev06","dev08","dev10","dev11","dev12","dev13","dev14","dev15","dev16","dev17","dev18","dev19","dev20"]
>>> enabled_zones = [x for x in zones if x not in disabled_zones]
>>> print(enabled_zones)
['dev02', 'dev03', 'dev04', 'dev07', 'dev09']

I am currently trying to loop over items in array1 using foreach and checking if they exist in array2 using in but I'm struggling with the syntax.

How can I achieve this using jq?


Solution

  • From jq manual :

    As well as normal arithmetic subtraction on numbers, the - operator can be used on arrays to remove all occurrences of the second array’s elements from the first array.

    this would do :

    jq '{ "enabled_zones": (.zones - .disabled_zones) }' data.json