How to remove images from the private docker registry?

I am running a private docker registry and I want to delete all images except latest from the repository. I do not want to delete the entire repository, but only some images inside it. The docs APIs don't mention a way to do this, but maybe this is possible?

+60
docker docker-registry
Aug 21 '14 at 22:09
source share
7 answers

You cannot currently use the Registry API for this task. This allows you to delete the repository or specific tag.

Typically, deleting a repository means that all tags associated with this repo are deleted.

Removing a tag means that the link between the image and the tag is removed.

None of the above will delete a single image. They are left on your disk.




Bypass

For this workaround, you need to save your docker files.

A workaround for your solution would be to remove all but the latest tags, and thus the ability to remove links to related images. You can then run this script to remove all images that are not referenced by tags or ancestors of any image used.

Terminology (images and tags)

Consider an image graph like this, where the capital letters ( A , B , ...) are short image identifiers, and <- means that the image is based on another image:

  A <- B <- C <- D 

Now we add tags to the image:

  A <- B <- C <- D | | | <version2> <version1> 

Here, the <version1> refers to image C , and the <version2> refers to image D

Clarification of your question

In your question, you said you want to delete

all images but latest

. Now this terminology is not entirely correct. You have mixed images and tags. Looking at the graph, I think you will agree that the <version2> is the latest version. In fact, according to this question , you can have a tag that represents the latest version:

  A <- B <- C <- D | | | <version2> | <latest> <version1> 

Since the <latest> refers to image D , I ask you: do you really want to delete everything except image D ? Probably not!

What happens if you remove the tag?

If you remove the <version1> tag using the Docker REST API, you will get the following:

  A <- B <- C <- D | <version2> <latest> 

Remember: Docker will never delete an image! Even if this happened, in this case he cannot delete the image, since the image C is part of the ancestor for the image D that is marked.

Even if you use this script , the image will not be deleted.

When the image can be deleted

Provided that you can control when someone can pull or click on your registry (for example, by disabling the REST interface). You can remove an image from a graphic image if there is no other image on it, and none of them refers to it.

Note that in the following graph, the image of D not based on C , but on B Therefore, D is independent of C If you remove the <version1> in this graph, the C image will not be used by any image and this script can remove it.

  A <- B <--------- D \ | \ <version2> \ <latest> \ <- C | <version1> 

After cleaning, your graph graph looks like this:

  A <- B <- D | <version2> <latest> 

Is this what you want?

+57
Aug 28 '14 at 14:20
source share
— -

The current registry v2 now supports deletion using DELETE /v2/<name>/manifests/<reference>

See: https://github.com/docker/distribution/blob/master/docs/spec/api.md#deleting-an-image

+15
Apr 28 '16 at 14:40
source share

Problem 1

You mentioned that this is your private docker registry, so you probably need to check the “Registry API” instead of the Hub API Dock , which is the link you provided.

Problem 2

docker registry API is a client / server protocol, before the server is implemented, whether images are deleted in the background. (I think)

 DELETE /v1/repositories/(namespace)/(repository)/tags/(tag*) 

Detailed description

Below I will tell you how it works now from your description as my understanding of your questions.

You start the docker private registry, I use by default and listen in 5000 port

 docker run -d -p 5000:5000 registry 

