229

By default, if I issue command:

sudo docker pull ruby:2.2.1

it will pull from the docker.io offical site by default.

Pulling repository docker.io/library/ruby

How do I change it to my private registry. That means if I issue

sudo docker pull ruby:2.2.1

it will pull from my own private registry, the output is something like:

Pulling repository my_private.registry:port/library/ruby
peterh
  • 11,875
  • 18
  • 85
  • 108
mainframer
  • 20,411
  • 12
  • 49
  • 68
  • 1
    Were you able to find a way to make it work? I was looking for exact the same thing. I'm using nexus as my docker private registry. I don't want to use my domain name and port number in my docker pull command. – Dinesh Dec 16 '19 at 19:55

11 Answers11

83

UPDATE: Following your comment, it is not currently possible to change the default registry, see this issue for more info.

You should be able to do this, substituting the host and port to your own:

docker pull localhost:5000/registry-demo

If the server is remote/has auth you may need to log into the server with:

docker login https://<YOUR-DOMAIN>:8080

Then running:

docker pull <YOUR-DOMAIN>:8080/test-image
Guy
  • 10,931
  • 5
  • 36
  • 47
  • 43
    `docker pull :8080/test-image` was ok. But what I want is `docker pull test-image`, whichi is without spesifying the DOMAIN and Port and without login. – mainframer Oct 10 '15 at 13:35
  • 4
    I have updated my answer based on your comment. It's not currently possible to set a default registry – Guy Oct 10 '15 at 13:39
  • It's not likely to ever become possible to set a different default registry either, due to it breaking the default namespace that most images rely on – Matt Nov 06 '17 at 01:52
  • 1
    They could do something like `@scopes` in npm to introduce new namespaces without conflict with existing. Having the registry hostname included in the image name makes registry caching/proxying/lock down inside a company or project difficult. This describes it well: http://www.informit.com/articles/article.aspx?p=2464012&seqNum=3 – Alexander Klimetschek Jul 25 '18 at 20:52
  • 1
    This PR seems to be the most recent discussion of that topic: https://github.com/moby/moby/pull/34319 – Alexander Klimetschek Jul 25 '18 at 21:25
55

There is the use case of a mirror of Docker Hub (such as Artifactory or a custom one), which I haven't seen mentioned here. This is one of the most valid cases where changing the default registry is needed.

Luckily, Docker (at least version 19.03.3) allows you to set a mirror (tested in Docker CE). I don't know if this will work with additional images pushed to that mirror that aren't on Docker Hub, but I do know it will use the mirror instead. Docker documentation: https://docs.docker.com/registry/recipes/mirror/#configure-the-docker-daemon.

Essentially, you need to add "registry-mirrors": [] to the /etc/docker/daemon.json configuration file. So if you have a mirror hosted at https://my-docker-repo.my.company.com, your /etc/docker/daemon.json should contain:

{
  "registry-mirrors": ["https://my-docker-repo-mirror.my.company.com"]
}

Afterwards, restart the Docker daemon. Now if you do a docker pull postgres:12, Docker should fetch the image from the mirror instead of directly from Docker Hub. This is much better than prepending all images with my-docker-repo.my.company.com

