Docker - 仓库(8)

一. 初始Docker 仓库

    在之前几篇文章中,使用过很多镜像创建实例,但是大家有没有发现以下几个问题

    ● 拉取的镜像只在当前服务器,只能本地使用

    ● 多个服务器部署同一个应用时,会拉取多次镜像

    ● 应用集群节点数过多,同一时间去拉取会消耗很大的网络出口带宽

    ● 命名规范性,一台服务器上部署多个应用模块,则命名需要很强的规范性

    ● 不便管理,一台服务器上部署多个项目模块时,无法对每个项目的模块进行区分

    Yum仓库,当本地需要去拉取依赖包时只需要进行认证、配置就可以直接下载。而Docker 仓库,就是与Yum起到相同功能的角色,一个是解决系统环境依赖包问题,一个是解决镜像管理、拉取问题

二. Docker 仓库软件介绍

    ● 第三方远程仓库

        Docker Hub、阿里云、网易云仓库,镜像存储在第三方云上

    ● Docker Repository

        Docker自身提供的一款私有仓库,没有Web Ui管理页面

    ● 开源技术实现

        Harbor,提供丰富的Api操作接口以及完善的Web UI功能

    本文着重介绍"Harbor"仓库的实现

三. Harbor仓库的部署与使用

    3.1 Harbor官网地址

            https://github.com/goharbor/harbor/releases

    3.2 Harbor系统要求说明

            docker 17.06.0-ce +和docker-compose 1.18.0+

    3.3 本文使用版本说明

[root@bjtn-app183-214 Harbor]# docker info | grep -i "server version"
Server Version: 18.06.3-ce
-rwxr-x--- 1 root root 643358224 May  2 14:32 harbor-offline-installer-v1.10.2.tgz
[root@bjtn-app183-214 Harbor]# pwd
/opt/app/Harbor
[root@bjtn-app183-214 Harbor]# ll
total 628280
-rwxr-x--- 1 root root 643358224 May  2 14:32 harbor-offline-installer-v1.10.2.tgz

    3.4 安装docker compose

[root@bjtn-app183-214 Harbor]# curl -L https://get.daocloud.io/docker/compose/releases/download/1.25.1/docker-compose-`uname -s`-`uname -m` -o /usr/local/bin/docker-compose
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100   423  100   423    0     0    337      0  0:00:01  0:00:01 --:--:--   337
100 16.2M  100 16.2M    0     0   647k      0  0:00:25  0:00:25 --:--:--  702k
[root@bjtn-app183-214 Harbor]# chmod +x /usr/local/bin/docker-compose && sudo ln -s /usr/local/bin/docker-compose /usr/bin/docker-compose
[root@bjtn-app183-214 Harbor]# docker-compose -v
docker-compose version 1.25.1, build a82fef07

    3.5 Harbor仓库支持https

            docker、maven对接Harbor默认是https

[root@bjtn-app183-214 cert]# pwd
/opt/app/Harbor/cert
[root@bjtn-app183-214 cert]# openssl genrsa -out docker-repo.key 4096
Generating RSA private key, 4096 bit long modulus
.............................................................................................................................................................................................................................++
....................................................................++
e is 65537 (0x10001)
[root@bjtn-app183-214 cert]# openssl req -x509 -new -nodes -sha512 -days 36500 \
> -subj "/C=TW/ST=Taipei/L=Taipei/O=example/OU=Personal/CN=docker-repo.com" \
> -key docker-repo.key \
> -out docker-repo.crt
[root@bjtn-app183-214 cert]# ll
total 8
-rw-r----- 1 root root 2033 May  2 14:44 docker-repo.crt
-rw-r----- 1 root root 3243 May  2 14:43 docker-repo.key

    3.6 部署Harbor

解压tar包
[root@bjtn-app183-214 Harbor]# pwd
/opt/app/Harbor
[root@bjtn-app183-214 Harbor]# tar -xf harbor-offline-installer-v1.10.2.tgz 
[root@bjtn-app183-214 Harbor]# mv harbor/* ./
[root@bjtn-app183-214 Harbor]# rm -rf harbor
修改配置
hostname:	本地主机IP
https:		https端口以及证书文件
	port: 
	certificate:	指明crt秘钥文件
	private_key:	指明key秘钥文件
