Skip to content

compat: Implement deprecations from Docker API v1.44#28787

Open
simek-m wants to merge 3 commits into
podman-container-tools:mainfrom
simek-m:docker-api-144-deprecations
Open

compat: Implement deprecations from Docker API v1.44#28787
simek-m wants to merge 3 commits into
podman-container-tools:mainfrom
simek-m:docker-api-144-deprecations

Conversation

@simek-m

@simek-m simek-m commented May 26, 2026

Copy link
Copy Markdown

This PR implements API deprecations to be compatible with Docker API v1.44.

  • api: Deprecate fields Container and ContainerConfig from GET /images/{name}/json
  • api: Deprecate response fields HairpinMode, LinkLocalIPv6Address,
    LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses from GET /containers/{id}/json
  • api: Deprecate is-automated filter for the GET /images/search endpoint

Deprecations in Docker Engine API v1.44 API

Deprecated: The is_automated field in the GET /images/search response has been deprecated and will always be set to false in the future because Docker Hub is deprecating the is_automated field in its search API. The deprecation is not versioned, and applies to all API versions.
Deprecated: The is-automated filter for the GET /images/search endpoint. The is_automated field has been deprecated by Docker Hub's search API. Consequently, searching for is-automated=true will yield no results. The deprecation is not versioned, and applies to all API versions.

The fields HairpinMode, LinkLocalIPv6Address, LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses available in NetworkSettings when calling GET /containers/{id}/json are deprecated and will be removed in a future release. You should instead look for the default network in NetworkSettings.Networks.

The Container and ContainerConfig fields in the GET /images/{name}/json response are deprecated and will no longer be included in API v1.45.

Fixes: https://redhat.atlassian.net/browse/RUN-3323

Checklist

Ensure you have completed the following checklist for your pull request to be reviewed:

  • Certify you wrote the patch or otherwise have the right to pass it on as an open-source patch by signing all
    commits. (git commit -s). (If needed, use git commit -s --amend). The author email must match
    the sign-off email address. See CONTRIBUTING.md
    for more information.
  • Referenced issues using Fixes: #00000 in commit message (if applicable)
  • Tests have been added/updated (or no tests are needed)
  • Documentation has been updated (or no documentation changes are needed)
  • All commits pass make validatepr (format/lint checks)
  • Release note entered in the section below (or None if no user-facing changes)

Does this PR introduce a user-facing change?

- api: is_automated field in the Compat GET /images/search response has been deprecated 
- api: is-automated filter for the Compat GET /images/search endpoint has been deprecated and will be ignored
- api: fields HairpinMode, LinkLocalIPv6Address, LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses available in NetworkSettings when calling Compat GET /containers/{id}/json are deprecated
- api: Container and ContainerConfig fields in the Compat GET /images/{name}/json response are deprecated

Questions and Notes

  • The changes to is_automated are according to the Docker docs not versioned, and apply to all API versions. Hence, I'm not sure if my approach is correct.
  • Should there be any warning log? I couldn't find any example of that in the existing code.
  • The PR version gated the ContainerConfig field for v1.45 so I kept the version. [compat api] Remove ContainerConfig field #27172
  • The test mocked output in search_mock_registry.go includes is_automated and I kept it there.

@simek-m

simek-m commented May 26, 2026

Copy link
Copy Markdown
Author

It's looks like that the mocked output with is_automated mentioned above is an issue (or the version gate not differentiating between libpod and compat?). I'll fix it.

[+1031s] Summarizing 1 Failure:
[+1031s]   [FAIL] Podman search podman search with mock registry [It] podman search with filter is-automated
[+1031s]   /var/tmp/go/src/github.com/containers/podman/test/e2e/search_test.go:185

EDIT:
Fixed in e6c98e5 and the additional failures appear not to be related to changes in this branch.

@simek-m simek-m force-pushed the docker-api-144-deprecations branch from e6c98e5 to e3be1af Compare May 26, 2026 15:19
@github-actions github-actions Bot added the kind/api-change Change to remote API; merits scrutiny label May 26, 2026

@inknos inknos left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Most likely you also want some versioned tests against the compat endpoints like in this previous PR about deprecating endpoints. https://github.com/containers/podman/pull/26213/changes

also, minor thing, the fixup commit could be squashed imho