Gakio
  • 783
  • 6
  • 7
  • 2
    Instead of asking clients to setup this config, is it possible to make the company's network dns to redirect the request to the mirror? – Sam Thomas Nov 04 '20 at 21:12
  • 5
    @SamThomas using DNS to redirect docker.io would require the new endpoint to have a valid TLS certificate for docker.io. Possible, but the cert would need to come from an internal Certificate Authority which the client is configured to trust. – Caleb Feb 10 '21 at 14:09
  • @Caleb I see your point. You still have to mess with the client... – Sam Thomas Feb 10 '21 at 16:33
  • 2
    An important caveat of the above is that you cannot use a private registry as a mirror. This is covered in the documentation [here](https://docs.docker.com/registry/recipes/mirror/#gotcha). Specifically: `It’s currently not possible to mirror another private registry. Only the central Hub can be mirrored.` – Keenan Apr 20 '22 at 20:36
28

It turns out this is actually possible, but not using the genuine Docker CE or EE version.

You can either use Red Hat's fork of docker with the '--add-registry' flag or you can build docker from source yourself with registry/config.go modified to use your own hard-coded default registry namespace/index.

Josiah
  • 571
  • 6
  • 12
  • 7
    RedHat's fork is the one available in centos-extras. Thanks for helping me understand why after switching to the docker.io version `--add-registry` stopped working. – chutz Apr 20 '17 at 11:00
  • 2
    You can also use the `--block-registry index.docker.io` option to get rid of the default registry. – Evan May 24 '19 at 15:34
  • 4
    The `--add-registry` [pull request](https://github.com/moby/moby/pull/10411) was **not merged**. This feature was ultimately refused ([#11816](https://github.com/moby/moby/issues/11816)). – Franklin Piat Jan 13 '20 at 13:35
16

The short answer to this is you don't, or at least you really shouldn't.

Yes, there are some container runtimes that allow you to change the default namespace, specifically those from RedHat. However, RedHat now regrets this functionality and discourages customers from using it. Docker has also refused to support this.

The reason this is so problematic is because is results in an ambiguous namespace of images. The same command run on two different machines could pull different images depending on what registry they are configured to use. Since compose files, helm templates, and other ways of running containers are shared between machines, this actually introduces a security vulnerability.

An attacker could squat on well known image names in registries other than Docker Hub with the hopes that a user may change their default configuration and accidentally run their image instead of the one from Hub. It would be trivial to create a fork of a tool like Jenkins, push the image to other registries, but with some code that sends all the credentials loaded into Jenkins out to an attacker server. We've even seen this causing security vulnerability reports this year for other package managers like PyPI, NPM, and RubyGems.

Instead, the direction of container runtimes like containerd is to make all image names fully qualified, removing the Docker Hub automatic expansion (tooling on top of containerd like Docker still apply the default expansion, so I doubt this is going away any time soon, if ever).

Docker does allow you to define registry mirrors for Docker Hub that it will query first before querying Hub, however this assumes everything is still within the same namespace and the mirror is just a copy of upstream images, not a different namespace of images. The TL;DR on how to set that up is the following in the /etc/docker/daemon.json and then systemctl reload docker:

{
  "registry-mirrors": ["https://<my-docker-mirror-host>"]
}

For most, this is a non-issue (this issue to me is the docker engine doesn't have an option to mirror non-Hub registries). The image name is defined in a configuration file, or a script, and so typing it once in that file is easy enough. And with tooling like compose files and Helm templates, the registry can be turned into a variable to allow organizations to explicitly pull images for their deploy from a configurable registry name.

BMitch
  • 231,797
  • 42
  • 475
  • 450
  • this ephesis on attackers is a bit laughble to me, since most people will live their entire lives and never encounter system virus or an intruder simply because their machines is behind so many proxies and "SERVER" that the NSA itself wont get through, secondly most pople need this functionatity to run their own registery for themselves, most companies wont support it because they do not want to relinquish control over what technicaly is supposed to be FREE – Max May 01 '23 at 18:08
  • 1
    "most people will live their entire lives and never encounter system virus" What are you basing that assumption on? "what technicaly is supposed to be FREE" What exactly is supposed to be free? Docker the software? its already free and open source. Hosting on Docker Hub? Why should it be free? If it should be free why shouldn't AWS ECR be free as well? While we are at it lets make every single cloud provider free – trve.fahad Jul 13 '23 at 18:04
12

if you are using the fedora distro, you can change the file

/etc/containers/registries.conf

Adding domain docker.io

Alan Kavanagh
  • 9,425
  • 7
  • 41
  • 65
  • 1
    This redhat specific configuration file is used to start dockerd with `--add-registry`. The feature will not be adopted by Docker in [pull request](https://github.com/moby/moby/pull/10411) was **not merged**. (also feature was ultimately refused ([#11816](https://github.com/moby/moby/issues/11816)). – Franklin Piat Jan 13 '20 at 13:38
11

Docker official position is explained in issue #11815 :

Issue 11815: Allow to specify default registries used in pull command

Resolution:

Like pointed out earlier (#11815), this would fragment the namespace, and hurt the community pretty badly, making dockerfiles no longer portable.

[the Maintainer] will close this for this reason.

Red Hat had a specific implementation that allowed it (see anwser, but it was refused by Docker upstream projet). It relied on --add-registry argument, which was set in /etc/containers/registries.conf on RHEL/CentOS 7.

EDIT:

Actually, Docker supports registry mirrors (also known as "Run a Registry as a pull-through cache"). https://docs.docker.com/registry/recipes/mirror/#configure-the-docker-daemon

Franklin Piat
  • 3,952
  • 3
  • 32
  • 45
8

It seems it won't be supported due to the fragmentation it would create within the community (i.e. two users would get different images pulling ubuntu:latest). You simply have to add the host in front of the image name. See this github issue to join the discussion.

(Note, this is not intended as an opinionated comment, just a very short summary of the discussion that can be followed in the mentioned github issue.)

datacarl
  • 2,591
  • 25
  • 21
  • 14
    fragmentation yes but just with the early days of linux there eventually became only three (source base[arch,gentoo,slax,...], debian based[debian/ubuntu], and redhat based[enterprise linux, rhel, centos]. It would be better from a security standpoint to be able to change the default upstream registry to something self managed. – Dwight Spencer Apr 29 '16 at 21:29
  • 2
    Saying "there are only three linuxes, redhat, debian, and source" is like saying "there are only three search providers: google, bing, and all the other search providers"... – Chris Browne Jul 29 '19 at 10:38
4

I tried to add the following options in the /etc/docker/daemon.json. (I used CentOS7)

"add-registry": ["192.168.100.100:5001"],
"block-registry": ["docker.io"],

after that, restarted docker daemon. And it's working without docker.io. I hope this someone will be helpful.

Jacob Baek
  • 49
  • 5
  • 4
    This configuration is specific to RedHat. The `--add-registry` [pull request](https://github.com/moby/moby/pull/10411) was **not merged**. – Franklin Piat Jan 13 '20 at 13:40
3

Earlier this could be achieved using DOCKER_OPTS in the /etc/default/docker config file which worked on Ubuntu 14:04 and had some issues on Ubuntu 15:04. Not sure if this has been fixed.

The below line needs to go into the file /etc/default/docker on the host which runs the docker daemon. The change points to the private registry is installed in your local network. Note: you would require to restart the docker service followed with this change.

DOCKER_OPTS="--insecure-registry <priv registry hostname/ip>:<port>"
andy boot
  • 11,355
  • 3
  • 53
  • 66
askb
  • 6,501
  • 30
  • 43
  • 14
    The '--insecure-registry' flag allows docker to pull from the named registry without TLS authentication. It does nothing toward setting a default registry when one isn't specified. – Josiah Apr 19 '18 at 16:39
  • 1
    It does if you next edit your /etc/hosts file and point the official repo/dockerhub hostnames at your http registry server. – Marc Jul 15 '21 at 14:19
-1

I'm adding up to the original answer given by Guy which is still valid today (soon 2020).

Overriding the default docker registry, like you would do with maven, is actually not a good practice.

When using maven, you pull artifacts from Maven Central Repository through your local repository management system that will act as a proxy. These artifacts are plain, raw libs (jars) and it is quite unlikely that you will push jars with the same name.

On the other hand, docker images are fully operational, runnable, environments, and it makes total sens to pull an image from the Docker Hub, modify it and push this image in your local registry management system with the same name, because it is exactly what its name says it is, just in your enterprise context. In this case, the only distinction between the two images would precisely be its path!!

Therefore the need to set the following rule: the prefix of an image indicates its origin; by default if an image does not have a prefix, it is pulled from Docker Hub.

avi.elkharrat
  • 6,100
  • 6
  • 41
  • 47
  • For exactly this reason maven repository storing releases by default does not allow overwriting and offers classifiers. Similarly docker uses tags. – coz Jun 09 '20 at 13:57
-6

Haven't tried, but maybe hijacking the DNS resolution process by adding a line in /etc/hosts for hub.docker.com or something similar (docker.io?) could work?

akavel
  • 4,789
  • 1
  • 35
  • 66
  • 7
    That will blow up in the connection stage; the server you connect to won't have a proper TLS certificate for the domain. – Michael Mol Jun 12 '18 at 17:44
  • You're looking for a HTTP rewrite which would require hijacking the https connection and rewriting the URL. In order to do this, you'd need a trusted CA to sign the TLS connection. – Drew Oct 16 '20 at 00:57
  • @Drew Depending whether docker is pinning the cert or not, I'd guess adding custom Root CA in the OS could maybe work? I'm not saying that's a Pretty and Proper Solution™, but sometimes you just need this one horrible hack and need it fast (To Be Fixed Later® once dust settles and blood^H money's no longer running...) – akavel Nov 06 '20 at 18:29
  • Add dockerhub as an insecure registry and patch /etc/hosts should work – Marc Jul 15 '21 at 14:20