Then I put a local image and insert it.

 $ docker tag ubuntu localhost:5000/ubuntu $ docker push localhost:5000/ubuntu The push refers to a repository [localhost:5000/ubuntu] (len: 1) Sending image list Pushing repository localhost:5000/ubuntu (1 tags) 511136ea3c5a: Image successfully pushed d7ac5e4f1812: Image successfully pushed 2f4b4d6a4a06: Image successfully pushed 83ff768040a0: Image successfully pushed 6c37f792ddac: Image successfully pushed e54ca5efa2e9: Image successfully pushed Pushing tag for rev [e54ca5efa2e9] on {http://localhost:5000/v1/repositories/ubuntu/tags/latest} 

After that, you can use the Registry API to check it in your private docker registry.

 $ curl -X GET localhost:5000/v1/repositories/ubuntu/tags {"latest": "e54ca5efa2e962582a223ca9810f7f1b62ea9b5c3975d14a5da79d3bf6020f37"} 

Now I can remove the tag using this API!

 $ curl -X DELETE localhost:5000/v1/repositories/ubuntu/tags/latest true 

Check again that the tag does not exist in your private registry server

 $ curl -X GET localhost:5000/v1/repositories/ubuntu/tags/latest {"error": "Tag not found"} 
+13
Aug 22
source share

I had the same problem with my registry, and I tried the solution listed below from the blog page. It is working.

Step 1: Directory List

You can list your directories by calling this URL:

 http://YourPrivateRegistyIP:5000/v2/_catalog 

The answer will be in the following format:

 { "repositories": [ <name>, ... ] } 

Step 2: Tag Identification for the Linked Directory

You can specify the tags for your catalog by calling this URL:

 http://YourPrivateRegistyIP:5000/v2/<name>/tags/list 

The answer will be in the following format:

 { "name": <name>, "tags": [ <tag>, ... ] 

}

Step 3: Display the manifest value for the associated tag

You can run this command in the docker registry container:

 curl -v --silent -H "Accept: application/vnd.docker.distribution.manifest.v2+json" -X GET http://localhost:5000/v2/<name>/manifests/<tag> 2>&1 | grep Docker-Content-Digest | awk '{print ($3)}' 

The answer will be in the following format:

 sha256:6de813fb93debd551ea6781e90b02f1f93efab9d882a6cd06bbd96a07188b073 

Run the command below with the manifest value:

 curl -v --silent -H "Accept: application/vnd.docker.distribution.manifest.v2+json" -X DELETE http://127.0.0.1:5000/v2/<name>/manifests/sha256:6de813fb93debd551ea6781e90b02f1f93efab9d882a6cd06bbd96a07188b073 

Step 4: Delete Marked Manifests

Run this command in the docker registration container:

 bin/registry garbage-collect /etc/docker/registry/config.yml 

Here is my config.yml

 root@c695814325f4:/etc# cat /etc/docker/registry/config.yml version: 0.1 log: fields: service: registry storage: cache: blobdescriptor: inmemory filesystem: rootdirectory: /var/lib/registry delete: enabled: true http: addr: :5000 headers: X-Content-Type-Options: [nosniff] health: storagedriver: enabled: true interval: 10s threshold: 3 
+12
May 4, '17 at 15:20
source share

It is really ugly, but it works, the text is tested in the registry: 2.5.1. I was not able to get the removal to work smoothly even after updating the configuration to enable the removal. The identifier was really hard to get, I had to log in to get it, maybe some misunderstanding. In any case, the following works:

  • Container entry

     docker exec -it registry sh 
  • Define the variables appropriate for your version of the container and container:

     export NAME="google/cadvisor" export VERSION="v0.24.1" 
  • Go to the registry directory:

     cd /var/lib/registry/docker/registry/v2 
  • Delete the files associated with your hash:

     find . | grep `ls ./repositories/$NAME/_manifests/tags/$VERSION/index/sha256`| xargs rm -rf $1 
  • Delete manifests:

     rm -rf ./repositories/$NAME/_manifests/tags/$VERSION 
  • Exit

     exit 
  • Launch GC:

     docker exec -it registry bin/registry garbage-collect /etc/docker/registry/config.yml 
  • If everything is done correctly, some information about deleted blobs is displayed.

+4
Oct 27 '16 at 20:51
source share

There are several clients (in Python, Ruby, etc.) that do just that. For my taste, it’s not always possible to install a runtime (such as Python) on my registry server, just to save my registry!




So deckschrubber is my solution:

 go get github.com/fraunhoferfokus/deckschrubber $GOPATH/bin/deckschrubber 

Images older than a certain age are automatically deleted. Age can be specified using -year , -month , -day or a combination thereof:

 $GOPATH/bin/deckschrubber -month 2 -day 13 -registry http://registry:5000 



UPDATE : here is a short introduction to deckschrubber.

+1
May 15 '17 at 1:18 p.m.
source share

This docker image includes a bash script that you can use to remove images from the remote registry v2: https://hub.docker.com/r/vidarl/remove_image_from_registry/

0
Sep 14 '17 at 10:38 on
source share



All Articles