在 bash 脚本中使用 jq 获取具有特定值模式的元素

在 bash 脚本中使用 jq 获取具有特定值模式的元素

我在 shell 脚本中调用 homebrew api,目的是在尝试安装该项目之前获取该项目的应用程序名称。幸运的是,API 在一个名为 的元素中提供了这一点artifacts。不幸的是,artifacts没有更多的键来仅选择一个元素。它可以是任意顺序的对象和数组的混合。

Google Chrome 的示例数据片段:

{
   "name":[
      "Google Chrome"
   ],
   "artifacts":[
      [
         "Google Chrome.app"
      ]
   ]
}

但 docker 却是另一回事:

{
   "name":[
      "Docker"
   ],
   "artifacts":[
       {
         "trash":[
           "$(brew --prefix)/bin/docker-compose.backup",
           "$(brew --prefix)/bin/docker.backup"
         ]
      },
      [
         "docker.app"
      ]
   ]
}

所以我不能artifacts像这样从 shell 脚本中获取元素 0 。

artifacts=$(curl -s "https://formulae.brew.sh/api/cask/google-chrome.json" | jq -r '.artifacts[0][0]')

有没有办法使用 jq 在元素中搜索artifacts以 *.app 结尾的模式的值?我能想出的最好的伪代码是这样的,但是我在尝试引用 $element 时陷入了一些混乱

# $cask is determined by a list the script loops through ('google-chrome' is one example)
for element in $(curl -s "https://formulae.brew.sh/api/cask/$cask.json" | jq -r '.artifacts'); do
    # if $element is an array and it's value ends with "*.app"
        # assign to a variable for later use
done

这里有一个jqplay片段更复杂的 JSON 返回之一。您将看到一个数组的一部分,其中包含唯一的值“docker.app”。这就是我想要的目标。

答案1

jq查询适用于 Docker 的 JSON:

.artifacts[] | arrays[0] | select(endswith(".app"))

过滤arrays器从 的元素中选择数组artifacts,然后我们可以查找这些数组的第一个元素以查找以 结尾的元素.app

答案2

类似的查询正如穆鲁所拥有的artifacts,但如果数组中的任何条目以字符串 结尾,则返回任何数组中的所有工件.app

.artifacts[] | select(type == "array" and any(endswith(".app")))[]

或者,

.artifacts[] | arrays | select(any(endswith(".app")))[]

因此,如果应用程序有一些伪影thething.app someotherthing.quux在同一个数组中,然后返回两者。

相关内容