From 77521d97c77906d400c520a7d25bc9950fd5d949 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Arda=20Y=C4=B1lmaz?= Date: Thu, 8 Oct 2026 18:50:13 +0300 Subject: [PATCH] Add Image.repo_digests and clarify id/short_id docs MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Arda Yılmaz --- docker/models/images.py | 13 +++++++++++++ tests/unit/models_images_test.py | 21 +++++++++++++++++++++ 2 files changed, 34 insertions(+) diff --git a/docker/models/images.py b/docker/models/images.py index 0e8cce3f82..2df30e76bf 100644 --- a/docker/models/images.py +++ b/docker/models/images.py @@ -13,6 +13,9 @@ class Image(Model): """ An image on the server. + Note that :py:attr:`id` and :py:attr:`short_id` refer to the local image + ID (the digest of the image config), which is not the same as the digest + of the image in a registry. Use :py:attr:`repo_digests` to get the latter. """ def __repr__(self): tag_str = "', '".join(self.tags) @@ -46,6 +49,16 @@ def tags(self): tags = [] return [tag for tag in tags if tag != ':'] + @property + def repo_digests(self): + """ + The image's repository digests, as a list of strings in the form + ``repository@sha256:...``. These are the digests the image is known + by in a registry. The list is empty for images that have never been + pushed to or pulled from a registry. + """ + return list(self.attrs.get('RepoDigests') or []) + def history(self): """ Show the history of an image. diff --git a/tests/unit/models_images_test.py b/tests/unit/models_images_test.py index 3478c3fedb..1fc34ae48d 100644 --- a/tests/unit/models_images_test.py +++ b/tests/unit/models_images_test.py @@ -144,6 +144,27 @@ def test_tags(self): }) assert image.tags == [] + def test_repo_digests(self): + image = Image(attrs={ + 'RepoDigests': [ + 'busybox@sha256:abc123', + 'example.com/busybox@sha256:def456', + ], + }) + assert image.repo_digests == [ + 'busybox@sha256:abc123', + 'example.com/busybox@sha256:def456', + ] + + def test_repo_digests_empty(self): + assert Image(attrs={'RepoDigests': []}).repo_digests == [] + + def test_repo_digests_none(self): + assert Image(attrs={'RepoDigests': None}).repo_digests == [] + + def test_repo_digests_missing(self): + assert Image(attrs={}).repo_digests == [] + def test_history(self): client = make_fake_client() image = client.images.get(FAKE_IMAGE_ID)