data_volume:	数据存储路径
harbor_admin_password:	登录Harbor Web UI密码

进行初始化,会拉取镜像文件
[root@bjtn-app183-214 Harbor]# ./prepare 
prepare base dir is set to /opt/app/Harbor
Unable to find image 'goharbor/prepare:v1.10.2' locally
v1.10.2: Pulling from goharbor/prepare
ae8395e171fb: Pull complete 
ca35e8aaa3ab: Pull complete 
40fe63fa9717: Pull complete 
b716a0e0062b: Pull complete 
611e775dac46: Pull complete 
456ee3045669: Pull complete 
3dfaed1ae811: Pull complete 

进行安装
./install.sh

    3.7 尝试访问主页

Docker - 仓库(8)

四. Docker客户端 与 Harbor之间交互

    4.1 Docker 认证 Harbor

            修改docker启动配置,新添Harbor仓库地址 --insecure-registry harbor的主机IP,笔者认为每一台docker客户端都需要配置

ExecStart=/usr/bin/dockerd --graph /opt/app/Docker --insecure-registry https://10.10.183.214

            重启Docker Daemon

systemctl daemon-reload
systemctl restart docker

            进行登录认证

[root@bjtn-app183-214 Harbor]# docker login 10.10.183.214
Username: admin
Password: 
WARNING! Your password will be stored unencrypted in /root/.docker/config.json.
Configure a credential helper to remove this warning. See
https://docs.docker.com/engine/reference/commandline/login/#credentials-store

Login Succeeded

    4.2 Harbor 创建临时项目

Docker - 仓库(8)

    4.3 为镜像打标签

            命令格式:docker tag [SOURCE_IMAGE][:TAG] [HarborIp]/[Repository]/IMAGE[:TAG]

            这里以rancher-server为例

[root@bjtn-app183-214 ~]# docker images | grep rancher
rancher/server                                                                v1.6.12             f61683a6ad09        3 years ago         968MB
[root@bjtn-app183-214  ~]# docker tag rancher/server:v1.6.12 10.10.183.214/docker-harbor-test1/docker-rancher-server:version1
[root@bjtn-app183-214 ~]# docker images | grep rancher
10.10.183.214/docker-harbor-test1/docker-rancher-server                       version1            f61683a6ad09        3 years ago         968MB
rancher/server

    4.4 Docker客户端 上传镜像

            命令格式:docker push [HarborIp]/[Repository]/[Image]:[Tag]

 [root@bjtn-app183-214 ~]# docker push 10.10.183.214/docker-harbor-test1/docker-rancher-server:version1
The push refers to repository [10.10.183.214/docker-harbor-test1/docker-rancher-server]
b05601ba6e00: Pushed 
753ee21c6bb5: Pushed 
....
version1: digest: sha256:627047da2ec626d3ce9f090834c8e29274c0899df962abbeee8a06ee0617e8c5 size: 4302

    4.5 验证Harbor仓库下载

            下载命令格式:docker pull [HarborIp]/[Repository]/[Image]:[Tag]

            删除本地与"rancher"相关的镜像

[root@bjtn-app183-214 ~]# docker rmi `docker images | grep -i "rancher" | awk '{print $3}' | xargs` --force
Untagged: 10.10.183.214/docker-harbor-test1/docker-rancher-server:version1
Untagged: 10.10.183.214/docker-harbor-test1/docker-rancher-server@sha256:627047da2ec626d3ce9f090834c8e29274c0899df962abbeee8a06ee0617e8c5
Untagged: rancher/server:v1.6.12
Untagged: rancher/server@sha256:19df74c0a542f3c105648436a806cc78a6db89c96f5421d0eaecfb5dd5947bce
Deleted: sha256:f61683a6ad0906c80b9e2c698842ba8c55f971f68aa03ad6cc8712358fd74de1

            docker客户端下载"rancher"镜像

[root@bjtn-app183-214 ~]# docker pull 10.10.183.214/docker-harbor-test1/docker-rancher-server:version1
version1: Pulling from docker-harbor-test1/docker-rancher-server
c314617ce3f1: Already exists 
2389af727e43: Already exists 
...
Digest: sha256:627047da2ec626d3ce9f090834c8e29274c0899df962abbeee8a06ee0617e8c5
Status: Downloaded newer image for 10.10.183.214/docker-harbor-test1/docker-rancher-server:version1
[root@bjtn-app183-214 ~]# docker images | grep -i "rancher"
10.10.183.214/docker-harbor-test1/docker-rancher-server                       version1            f61683a6ad09        3 years ago         968MB

            说明: Harbor仓库显示的镜像大小只有"334.86MB",但是下载到Docker客户端本地后大小有"968MB",个人理解是Harbor仓库只展示了最外层镜像的大小,没有展示内部封装或者里依赖镜像大小

五. Harbor Api接口使用

        ● 以下脚本实现了调用Harbor Api定时清理所有项目所有仓库的历史镜像信息,只保留每个仓库近10次镜像

● 仓库中镜像的tag已[server]:[time](服务名称:时间戳)规范命名

● 笔者在项目中部署时未使用"latest"版本,部署总是有问题(未解决),在部署中以最新时间戳的tag进行部署,后续可根据业务需求进行更改

● mvn编译+上传镜像到Harbor是在代码层实现,笔者只是实现了拉取+部署,后续可以调研下"jenkins docker cloud"插件使用

● 关于其他Api接口使用方法可以自行研究下

#!/bin/bash
# Created on Wed Mar  3 17:25:18 CST 2021
# author:wtc

# haror 认证信息
harbor_host="$ip"
harbor_user="$user"
harbor_pass="$pass"

# 获取所有项目信息
get_all_project_id() {
	project_id_data=`curl -s -u "$harbor_user:$harbor_pass" -X GET --insecure --header 'Accept: application/json' "https://$harbor_host/api/search" | jq ".project" | jq ".[].project_id" | xargs`
	echo "$project_id_data"
}
# 获取所有仓库信息
get_all_repo_name() {
	for project_id in $project_id_data;do
		repo_name_data=`curl -s -u "$harbor_user:$harbor_pass" -X GET --insecure --header 'Accept: application/json' "https://$harbor_host/api/repositories?project_id=$project_id" | jq .[].name | xargs`
		echo "$repo_name_data"
	done
}
repo_name_data=`get_all_repo_name`
# 保留近10个最新镜像文件,包含latest
get_all_image_tag() {
	for repo_name in $repo_name_data;do
		tag_data=`curl -s -u "$harbor_user:$harbor_pass" -X GET --insecure --header 'Accept: application/json'  "https://$harbor_host/api/repositories/$repo_name/tags" | jq ".[].name" | xargs`
		array_tag=(`echo $tag_data`)
		# 控制保留历史版本个数
		if [ ${#array_tag[@]} -le 10 ];then
			echo "$repo_name 仓库的镜像数未超过10个,不做处理!"
			continue
		else
			for ((tag_index=0;tag_index<=`expr ${#array_tag[@]} - 10`;tag_index++));do
				tag_name=${array_tag[$tag_index]}
				if [ "$tag_name" == "latest" ];then
					continue
				else
					curl -s -u "$harbor_user:$harbor_pass" -X DELETE --insecure --header 'Accept: application/json'  "https://$harbor_host/api/repositories/$repo_name/tags/$tag_name"
					if [ $? -eq 0 ];then
						echo "$repo_name 仓库的镜像${array_tag[$tag_index]}删除成功!"
					else
						echo "$repo_name 仓库的镜像${array_tag[$tag_index]}删除失败!"
					fi
				fi
			done
		fi
	done
}
# 删除|部署
if [ "$#" -ne 6 ];then
	# 开启是否删除镜像
	get_all_image_tag
else
	# 项目名称在代码中写死,通过Jenkins传参 ${project}、${mould}、${PortMapping}、${YamlPath}、${YamlName}、${LogPath}
	echo "$@"
	# 部署由jenkins 个性化传参,这里不做展示
fi


上一篇:java调用 webservices接口实现天气预报


下一篇:第四章 部署K8s前准备工作