Comment on lines +54 to +57
// https://docs.docker.com/reference/api/engine/version-history/#v144-api-changes
if _, err := apiutil.SupportedVersion(r, ">=1.44.0"); err == nil && !utils.IsLibpodRequest(r) {
delete(query.Filters, "is-automated")
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

stated in docker's api

The deprecation is not versioned, and applies to all API versions.

therefore I believe it should just be deleted, not only if version >= 1.44

Comment on lines 87 to 88
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

probably the Automated field should be zeroed out before writing to the response since it's documented to be always false. also, I would verify what docker wants, probably a bool and not a string. Then I would add a specific test for this field and its type

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1 to this.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@simek-m ptal when you have capacity :)

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@inknos I thought the agreement was not to zero it and be transparent - just return what's received in the response. The docs state:

will always be set to false in the future

and I think that if Docker Hub returns true for some reason (IIRC it happened when testing), it should not be changed to false here. Now, the Docker structure is used directly for the response.

But I can zero it if you think that's better.

Comment thread pkg/domain/entities/types/images.go Outdated
Stars int
// Official indicates if it's an official image.
Official string
// Deprecated: the "is_automated" field is deprecated and will always be "false".

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we are not really deprecating this, but we want to touch the compat struct only, which we don't have. Therefore, I believe it's better to create a compat struct with the correct docker types and the deprecation should happen there. this struc is used elsewhere and we don't deprecate this option for the libpod code

@simek-m

simek-m commented May 27, 2026

Copy link
Copy Markdown
Author

Thank you, @inknos

Regarding is_automated / is-automated:

  • How I approached the deprecation is definitely wrong, but I'm now not sure if there should be any other action on the filter side apart from documenting it. My reasoning is that they state searching for is-automated=true will yield no results and it should be transparent to the consumer, i.e. searching for is-automated=true will yield no results.
  • Likewise, I'm not sure the is_automated field should be zeroed or be transparent and pass it as it's received (maybe omitempty?). It looks like it's a Docker Hub only thing, though.
  • The compat response struct with a deprecation is a very good point, for the record the current response looks like this:
[
  {
    "Index": "docker.io",
    "Name": "docker.io/library/alpine",
    "Description": "A minimal Docker image based on Alpine Linux with a complete package index and only 5 MB in size!",
    "Stars": 11509,
    "Official": "[OK]",
    "Automated": "",
    "Tag": ""
  },
  {
    "Index": "docker.io",
    "Name": "docker.io/alpine/git",
    "Description": "A  simple git container running in alpine linux, especially for tiny linux distro.",
    "Stars": 252,
    "Official": "",
    "Automated": "[OK]",
    "Tag": ""
  },
  {
    "Index": "docker.io",
    "Name": "docker.io/alpine/socat",
    "Description": "Run socat command in alpine container",
    "Stars": 115,
    "Official": "",
    "Automated": "[OK]",
    "Tag": ""
  },
  {
    "Index": "docker.io",
    "Name": "docker.io/alpine/curl",
    "Description": "",
    "Stars": 12,
    "Official": "",
    "Automated": "",
    "Tag": ""
  },
  {
    "Index": "docker.io",
    "Name": "docker.io/alpine/helm",
    "Description": "Auto-trigger docker build for kubernetes helm when new release is announced",
    "Stars": 70,
    "Official": "",
    "Automated": "",
    "Tag": ""
  }
]

and the Docker one like this:

[
  {
    "star_count": 11509,
    "is_official": true,
    "name": "alpine",
    "is_automated": false,
    "description": "A minimal Docker image based on Alpine Linux with a complete package index and only 5 MB in size!"
  },
  {
    "star_count": 252,
    "is_official": false,
    "name": "alpine/git",
    "is_automated": false,
    "description": "A  simple git container running in alpine linux, especially for tiny linux distro."
  },
  {
    "star_count": 115,
    "is_official": false,
    "name": "alpine/socat",
    "is_automated": false,
    "description": "Run socat command in alpine container"
  },
  {
    "star_count": 12,
    "is_official": false,
    "name": "alpine/curl",
    "is_automated": false,
    "description": ""
  },
  {
    "star_count": 70,
    "is_official": false,
    "name": "alpine/helm",
    "is_automated": false,
    "description": "Auto-trigger docker build for kubernetes helm when new release is announced"
  }
]

What do you think?

