本文主要是介绍干货|Nginx+Portus+Registry搭建私有镜像仓库,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
Portus介绍
Portus是SUSE为Docker Registry(v2)开发的一款开源的用户前端和授权管理软件。提供企业私有Docker Registry的用户和权限管理功能,并提供Web界面使得管理员能够更加简易的进行管理操作。可以简单的理解为通过Portus+Registry的结合来实现企业私有的Docker Hub部署和管理。
Portus特性
安全
Portus实现私有Docker Registry中所有镜像的权限管理,针对不同的镜像设置不同用户或组的Push和Pull权限。
用户管理
Portus提供Web界面管理方式,可非常容易的进行用户和组的添加、修改、授权和删除等操作。
搜索
Portus提供了私有仓库内容的概览,但是也可以通过搜索功能更快找到需要的镜像。
Portus的功能还有很多,比如LDAP支持,操作审计等等。Portus权限管理的安全性和细粒度还算比较高,Repository层面设置不同用户和组的权限,用户层面又设置了不同的角色,通过多方面的授权实现镜像的安全性管理。个人觉得如果企业内部的开发测试环境需要一个私有的Registry的话,可以考虑采用Portus。
Registry v2验证过程
Docker Client通过Docker Daemon拉取镜像白话版:
\1.我要搬货
\2.没授权,去相关部门开单子(拿Token)
\3.我要搬货,这是我的申请单(提交用户名和密码申请Token)
\4.核实信息,单子盖章(拿到Token)
\5.我要搬货,这是授权单
\6.通过,搬走
Portus主要功能就是上面的”相关部门”(Authorization Service)了,负责用户请求的验证和授权功能。
环境介绍
私有”Docker Hub”整个环境的5个容器跑在一台Docker宿主机上,并使用两个Alias实现Portus和Registry的访问。
-
Docker宿主机:docker04.onlyeric.com
-
容器:
portus_nginx_1: Nginx反向代理服务
portus_registry_1: 私有Registry服务
portus_web_1: Portus的Web服务
portus_crono_1: Portus服务
portus_db_1: Portus数据库服务 -
Alias
onlyeric.reg 用户pull/push操作的镜像服务器
portus.onlyeric.com 管理员访问的Portus界面
环境准备
Server: 内网KVM虚机
OS: CentOS 7.2
IP: 192.168.2.14
Docker Engine: 1.11.2
Docker Compose: 1.7.1
Docker Images:
library/registry:2.3.1
library/mariadb:10.0.23
library/rails:4.2.2
nginx:1.10.1
(rails是构建portus的基础镜像,其他三个顾名思义了)
Alias:
192.168.2.14 onlyeric.reg
192.168.2.14 portus.onlyeric.com
(由于内网没有配置DNS服务器,所以需要在客户端和服务端都添加以上记录到hosts文件)
Docker Engine配置:
“--insecure-registry onlyeric.reg”
Portus容器化部署脚本:
https://github.com/SUSE/Portus.git
(该脚本由SUSE官方提供,旨在方便Portus的开发和测试)
在以上准备工作搞定之后就可以开始进行Portus的部署了。需要的Image可以不用提前准备,因为SUSE提供的部署脚本已含有镜像的下载内容。但是考虑到国内访问Docker Hub经常抽风,个人建议先把镜像给下载或者从哪儿Load过来。
安装部署
Portus脚本修改
默认的Portus脚本里不含nginx容器和配置,Portus和Registry的访问需要加端口。以下配置的变更主要是为了实现Nginx到Potus和Registry端口转发,实现不带端口(80端口)的访问。
下载Portus脚本
# git clone git clone https://github.com/SUSE/Portus.git
修改Gemfile
1 2 3 4 | # vi Gemfile #source "https://rubygems.org" source "http://rubygems.org" (国外的服务器无需修改) |
创建nginx配置目录
# mkdir nginx/conf.d
创建nginx配置文件
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 | # pwd /root/Portus/nginx/conf.d Portus反向代理配置文件 # vi portus.conf server { listen 0.0.0.0:80; server_name portus.onlyeric.com; location / { proxy_set_header Host $host; proxy_set_header X-Forwarded-Proto $scheme; proxy_set_header X-Forwarded-Host $http_host; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_redirect off; proxy_pass http://web:3000/; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; proxy_read_timeout 900s; } access_log /var/log/nginx/portus.access.log main; error_log /var/log/nginx/portus.error.log error; } registry反向代理配置文件 # vi registry.conf upstream onlyeric.reg { server registry:5000; } map $upstream_http_docker_distribution_api_version $docker_distribution_api_version { 'registry/2.0' ''; default registry/2.0; } server { listen 80; server_name onlyeric.reg; client_max_body_size 0; chunked_transfer_encoding on; location /v2/ { if ($http_user_agent ~ "^(docker\/1\.(3|4|5(?!\.[0-9]-dev))|Go ).*$" ) { return 404; } add_header 'Docker-Distribution-Api-Version' $docker_distribution_api_version always; proxy_pass http://onlyeric.reg; proxy_set_header Host $http_host; # required for docker client's sake proxy_set_header X-Real-IP $remote_addr; # pass on real client's IP proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; proxy_read_timeout 900; } } |
(配置文件中使用到的registry和web是在容器层面做过link的)
修改compose文件
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 | # pwd /root/Portus/compose # vi docker-compose.yml.template web: build: . command: puma -b tcp://0.0.0.0:3000 -w 3 environment: - PORTUS_MACHINE_FQDN_VALUE=EXTERNAL_IP - PORTUS_DB_HOST=portus_db_1 volumes: - .:/portus ports: - 3000:3000 links: - db extra_hosts: - "onlyeric.reg:192.168.2.14" - "portus.onlyeric.com:192.168.2.14" crono: image: portus_web entrypoint: bin/crono environment: - PORTUS_MACHINE_FQDN=EXTERNAL_IP - PORTUS_DB_HOST=portus_db_1 volumes: - .:/portus links: - db extra_hosts: - "onlyeric.reg:192.168.2.14" - "portus.onlyeric.com:192.168.2.14" db: image: library/mariadb:10.0.23 environment: MYSQL_ROOT_PASSWORD: portus extra_hosts: - "onlyeric.reg:192.168.2.14" - "portus.onlyeric.com:192.168.2.14" registry: image: library/registry:2.3.1 volumes: - /registry:/registry_data - ./compose/registry/portus.crt:/etc/docker/registry/portus.crt:ro - ./compose/registry/config.yml:/etc/docker/registry/config.yml:ro ports: - 5000:5000 - 5001:5001 # required to access debug service links: - web extra_hosts: - "onlyeric.reg:192.168.2.14" - "portus.onlyeric.com:192.168.2.14" nginx: image: nginx:1.10.1 links: - registry - web volumes: - ./nginx/conf.d:/etc/nginx/conf.d ports: - 80:80 extra_hosts: - "onlyeric.reg:192.168.2.14" - "portus.onlyeric.com:192.168.2.14" |
(添加nginx容器,并将alias的解析添加到所有容器中。其中将registry容器中images存放的目录给mount到Docker host的文件系统上)
修改registry配置文件
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | # pwd /root/Portus/compose/registry # vi config.yml.template version: 0.1 storage: filesystem: rootdirectory: /registry_data delete: enabled: true http: addr: 0.0.0.0:5000 debug: addr: 0.0.0.0:5001 auth: token: realm: http://EXTERNAL_IP:3000/v2/token service: EXTERNAL_IP issuer: EXTERNAL_IP rootcertbundle: /etc/docker/registry/portus.crt notifications: endpoints: - name: portus url: http://EXTERNAL_IP:3000/v2/webhooks/events timeout: 500ms threshold: 5 backoff: 1s |
(将service后的5000端口去掉)
环境部署
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 | # pwd /root/Portus # ./compose-setup.sh -e onlyeric.reg ########### # WARNING # ########### This deployment method is intended for testing/development purposes. To deploy Portus on production please take a look at: http://port.us.org/documentation.html The setup will destroy the containers used by Portus, removing also their volumes. Are you sure to delete all the data? (Y/N) [Y] Y . . . ################### # SUCCESS # ################### Make sure port 3000 and 5000 are open on host onlyeric.reg Open http://onlyeric.reg:3000 with your browser and perform the following steps: 1. Create an admin account 2. You will be redirected to a page where you have to register the registry. In this form: - Choose a custom name for the registry. - Enter onlyeric.reg:5000 as the hostname. - Do *not* check the "Use SSL" checkbox, since this setup is not using SSL. Perform the following actions on the docker hosts that need to interact with your registry: - Ensure the docker daemon is started with the '--insecure-registry onlyeric.reg:5000' - Perform the docker login. To authenticate against your registry using the docker cli do: $ docker login -u <portus username> -p <password> -e <email> onlyeric.reg:5000 To push an image to the private registry: $ docker pull busybox $ docker tag busybox onlyeric.reg:5000/<username>busybox $ docker push onlyeric.reg:5000/<username>busybox |
确认脚本运行的WARNING很友善的提示了该部署方式主要是用于开发测试环境,个人猜测原因可能是没有激活SSL安全配置。
部署的过程主要是使用docker compose来基于编辑好的compose文件启动环境。涵盖portus_web:latest镜像的build以及5个容器的启动。如果是在国内的网络环境部署的话整个过程非常长,因为portus_web镜像构建的时候需要更新很多软件包。如果之前没将需要的images准备好的话,该过程可能会更长。国外服务器的话大概30分钟之内可以搞定,Docker的魅力就在此了。任何应用不需要过多的安装和配置,拿着镜像启动成容器直接用就行。
部署成功后会提示SUCCESS并提供了很多链接和操作说明。这里需要注意的是由于我们使用了Nginx做了Portus和Registry的反向代理,所以在访问应用时后面的端口可以省略。
按照之前的规划:
Portus Web的Link为http://portus.onlyeric.com
Registry为onlyeric.reg
Portus配置
登录Portus
http://portus.onlyeric.com
创建admin帐号
(帐号密码任意设置)
配置Registry
在首次登录Portus的时候会自动弹出配置Registry的窗口
(Name任意,Hostname为onlyeric.reg)
(配置成功后会直接跳到如上界面)
基本验证
登陆测试
1 2 3 | # docker login -u onlyeric -p zaq12wsx! onlyeric.reg Login Succeeded (登录成功) |
Push测试
1 2 3 4 5 6 7 8 9 | # docker tag busybox:latest onlyeric.reg/onlyeric/busybox:latest (Tag测试所需镜像,REGISTRY_NAME/USERNAME/IMAGE_NAME/IMAGE_TAG) # docker push onlyeric.reg/onlyeric/busybox:latest The push refers to a repository [onlyeric.reg/onlyeric/busybox] 5f70bf18a086: Pushed 8ac8bfaff55a: Pushed latest: digest: sha256:507bc9f5e7844d90c630f141a93b073473e24bd0b27daef574ffa93f97d01181 size: 733 (镜像上传成功) |
稍等片刻之后Portus的Web界面也可以看到上传成功的镜像
Pull测试
1 2 3 4 5 6 7 8 9 | # docker rmi onlyeric.reg/onlyeric/busybox:latest Untagged: onlyeric.reg/onlyeric/busybox:latest (删除原有镜像) # docker pull onlyeric.reg/onlyeric/busybox:latest latest: Pulling from onlyeric/busybox Digest: sha256:507bc9f5e7844d90c630f141a93b073473e24bd0b27daef574ffa93f97d01181 Status: Downloaded newer image for onlyeric.reg/onlyeric/busybox:latest (镜像下载成功) |
基本权限管理
创建用户
Admin–>Users–>Create new user
创建用户组
Teams–>Create new team–>users
添加用户到组
users–>Add members–>Role(Viewer)–>test
修改Namespace所属组
Namespaces–>onlyeric–>Edit namespace–>Team–>users
异机测试
测试前提
- 添加hosts文件记录”192.168.2.14 onlyeric.reg”
- 将参数配置”--insecure-registry onlyeric.reg”到异机的Docker并重启服务
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | # docker login -u test -p zaq12wsx! onlyeric.reg Login Succeeded (登陆成功) # docker pull onlyeric.reg/onlyeric/busybox:latest latest: Pulling from onlyeric/busybox 8ddc19f16526: Pull complete a3ed95caeb02: Pull complete Digest: sha256:507bc9f5e7844d90c630f141a93b073473e24bd0b27daef574ffa93f97d01181 Status: Downloaded newer image for onlyeric.reg/onlyeric/busybox:latest # docker images|grep busybox onlyeric.reg/onlyeric/busybox latest 332de81782ef 3 weeks ago 1.093 MB (下载镜像成功) |
至此Nginx+Portus+Registry的部署过程及基本配置已经完成。由于此次配置的环境没有SSL相关安全的配置,建议仅在开发测试环境使用该方案。
文末特别感谢Wilson@擎天柱和Iason@CMDT的无损交流和倾情指导。
PS:Portus本身是支持生产环境的安全部署的,关注”小张烤茄”并回复”portus”,会有惊喜呈上。(各位看官请原谅此等无耻求关注行为…)
这篇关于干货|Nginx+Portus+Registry搭建私有镜像仓库的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!