Home > database >  How do I filter a JSON output using jq with a nested sub-key value
How do I filter a JSON output using jq with a nested sub-key value

Time:07-27

I am trying to use jq to filter the latest Docker Image version from a curl output. So far I could come up to here:

Command curl https://docker.hub.example.net/api/v1.0/projects/myapp/repositories/artifacts | jq -r '(.[] | {digest, tags})'

Output:

Note: Some sub-keys have been removed and real values have been replaced with some example values in the output.

{
  "digest": "sha256:.......",
  "tags": [
    {
      "artifact_id": 123456,
      "name": "latest",
    },
    {
      "artifact_id": 123456,
      "name": "1.0.1234567890.ab12cd3",
    }
  ]
}
{
    "digest": "sha256:.......",
    "tags": [
    {
      "artifact_id": 234567,
      "name": "1.0.1234567890.bc23de4",
    }
  ]
}
{
    "digest": "sha256:.......",
    "tags": [
    {
      "artifact_id": 345678,
      "name": "1.0.1234567890.cd34ef5",
    }
  ]
}

As you can see in the above output, only one digest has two tags with the same contents except the name sub-key values are different. One is "name": "latest" and the other is the image version (e.g. "name": "1.0.1234567890.ab12cd3"). Other digests have only one tag.

I need to get the image version from the digest that has the other tag with "name": "latest". I prefer to avoid scripted loop, if possible, and just use the jq options.

How can I achieve this?

CodePudding user response:

Use select in combination with any:

curl ... | jq -r '
  .[] | select(.tags | any(.name == "latest"))
  | first(.tags[] | select(.name != "latest")).name
'
1.0.1234567890.ab12cd3

Demo

  • Related