(The fixup commits were not autosquashed, because I'd already opened the PR and wanted to make clear what was changed after and avoid force-pushing.)

EDIT:
Discussed elsewhere and the plan is:

  • Introduce compat structure matching the Docker one (can be directly imported).
  • Document in Swagger.

@TomSweeneyRedHat

Copy link
Copy Markdown
Contributor

restarted the failing tests.

@simek-m simek-m force-pushed the docker-api-144-deprecations branch from e3be1af to 41f83b4 Compare June 1, 2026 11:23
@simek-m

simek-m commented Jun 1, 2026

Copy link
Copy Markdown
Author
[
  {
    "star_count": 11513,
    "is_official": true,
    "name": "alpine",
    "is_automated": false,
    "description": "A minimal Docker image based on Alpine Linux with a complete package index and only 5 MB in size!"
  }
]
  • compat (now matching the Docker response format):
[
  {
    "star_count": 11513,
    "is_official": true,
    "name": "docker.io/library/alpine",
    "is_automated": false,
    "description": "A minimal Docker image based on Alpine Linux with a complete package index and only 5 MB in size!"
  }
]
  • libpod (that was the original format of the compat endpoint too):
[
  {
    "Index": "docker.io",
    "Name": "docker.io/library/alpine",
    "Description": "A minimal Docker image based on Alpine Linux with a complete package index and only 5 MB in size!",
    "Stars": 11513,
    "Official": "[OK]",
    "Automated": "",
    "Tag": ""
  }
]

@simek-m simek-m force-pushed the docker-api-144-deprecations branch from 41f83b4 to e8c9311 Compare June 2, 2026 11:54
i = 1
# Need to explicitly set start method
# # https://docs.python.org/dev/library/multiprocessing.html#contexts-and-start-methods
mp.set_start_method('fork')

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The multiprocessing sub-tests weren't actually correctly asserted and they failed silently. Simplified that with sequential sub-tests.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@simek-m you should rebase to main if you didn't so ci jobs will show up and run the tests

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@inknos I did, but I think the CI workflow needs to be approved.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

don't see the ci runs, but if you do, everything's correct, so apologies if that's the case and if you did rebase already 🥲

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, need to apologize :) I checked that the CI changes are in this branch, but rebased again to the latest.

It looks like it won't run automatically, though:
Screenshot 2026-06-02 at 15 17 27

…dpoint

The Docker API in version 1.44 deprecates the is_automated field for
the GET /images/search endpoint. The is_automated field has been deprecated
by Docker Hub's search API. Consequently, searching for is-automated=true
will yield no results.

The Docker API in version 1.44 deprecates the is_automated field
in the GET /images/search response and will always be set to false in the
future because Docker Hub is deprecating the is_automated field in its search API.

Return struct moby/api for the compat endpoint that matches the Docker
API response format and deprecates is_automated.

Update test_v2_0_0_image.py::ImageTestCase::test_search_compat
to verify returned format and fix subtests not being asserted (remove mp).

Fixes: https://redhat.atlassian.net/browse/RUN-3323

Signed-off-by: Marek Simek <msimek@redhat.com>
@simek-m simek-m force-pushed the docker-api-144-deprecations branch from e8c9311 to c3ed8ec Compare June 2, 2026 13:18
@inknos

inknos commented Jun 2, 2026

Copy link
Copy Markdown
Contributor

I'd wait for the ci to be run @Honny1 do you have permissions to approve? then LGTM

@Honny1

Honny1 commented Jun 8, 2026

Copy link
Copy Markdown
Contributor

I'd wait for the ci to be run @Honny1 do you have permissions to approve? then LGTM

CI is green.

@simek-m

simek-m commented Jun 8, 2026

Copy link
Copy Markdown
Author

I'd wait for the ci to be run @Honny1 do you have permissions to approve? then LGTM

CI is green.

@Honny1 Thank you, it looks like that even with Nicola's approval, the PR is shown as "review required" when I filter it.

@Honny1 Honny1 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would like to have versioned compat API tests for the container inspect and image inspect deprecations.

Comment thread pkg/api/handlers/swagger/responses.go
@Honny1

Honny1 commented Jun 10, 2026

Copy link
Copy Markdown
Contributor

PTAL @podman-container-tools/podman-maintainers

@simek-m

simek-m commented Jun 10, 2026

Copy link
Copy Markdown
Author

@Honny1

I would like to have versioned compat API tests for the container inspect and image inspect deprecations.

  • ImageInspect.Container - it's never populated and omitempty.
  • ImageInspect.ContainerConfig - there is already a test in
    t GET /v1.44/images/$iid/json 200 \

It's trickier with the HairpinMode, LinkLocalIPv6Address,
LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses. There are currently no version gates that could be tested.

  • I only considered the changes in v1.44 in isolation and there was no removal version:

The fields HairpinMode, LinkLocalIPv6Address, LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses available in NetworkSettings when calling GET /containers/{id}/json are deprecated and will be removed in a future release. You should instead look for the default network in NetworkSettings.Networks.

But version v1.52 removes them:

GET /containers/{id}/json: the NetworkSettings no longer returns the deprecated Bridge, HairpinMode, LinkLocalIPv6Address, LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses, EndpointID, Gateway, GlobalIPv6Address, GlobalIPv6PrefixLen, IPAddress, IPPrefixLen, IPv6Gateway, and MacAddress fields. These fields were deprecated in API v1.21 (docker v1.9.0) but kept around for backward compatibility.

  • This PR marked the fields HairpinMode, LinkLocalIPv6Address,
    LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses deprecated on the InspectNetworkSettings and InspectBasicNetworkConfig in libpod/define/container_inspect.go and that's arguably wrong, because the structures are shared by compat and libpod. I have to change that.

  • The fields HairpinMode, LinkLocalIPv6Address, LinkLocalIPv6PrefixLen are not populated at all (they are serialized as their zero values). For proper version gating, the code needs to be refactored, because the handler doesn't populate the fields directly, but uses helpers.

  • The fields were deprecated in a previous change on LegacyNetworkSettings. That's the compat structure that should be version-gated. To do it properly in the handler, the code needs to be refactored, because the handler doesn't populate it directly, but uses a LibpodToContainerJSON helper.

TLDR.: I remove the deprecations from shared structures and try to introduce a version gating for <v1.52 for the fields. It might not be worth it for the not populated fields.

@inknos

inknos commented Jun 10, 2026

Copy link
Copy Markdown
Contributor

TLDR.: I remove the deprecations from shared structures and try to introduce a version gating for <v1.52 for the fields. It might not be worth it for the not populated fields.

we have to go there eventually, but since we are ~8 versions away from 1.52 I hope this does not introduce more confusion going forward to what's fixed and what's not. I would say to keep it simple, test what we can concerning 1.44 and move on

simek-m added 2 commits June 11, 2026 13:49
The Docker API 1.44 deprecates the fields HairpinMode, LinkLocalIPv6Address,
LinkLocalIPv6PrefixLen, SecondaryIPAddresses, SecondaryIPv6Addresses available in
NetworkSettings when calling GET /containers/{id}/json and will be removed in a future release.
You should instead look for the default network in NetworkSettings.Networks.

The fields are removed in 1.52. Version gate SecondaryIPAddresses, SecondaryIPv6Addresses
in the handler and update test. HairpinMode, LinkLocalIPv6Address, LinkLocalIPv6PrefixLen
are not returned by the compat endpoint as the response is serialized
to the moby/moby/api structure missing these fields.

Fixes: https://redhat.atlassian.net/browse/RUN-3323

Signed-off-by: Marek Simek <msimek@redhat.com>
…{name}/json

The Docker API deprecates Container and ContainerConfig fields in
the GET /images/{name}/json response are deprecated and
they will no longer be included in API v1.45.

Fixes: https://redhat.atlassian.net/browse/RUN-3323

Signed-off-by: Marek Simek <msimek@redhat.com>
@simek-m simek-m force-pushed the docker-api-144-deprecations branch from c3ed8ec to f9dccd1 Compare June 11, 2026 11:50
@simek-m

simek-m commented Jun 11, 2026

Copy link
Copy Markdown
Author

TLDR.: I remove the deprecations from shared structures and try to introduce a version gating for <v1.52 for the fields. It might not be worth it for the not populated fields.

we have to go there eventually, but since we are ~8 versions away from 1.52 I hope this does not introduce more confusion going forward to what's fixed and what's not. I would say to keep it simple, test what we can concerning 1.44 and move on

@inknos
Yeah, unfortunately it's already confusing, because some deprecations/removals from v1.52 are already in main.

@Honny1
I updated the PR and in b566483:

  • Reverted the deprecations on structures used by libpod.
  • SecondaryIPAddresses, SecondaryIPv6Addresses were already deprecated. I added version gating to the handler for version v1.52 where it's removed and updated test to check it's present before v1.52.
  • HairpinMode, LinkLocalIPv6Address,
    LinkLocalIPv6PrefixLen were already removed as a by-effect of embedding moby/moby/api structure in LegacyNetworkSettings (deprecated) and the fields are no longer present there. libpod still has them.

@packit-as-a-service

Copy link
Copy Markdown

tmt tests failed for commit f9dccd1. @lsm5, @psss, @thrix please check.

@Honny1 Honny1 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just a possible linter issue.

Comment thread pkg/api/handlers/compat/images.go

@Honny1 Honny1 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@simek-m

simek-m commented Jun 12, 2026

Copy link
Copy Markdown
Author

Updated the release notes - I forgot to make it clear that it relates to the Compat endpoints.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

kind/api-change Change to remote API; merits scrutiny

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants