部署 Docker Registry 服务

本文讲的是部署 Docker Registry 服务,【编者的话】本文阐释了怎样部署私有的 Docker Registry 服务 —— 或为公司私用,或公开给其他用户使用。例如,你公司可能需要私人的 Registry 来支持持续集成(CI)。又或,你的公司可能有大量镜像方式的产品或服务,你想以公司品牌的方式来整体提供和呈现。

本文阐释了怎样部署私有的 Docker Registry 服务 —— 或为公司私用,或公开给其他用户使用。例如,你公司可能需要私人的 Registry 来支持持续集成(CI)。又或,你的公司可能有大量镜像方式的产品或服务,你想以公司品牌的方式来整体提供和呈现。

Docker 公共的 Registry 里维护有一个默认的 registry 镜像可以用以协助该部署过程。该 Registry 镜像对本地测试足矣,但不能用于生产环境。对于生产环境,应以 docker/distribution 为基础,自行配置并构建自定义 Registry 镜像。

注意:本文中的例子在 Ubuntu 14.04 下编写及测试。如果你在不同的操作系统中运行
Docker,你或许需要“翻译”这些命令,以适合你运行环境的需要。

官方镜像下的简单示例

本节中,将创建一个 Container 来运行 Docker 的官方 Registry 镜像。你将推送(Push)一个镜像到这个 Registry 服务器,然后再从该 Registry 中拉取(Pull)同一个镜像。

这是个很好的练习,有助于理解客户端与本地 Registry 的基本交互。

1、安装 Docker。

2、从 Docker 公共 Registry 中运行 hello-world 镜像。

$ docker run hello-world

run 命令自动从 Docker 的官方镜像库中将 hello-world 镜像 pull 下来。

3、在 localhost 上启动 Registry 服务。

$ docker run -p 5000:5000 registry:2.0

这将在 DOCKER_HOST 上启动一个 Registry 服务,并在 5000 端口监听。

4、列出镜像。

$ docker images
REPOSITORY     TAG     IMAGE ID      CREATED       VIRTUAL SIZE
registry       2.0     bbf0b6ffe923  3 days ago    545.1 MB
golang         1.4     121a93c90463  5 days ago    514.9 MB
hello-world    latest  e45a5af57b00  3 months ago  910 B

这个列表应当包括一个由先前运行而得来的 hello-world 镜像。

5、为本地 repoistory 重新标记 hello-world 镜像。

$ docker tag hello-world:latest localhost:5000/hello-mine:latest

此命令使用 [REGISTRYHOST/]NAME[:TAG] 格式为 hello-world:latest 重新打标。REGISTRYHOST 在此例中是 localhost。在 Mac OSX 环境中,得把 localhost 换成 $(boot2docker ip):5000

6、列出新镜像。

$ docker images
REPOSITORY                  TAG          IMAGE ID      CREATED       VIRTUAL SIZE
registry                    2.0     bbf0b6ffe923  3 days ago    545.1 MB
golang                      1.4     121a93c90463  5 days ago    514.9 MB
hello-world                 latest  e45a5af57b00  3 months ago  910 B
localhost:5000/hello-mine   latest  ef5a5gf57b01  3 months ago  910 B

可以看到,新镜像已经出现在列表中。

7、推送新镜像到本地 Registry 中。

$ docker push localhost:5000/hello-mine:latest
The push refers to a repository [localhost:5000/hello-mine] (len: 1)
e45a5af57b00: Image already exists
31cbccb51277: Image successfully pushed
511136ea3c5a: Image already exists
Digest: sha256:a1b13bc01783882434593119198938b9b9ef2bd32a0a246f16ac99b01383ef7a

8、使用 curl 命令及 Docker Registry 服务 API v2 列出 Registry 中的镜像:

$ curl -v -X GET http://localhost:5000/v2/hello-mine/tags/list
* Hostname was NOT found in DNS cache
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 5000 (#0)
> GET /v2/hello-mine/tags/list HTTP/1.1
> User-Agent: curl/7.35.0
> Host: localhost:5000
> Accept: */*
>
< HTTP/1.1 200 OK
< Content-Type: application/json; charset=utf-8
< Docker-Distribution-Api-Version: registry/2.0
< Date: Sun, 12 Apr 2015 01:29:47 GMT
< Content-Length: 40
<
{"name":"hello-mine","tags":["latest"]}
* Connection #0 to host localhost left intact

也可以通过在浏览器中访问以下地址来获取这些信息:http://localhost:5000/v2/hello-mine/tags/list

9、从你的本地环境中移除所有未使用的镜像:

$ docker rmi -f $(docker images -q -a )

此命令仅用于说明目的;移除镜像强制 run 从 Registry 而不是从本地缓存拉取。如果在这之后运行docker images,在你的镜像列表中,应该看不到任何 hello-world 或 hello-mine 的实例。

$ docker images
REPOSITORY      TAG      IMAGE ID      CREATED       VIRTUAL SIZE
registry         2.0     bbf0b6ffe923  3 days ago    545.1 MB
golang           1.4     121a93c90463  5 days ago    514.9 MB

10、试运行 hello-mine

$ docker run hello-mine
Unable to find image 'hello-mine:latest' locally
Pulling repository hello-mine
FATA[0001] Error: image library/hello-mine:latest not found

命令 run 运行失败,因为你的新镜像在 Docker 公共 Registry 中是不存在的。

11、现在,尝试指定镜像的 Registry 来运行镜像:

$ docker run localhost:5000/hello-mine

如果你在这之后运行 docker images, 你会发现里面多了一个 hello-mine 的实例。

使 Docker 官方 Registry 镜像做好生产环境准备

Docker 的官方镜像只为简单的测试或除错准备。其配置对多数生产环境来讲都不适用。例如,任何能访问服务器 IP 的客户端,都能推送及拉取镜像。参看下一节,获取使该镜像做好生产环境准备的信息。

理解生产环境的部署

当部署一个用于生产环境发布的 Registry 时,须考虑如下因素:

BACKEND STORAGE 应在何处存储镜像?
ACCESS AND/OR AUTHENTICATION 用户是否应拥有全部或受控的访问权限?这取决于你为公众提供镜像服务,还是只为公司内部提供。
DEBUGGING 当问题或状况发生时,是否有解决这些它们的方法。日志由于可以看到问题动向,这使其很有用。
CACHING 快速提取镜像可能至关重要,如果依赖镜像进行测试、构建,或有其他自动化系统的话。

我们可以配置 Registry 功能特性,用以调整适配这些因素。可以在命令行里指定选项来干这个,或者更通常地,用一个 Registry 配置文件来完成此事。配置文件是 YAML 格式的。

Docker 的官方 Repository 镜像用以下配置文件做了预置:

version: 0.1
log:
level: debug
fields:
service: registry
environment: development
storage:
cache:
  layerinfo: inmemory
filesystem:
  rootdirectory: /tmp/registry-dev
http:
addr: :5000
secret: asecretforlocaldevelopment
debug:
  addr: localhost:5001
redis:
addr: localhost:6379
pool:
maxidle: 16
maxactive: 64
idletimeout: 300s
dialtimeout: 10ms
readtimeout: 10ms
writetimeout: 10ms
notifications:
endpoints:
  - name: local-8082
    url: http://localhost:5003/callback
    headers:
       Authorization: [Bearer <an example token>]
    timeout: 1s
    threshold: 10
    backoff: 1s
    disabled: true
  - name: local-8083
    url: http://localhost:8083/callback
    timeout: 1s
    threshold: 10
    backoff: 1s
    disabled: true

这个配置非常基本,可以看到这在生产环境下会有一些问题。例如,http 区块详述了运行 Registry 的主机的 HTTP 服务器配置,但服务器没有使用甚至是最低要求的传输层安全性(TLS)配置。接下来我们将配置这些东西。

在 Registry 服务器上配置 TLS

在本节中,将在服务器上配置 TLS,使能通过 https 协议来通信。在服务器上启用 TLS 是在企业防火墙内运行 Registry 推荐的最低安全配置。达成这一目标的方法之一就是构建你自己的 Registry 镜像。

下载 source 并生成 certificates

1、下载 Registry 源码

当然,也可以使用 git clone 命令。

2、把下载的包解压到本地目录。

解压后创建 distribution 目录。

3、进入 distribution 目录。

$ cd distribution

4、新建 certs 子目录。

$ mkdir certs

5、使用 SSL 生成自签名证书。

$ openssl req \
     -newkey rsa:2048 -nodes -keyout certs/domain.key \
     -x509 -days 365 -out certs/domain.crt

此命令将提示你回答一些基本的信息,用于创建证书。

6、列出 certs 目录的内容。

$ ls certs
domain.crt domain.key

当你构建这个 Container 时,certs 目录及其内容也会自动被复制。

将 TLS 加入配置

distribution 软件库在 cmd 子目录中包含有示例 Registry 配置。在本节中,您可以编辑这些配置之一,以添加 TLS 支持。

1、编辑 ./cmd/registry/config.yml 文件。

$ vi ./cmd/registry/config.yml

2、定位到 http 区块。

http:
    addr: :5000
    secret: asecretforlocaldevelopment
    debug:
            addr: localhost:500

3、给服务器的自签名证书新增一个 tls 区块:

http:
    addr: :5000
    secret: asecretforlocaldevelopment
    debug:
            addr: localhost:5001
    tls:
        certificate: /go/src/github.com/docker/distribution/certs/domain.crt
        key: /go/src/github.com/docker/distribution/certs/domain.key

提供 Container 内到证书的路径。如果你希望跨 Layer 使用两步认证,那么你可以增加一个 clientcas 区块选项。

4、保存并关闭该文件。

构建并运行你的 Registry 镜像

1、构建你的 Registry 镜像。

$ docker build -t secure_registry .

2、运行你的新镜像。

$ docker run -p 5000:5000 registry_local:latest
time="2015-04-12T03:06:18.616502588Z" level=info msg="endpoint local-8082 disabled, skipping" environment=development instance.id=bf33c9dc-2564-406b-97c3-6ee69dc20ec6 service=registry
time="2015-04-12T03:06:18.617012948Z" level=info msg="endpoint local-8083 disabled, skipping" environment=development instance.id=bf33c9dc-2564-406b-97c3-6ee69dc20ec6 service=registry
time="2015-04-12T03:06:18.617190113Z" level=info msg="using inmemory layerinfo cache" environment=development instance.id=bf33c9dc-2564-406b-97c3-6ee69dc20ec6 service=registry
time="2015-04-12T03:06:18.617349067Z" level=info msg="listening on :5000, tls" environment=development instance.id=bf33c9dc-2564-406b-97c3-6ee69dc20ec6 service=registry
time="2015-04-12T03:06:18.628589577Z" level=info msg="debug server listening localhost:5001"
2015/04/12 03:06:28 http: TLS handshake error from 172.17.42.1:44261: remote error: unknown certificate authority

观察启动时的信息。你应该可以看到 tls 在运行。

3、使用 curl 验证可以通过 https 连接。

$ curl -v https://localhost:5000
* Rebuilt URL to: https://localhost:5000/
* Hostname was NOT found in DNS cache
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 5000 (#0)
* successfully set certificate verify locations:
*   CAfile: none
CApath: /etc/ssl/certs
* SSLv3, TLS handshake, Client hello (1):
* SSLv3, TLS handshake, Server hello (2):
* SSLv3, TLS handshake, CERT (11):
* SSLv3, TLS alert, Server hello (2):
* SSL certificate problem: self signed certificate
* Closing connection 0
curl: (60) SSL certificate problem: self signed certificate
More details here: http://curl.haxx.se/docs/sslcerts.html

配置适合 v1 及 v2 版本 Registry 的 Nginx

本节介绍了如何使用 docker-compose ,在 nginx 代理背后运行版本 1 和 2 并存的 Registry 服务。并存的 Registry 服务都用 localhost:5000 访问。如果 docker 客户端版本小于 1.6,那么 Nginx 将其请求路由到 1.0 版本的 Registry 服务。从更新版本客户端发来的请求,将路由到 2.0 版本的 Registry 服务。

此过程使用您在上面最后一个过程中创建的 distribution 目录。该目录包含有一个 compose 配置示例。

安装 Docker Compose

1、在你 distribution 目录所在主机上打开一个新的终端窗口。

2、获取 docker-compose 二进制可执行文件。

$ sudo wget https://github.com/docker/compose/releases/download/1.1.0/docker-compose-`uname -s`-`uname -m` -O /usr/local/bin/docker-compose

此命令将二进制可执行文件安装到 /usr/local/bin 目录。

3、添加可执行权限到二进制文件。

$ sudo chmod +x /usr/local/bin/docker-compose

做一些清理

1、移除早先的镜像。

$ docker rmi -f $(docker images -q -a )

该步骤是一个内部管理步骤。这可以防止你在这个例子里错误地选取了旧的镜像。

2、编辑 distribution/cmd/registry/config.yml 文件,并移除 tls 区块。

如果沿用了前面例子里的东西,你就会有一个 tls 区块。

3、保存变更并关闭文件。

配置 SSL

1、进入 distribution/contrib/compose/nginx 目录。

该目录包含了 Nginx 及 Registry 的配置文件。

2、使用 SSL 生成自签名证书。

$ openssl req \
     -newkey rsa:2048 -nodes -keyout domain.key \
     -x509 -days 365 -out domain.crt

此命令将提示你回答一些问题,供证书创建使用。

3、编辑 Dockerfile 并添加以下行。

COPY domain.crt /etc/nginx/domain.crt
COPY domain.key /etc/nginx/domain.key

当你全部搞完的时候,这个文件看上去像下面。

FROM nginx:1.7

COPY nginx.conf /etc/nginx/nginx.conf
COPY registry.conf /etc/nginx/conf.d/registry.conf
COPY docker-registry.conf /etc/nginx/docker-registry.conf
COPY docker-registry-v2.conf /etc/nginx/docker-registry-v2.conf
COPY domain.crt /etc/nginx/domain.crt
COPY domain.key /etc/nginx/domain.key

4、保存并关闭 Dockerfile 文件。

5、编辑 registry.conf 文件并增加以下配置。

ssl on;
ssl_certificate /etc/nginx/domain.crt;
ssl_certificate_key /etc/nginx/domain.key;

这是一个 nginx 配置文件。

6、保存并关闭 registry.conf 文件。

构建并运行

1、进到 distribution/contrib/compose 目录

此目录包含单一个 docker-compose.yml 配置。

nginx:
build: "nginx"
ports:
    - "5000:5000"
links:
    - registryv1:registryv1
    - registryv2:registryv2
registryv1:
image: registry
ports:
    - "5000"
registryv2:
build: "../../"
ports:
    - "5000"

此配置按 nginx/Dockerfile 所指定,构建一个新的 nginx 镜像。1.0 版本的 Registry 来自 Docker 的官方公开镜像。Registry 2.0 镜像将从你前面用到的 distribution/Dockerfile 来构建。

2、获取 Registry 1.0 镜像。

$ docker pull registry:0.9.1

Compose 的配置是在本地寻找此镜像。如果你不做这步,那后面的步骤会失败。

3、构建 nginx,Registry 2.0 镜像,以及

$ docker-compose build
registryv1 uses an image, skipping
Building registryv2...
Step 0 : FROM golang:1.4

...

Removing intermediate container 9f5f5068c3f3
Step 4 : COPY docker-registry-v2.conf /etc/nginx/docker-registry-v2.conf
---> 74acc70fa106
Removing intermediate container edb84c2b40cb
Successfully built 74acc70fa106

此命令将输出其执行过程,直到运行结束。

4、启动使用了 Compose 的配置。

$ docker-compose up
Recreating compose_registryv1_1...
Recreating compose_registryv2_1...
Recreating compose_nginx_1...
Attaching to compose_registryv1_1, compose_registryv2_1, compose_nginx_1
...

5、在另一个终端,显示运行中的配置。

$ docker ps
CONTAINER ID        IMAGE                       COMMAND                CREATED             STATUS              PORTS                                     NAMES
a81ad2557702        compose_nginx:latest        "nginx -g 'daemon of   8 minutes ago       Up 8 minutes        80/tcp, 443/tcp, 0.0.0.0:5000->5000/tcp   compose_nginx_1
0618437450dd        compose_registryv2:latest   "registry cmd/regist   8 minutes ago       Up 8 minutes        0.0.0.0:32777->5000/tcp                   compose_registryv2_1
aa82b1ed8e61        registry:latest             "docker-registry"      8 minutes ago       Up 8 minutes        0.0.0.0:32776->5000/tcp                   compose_registryv1_1

浏览一下

1、检查一下你 nginx 服务器上的 TLS。

$ curl -v https://localhost:5000
* Rebuilt URL to: https://localhost:5000/
* Hostname was NOT found in DNS cache
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 5000 (#0)
* successfully set certificate verify locations:
*   CAfile: none
CApath: /etc/ssl/certs
* SSLv3, TLS handshake, Client hello (1):
* SSLv3, TLS handshake, Server hello (2):
* SSLv3, TLS handshake, CERT (11):
* SSLv3, TLS alert, Server hello (2):
* SSL certificate problem: self signed certificate
* Closing connection 0
curl: (60) SSL certificate problem: self signed certificate
More details here: http://curl.haxx.se/docs/sslcerts.html

2、标记 v1 registry 镜像。

$ docker tag registry:latest localhost:5000/registry_one:latest

3、将其推送到 localhost

$ docker push localhost:5000/registry_one:latest

如果你在使用 1.6 版本的 Docker 客户端,这将推送镜像到 v2 registry。

4、使用 curl 来列出 Registry 中的镜像。

$ curl -v -X GET http://localhost:32777/v2/registry1/tags/list
* Hostname was NOT found in DNS cache
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 32777 (#0)
> GET /v2/registry1/tags/list HTTP/1.1
> User-Agent: curl/7.36.0
> Host: localhost:32777
> Accept: */*
>
< HTTP/1.1 200 OK
< Content-Type: application/json; charset=utf-8
< Docker-Distribution-Api-Version: registry/2.0
< Date: Tue, 14 Apr 2015 22:34:13 GMT
< Content-Length: 39
<
{"name":"registry1","tags":["latest"]}
* Connection #0 to host localhost left intact

本例参照引用了分配给 2.0 Registry 服务的特定端口。早些时候,在使用 docker ps 命令显示正在运行的容器时,你应该看到过这个端口。

原文链接:部署 Docker Registry 服务(翻译:Live Digital

原文发布时间为:2015-04-18

本文作者:analyser 

本文来自合作伙伴DockerOne,了解相关信息可以关注DockerOne。

原文标题:部署 Docker Registry 服务

时间: 2024-11-15 00:59:03

部署 Docker Registry 服务的相关文章

Moving to Docker(二)搭建一个私有registry服务

本文讲的是Moving to Docker(二)搭建一个私有registry服务,[编者的话]本文是<Moving to Docker>系列的第二篇,这个系列的文章讲述了创业公司如何把基础服务迁移到Docker上,以及迁移过程中的经验教训.本文主要介绍了如何安装.测试和使用私有registry服务,其中也包含了从DigitalOcean选VPS和注册Amazon S3服务. 这是迁移到Docker系列的第二篇,整个系列都是介绍我们公司是如何把基础设施从PaaS迁移到Docker的. 第一篇:介

一键部署自动感知服务的Docker集群(一)

问:部署一套自动感知服务的集群需要几步? 答:三步! 本系列介绍如何利用阿里云资源编排服务(ROS)和容器服务(CS)轻松搭建自动感知服务的Docker集群.本文是第一篇,简单介绍如何在阿里云上部署Docker集群,带您快速体验一键部署的快感! >> 一键部署传送门 >> 背景 在云上搭建一套Docker集群还是需要很多技术储备也蛮复杂的一件的事情.一个相对基础的结构如下图所示: 搭建如上的一套环境,一般需要如下流程: 搭建VPC网络 选购ECS服务器,配置安全组访问规则,如上图所

《Spring Cloud与Docker微服务架构实战》配套代码

不才写了本使用Spring Cloud玩转微服务架构的书,书名是<Spring Cloud与Docker微服务架构实战> - 周立,已于2017-01-12交稿.不少朋友想先看看源码,现将代码放出. 本次放出的代码: 共计70+个DEMO 覆盖Eureka.Ribbon.Feign.Hystrix.Zuul.Spring Cloud Config.Spring Cloud Bus.Spring Cloud Sleuth.Docker.Docker Compose等. 1-11章代码地址: ht

deploy owned private docker registry based on docker HUB registry image

docker HUB提供了registry的image, 可以非常方便的搭建私有regisrty. 当然你也可以选择从docker-registry的源码来搭建. 见 : https://github.com/docker/docker-registry 本文主要说一下使用docker registry image搭建私有registry. 1. 首先要部署docker 参考 :  https://docs.docker.com/installation/#installation 2. 启动d

利用阿里云容器服务实现Docker微服务间的负载均衡和服务发现

基于容器服务实现Docker微服务间的负载均衡和自动服务发现的方法 在容器服务上可以通过acsrouting将基于域名的http的服务暴漏出去,而且能够配合健康检查自动的负载均衡和服务发现,当其中一个容器出现问题之后,routing会自动将健康检查失败的容器从后端摘除,所以能做到自动的服务发现. 然而这个是将服务暴漏到外网的,那么服务间如何通过这种方式做到自动的服务发现和的负载均衡呢?容器服务引入了负载均衡的功能,只需要使用.local结尾的域名,并在依赖的服务的external_links中增

搭建一个私有的Docker registry

搭建一个私有的Docker registry [TL;DR] 这是系列的第二篇文章,这系列讲述了我的公司如何把基础服务从PaaS迁移到Docker上 第一篇文章: 我谈到了接触Docker之前的经历: 第三篇文章: 我展示如何使创建镜像的过程自动化以及如何用Docker部署一个Rails应用. 为什么需要搭建一个私有的registry呢?嗯,对于新手来说,Docker Hub(一个Docker公共仓库)只允许你拥有一个免费的私有版本库(repo).其他的公司也开始提供类似服务,但是价格可不便宜.

基于OSS搭建私有 Docker Registry

基于OSS搭建私有 Docker Registry Docker Registry 作为 Docker 的核心组件之一负责了镜像的存储以及分发.用户只需要使用 Docker 的客户端就可以直接和 Registry 进行交互,下载和上传镜像.最初版本的 Registry 由 Python 实现.由于设计初期在安全性,性能以及 API 的设计上有着诸多的缺陷,该版本在 0.9 之后停止了开发.新的项目由 Go 语言开发,所有的API,底层存储方式,系统架构都进行了全面的重新设计已解决上一代 Regi

搭建一个私有的Docker registry教程_docker

为什么需要搭建一个私有的registry呢?嗯,对于新手来说,Docker Hub(一个Docker公共仓库)只允许你拥有一个免费的私有版本库(repo).其他的公司也开始提供类似服务,但是价格可不便宜.另外,如果你需要用Docker部署一个用于生产环境的应用,恐怕你不希望将这些镜像放在公开的Docker Hub上吧! 这篇文章提供了一个非常务实的方法来处理搭建私有Docker registry时出现的各种错综复杂的情况.我们将会使用一个运行于DigitalOcean(之后简称为DO)的非常小巧

Kubernetes持续部署Docker Apps

本文讲的是Kubernetes持续部署Docker Apps[编者的话]本文是Codeship系列文章(Continuous Deployment for Docker Apps to Kubernetes)的第二篇,介绍了Codeship的相关配置项.如果已经等不及了,你可以下载电子书<Continuous Deployment for Docker Apps to Kubernetes> 这一系列文章中,我们介绍过了using Kubernetes for deployments.本篇我们