一、初识docker
1.1、安装docker
# 配置主机名:
hostnamectl set-hostname docker1 && bash
# 关闭防火墙
systemctl disable firewalld --now
# 关闭 iptables 防火墙
# 安装 iptables
yum install iptables-services -y
# 禁用 iptables
service iptables stop && systemctl disable iptables
# 清空防火墙规则
iptables -F
# 关闭 selinux
setenforce 0
sed -i 's/SELINUX=enforcing/SELINUX=disabled/g' /etc/selinux/config
注意:修改 selinux 配置文件之后,重启机器,selinux 才能永久生效
getenforce
显示 Disabled 表示 selinux 关闭成功
# 配置时间同步
yum install -y ntp ntpdate
ntpdate cn.pool.ntp.org
# 编写计划任务
crontab -e
* */1 * * * /usr/sbin/ntpdate cn.pool.ntp.org
# 重启 crond 服务使配置生效:
systemctl restart crond
# 安装基础软件包
yum install -y wget net-tools nfs-utils lrzsz gcc gcc-c++ make cmake libxml2-devel openssl-devel curl curl-devel unzip sudo ntp libaio-devel wget vim ncurses-devel autoconf automake zlib-devel python-devel epel-release openssh-server socat ipvsadm conntrack yum-utils
# 配置 docker-ce 国内 yum 源(阿里云)
yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
# 安装 docker 依赖包
yum install -y device-mapper-persistent-data lvm2
# 安装 docker-ce
yum -y install docker-ce
# 启动 docker 服务
systemctl enable docker --now
systemctl status docker
# 查看 Docker 版本信息
docker version
1.2、开启包转发功能和修改内核参数
# 内核参数修改:br_netfilter 模块用于将桥接流量转发至 iptables 链,br_netfilter 内核参数需要开启转发。
modprobe br_netfilter
cat > /etc/sysctl.d/docker.conf << END
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1
END
# 使参数生效
sysctl -p /etc/sysctl.d/docker.conf
# 重启后模块失效,下面是开机自动加载模块的脚本
cat > /etc/rc.sysinit << END
#!/bin/bash
for file in /etc/sysconfig/modules/*.modules ; do
[ -x $file ] && $file
done
END
# 在/etc/sysconfig/modules/目录下新建文件如下
cat > /etc/sysconfig/modules/br_netfilter.modules << END
modprobe br_netfilter
END
# 增加权限
chmod 755 /etc/sysconfig/modules/br_netfilter.modules
# 重启机器模块也会自动加载
lsmod | grep br_netfilter
# 注: Docker 安装后出现:WARNING: bridge-nf-call-iptables is disabled 的解决办法:
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1:
将 Linux 系统作为路由或者 VPN 服务就必须要开启 IP 转发功能。当 linux 主机有多个网卡时一个网卡收到的信息是否能够传递给其他的网卡 ,如果设置成 1 的话 可以进行数据包转发,可以实现 VxLAN 等功能。不开启会导致 docker 部署应用无法访问。
# 重启 docker
systemctl restart docker
1.3、配置docker镜像加速器
# 登陆阿里云镜像仓库
https://cr.console.aliyun.com/cn-hangzhou/instances/mirrors
# 执行以下命令即可
sudo mkdir -p /etc/docker
sudo cat > /etc/docker/daemon.json <<-'EOF'
{
"registry-mirrors":["https://rsbud4vc.mirror.aliyuncs.com","https://registry.docker-cn.com","https://docker.mirrors.ustc.edu.cn","https://dockerhub.azk8s.cn","http://hub-mirror.c.163.com","http://qtid6917.mirror.aliyuncs.com", "https://rncxm540.mirror.aliyuncs.com"],
"exec-opts": ["native.cgroupdriver=systemd"],
"insecure-registries": ["harbor.lab.home"]
}
EOF
sudo systemctl daemon-reload
sudo systemctl restart docker
1.4、docker的基本用法
1.4.1、镜像相关
# 搜索镜像
docker search centos
'解释说明:
- NAME: 镜像仓库源的名称
- DESCRIPTION: 镜像的描述
- OFFICIAL: 是否 docker 官方发布,有ok的为官方发布的
- stars: 类似 Github 里面的 star,表示点赞、喜欢的意思。
- AUTOMATED: 自动构建。
# 下载镜像
docker pull centos
# 查看本地镜像
docker images
# 把镜像做成离线压缩包
docker save -o centos.tar.gz centos
-o:指定输出文件
# 将离线压缩包加载到docker里
docker load -i centos.tar.gz
# 删除镜像
docker rmi -f centos:latest
1.4.2、容器相关
# 以交互式方式启动并进入容器
docker run --name centos -it centos /bin/bash
--name:指定容器名
-i:直接进入容器
-t:给容器分配一个伪终端
# 以守护进程的方式启动容器(进入容器后退出容器不会使容器退出运行)
docker run --name centos -dt centos
-d:在后台运行容器
# 进入容器
docker exec -it centos /bin/bash
# 查看正在运行的容器
docker ps
-a:查看所有容器(包括已停止运行的容器)
# 停止容器
docker stop 容器名/容器ID
# 启动已停止的容器
docker start 容器名/容器ID
# 删除容器
docker rm -f 容器名/容器ID
-f:强制删除
# 查看容器日志
docker logs 容器名
# 特权模式
--privileged=true 开启真正的特权模式
--device 参数:将主机设备添加到容器
# 提交docker镜像
docker commit -a "xkj" -m "eve" fe3eb6292c61 eve:v1
1.5、实战使用docker部署nginx服务
# 启动容器
docker run --name nginx -p 80 -itd centos
-p:将容器的80端口随机映射到物理机的某个端口上
# 查看容器(可以看到80端口映射在物理机上的哪个端口)
docker ps -a
# 在docker中安装nginx
docker exec -it nginx /bin/bash
ip a
rm -rf /etc/yum.repos.d/*
curl -o /etc/yum.repos.d/CentOS-Base.repo https://mirrors.aliyun.com/repo/Centos-vault-8.5.2111.repo
yum -y install wget vim nginx
yum -y install vim-enhanced
# 创建静态网页文件
mkdir /var/www/html/ -p
cat > /var/www/html/index.html << 'EOF'
<html>
<head>
<title>nginx in docker</title>
</head>
<body>
<h1>hello,My Name is xianchao</h1>
</body>
</html>
EOF
# 修改nginx配置文件
vim /etc/nginx/nginx.conf
root /var/www/html;
# 启动nginx服务
/usr/sbin/nginx
1.6、二进制安装docker
1.6.1、安装
# 链接
https://download.docker.com/linux/static/stable/x86_64/
# 解压
tar zxvf docker-18.03.1-ce.tgz
# 复制二进制文件到/usr/bin目录下
cp docker/* /usr/bin/
# 检查
docker version
# 配置 docker.service文件
cat > /etc/systemd/system/docker.service <<EOF
[Unit]
Description=Docker Application Container Engine
Documentation=https://docs.docker.com
After=network-online.target firewalld.service
Wants=network-online.target
[Service]
Type=notify
ExecStart=/usr/bin/dockerd
ExecReload=/bin/kill -s HUP $MAINPID
LimitNOFILE=infinity
LimitNPROC=infinity
TimeoutStartSec=0
Delegate=yes
KillMode=process
Restart=on-failure
StartLimitBurst=3
StartLimitInterval=60s
[Install]
WantedBy=multi-user.target
EOF
# 启动服务
systemctl daemon-reload
systemctl enable docker --now
1.6.2、配置docker镜像加速器
# 登陆阿里云镜像仓库
https://cr.console.aliyun.com/cn-hangzhou/instances/mirrors
# 执行以下命令即可
sudo mkdir -p /etc/docker
sudo cat > /etc/docker/daemon.json <<-'EOF'
{
"registry-mirrors":["https://y8y6vosv.mirror.aliyuncs.com","https://registry.dockecn.com","https://docker.mirrors.ustc.edu.cn","https://dockerhub.azk8s.cn","http://humirror.c.163.com"]
}
EOF
sudo systemctl daemon-reload
sudo systemctl restart docker
二、dockerfile构建镜像
2.1、dockerfile基础介绍
dockerfile是一个用来构建镜像的文本文件,可以将一个基础镜像搭建为可部署的镜像
# 使用dockerfile文件构建镜像
docker build -f dockerfile文件 -t 镜像名
-f:指定使用的dockerfile文件
-t:指定生成的镜像名称
# dockerfile构建镜像过程
- 从基础镜像运行成为容器
- 运行dockerfile中的一条指令,对容器做出修改
- 执行类似于docker commit的操作,提交出一个新的镜像层
- 基于刚刚的新镜像层运行一条指令,对容器做出修改
- 提交新的镜像层,如此循环,直到所有指令执行结束
2.2、dockerfile语法解析
2.2.1、FROM,MAINTAINER,RUN,EXPOSE
# FROM 镜像名
基础的镜像,之后所有的指令都是基于该镜像做出的修改
# MAINTAINER 作者
# RUN 指令
包含两种模式:shell和exec模式
- shell模式:直接加命令
- exec模式:RUN ["executable","param1","param2"]
例如:RUN ["/bin/bash","-c","echo hello"]
# EXPOSE 端口
声明端口,可用于后续启动镜像时做端口映射
- 可以是多个端口
2.2.2、CMD
# CMD 指令
用于指定在镜像启动成为容器时,在容器中运行的命令(如启动时开启nginx)
- 和'RUN'相同,都有shell和bash两种模式
例如:CMD ["/usr/sbin/nginx","-g","daemon off;"]
# 创建 index.html
cat > index.html << 'EOF'
<html>
<head>
<title>page added to dockerfile</title>
</head>
<body>
<h1>i am in df_test </h1>
</body>
</html>
EOF
# 下载centos的yum源
curl -o ./Centos-vault-8.5.2111.repo https://mirrors.aliyun.com/repo/Centos-vault-8.5.2111.repo
# 使用dockerfile构建镜像可以使用-f指定dockerfile文件名,不知道默认为当前目录下的Dockerfile
# 简单的dockerfile(需要先将Centos-vault-8.5.2111.repo文件下载下来)
FROM centos
MAINTAINER xkj
RUN rm -f /etc/yum.repos.d/*
RUN curl -o /etc/yum.repos.d/Centos-vault-8.5.2111.repo https://mirrors.aliyun.com/repo/Centos-vault-8.5.2111.repo
RUN yum -y install wget nginx
COPY index.html /usr/share/nginx/html/
EXPOSE 80
ENTRYPOINT ["/usr/sbin/nginx","-g","daemon off;"]
# CMD演示实例
FROM centos
MAINTAINER xkj
RUN rm -f /etc/yum.repos.d/*
RUN curl -o /etc/yum.repos.d/Centos-vault-8.5.2111.repo https://mirrors.aliyun.com/repo/Centos-vault-8.5.2111.repo
RUN yum -y install wget nginx --nogpgcheck
COPY index.html /usr/share/nginx/html/
EXPOSE 80
CMD ["/usr/sbin/nginx","-g","daemon off;"]
构建镜像:docker build -f dockerfile文件名 -t="dockerfile/nginx_cmd:v1" .
启动容器:docker run -p 8080:80 --name cmd_test -dt dockerfile/nginx_cmd:v1
查看页面内容:curl 192.168.68.130:8080
2.2.3、ENTRYPOINT
类似于CMD,但其不会被'docker run'的命令行参数指定的指令而覆盖,且这些命令行参数会被当作参数送给'ENTRYPOINT'指令指定的程序。
但如果命令行'docker run'中使用了'--entrypoint'选项时,将覆盖'CMD'指令指定的程序.
优点:执行docker run时,可以知道entrypoint运行所需的参数
# 注意:当一个 dockerfile 中有多个 ENTRYPOINT 指令,只有最后一个会生效
# 格式
ENTERYPOINT [“executable”,“param1”,“param2”](exec 模式)
ENTERYPOINT command (shell 模式)
可以搭配'CMD'命令使用:一般只有变参才会使用CMD,这里的CMD等于是给ENTRYPOINT传参。
# 实例:假设已通过dockerfile构建了nginx:test镜像,在dockerfile中有如下字段
FROM nginx
ENTRYPOINT ["nginx", "-c"] # 定参
CMD ["/etc/nginx/nginx.conf"] # 变参
不传参运行:docker run nginx:test
- 此时容器内会默认运行命令:nginx -c /etc/nginx/nginx.conf
传参运行:docker run nginx:test -c /etc/nginx/new.conf
- 此时容器内会默认运行命令:nginx -c /etc/nginx/new.conf
2.2.4、COPY
将本地的文件或目录拷贝到容器中
# 格式
COPY [--chown=<user>:<group>] <源路径 1>... <目标路径>
COPY [--chown=<user>:<group>] ["<源路径 1>",... "<目标路径>"]
其中[--chown=<usser>:<group>]为可选参数,含义为用户可以改变文件的所有者和所属组
# 在源文件和源目录可以使用通配符,如
COPY hom* /mydir/
COPY hom?.txt /mydir/
# 如果语句中指定的目标目录不存在,则会自动创建
# 实例
cat > index.html << 'EOF'
<html>
<head>
<title>page added to dockerfile</title>
</head>
<body>
<h1>i am in df_test </h1>
</body>
</html>
EOF
cat > copy_test << 'EOF'
FROM centos
MAINTAINER xianchao
RUN yum install wget -y
RUN yum install nginx -y
COPY index.html /usr/share/nginx/html/
EXPOSE 80
ENTRYPOINT ["/usr/sbin/nginx","-g","daemon off;"]
EOF
docker build -f copy_test -t='dockerfile/copy:v1' .
docker run -dt -p 80 --name html dockerfile/copy:v1
docker ps | grep html
2.2.5、ADD
同样是拷贝,使用方法与COPY相同
# ADD与COPY相比的优缺点
优点:ADD可以在拷贝的同时,将'.tar.gz'或'.tar.bz2'等文件在拷贝的同时,将该文件解压到目标路径下
缺点:无法在不解压的情况下拷贝tar压缩文件。且会令镜像构建缓存失效,从而可能会令镜像构建变得比较缓慢
如果单纯拷贝文件,推荐使用COPY
2.2.6、VOLUME
定义匿名数据卷。启动容器时忘记挂载数据卷时,会自动挂载到数据卷。
# 作用
- 避免重要数据因容器重启而丢失
- 避免容器不断变大
# 格式
VOLUME ["<路径1>","<路径2>"...]
VOLUME <路径>
# 在启动容器时,可以通过-v参数来实现容器的持久化存储,即修改挂载点
VOLUME ["/data"]
2.2.7、WORKDIR
# 指定工作目录。该目录会在构建镜像的每一层都存在
docker build 构建镜像过程中,每执行一个RUN都是新建一层。只有通过WORKDIR指定的目录会在每一层都存在
# WORKDIR指定的工作目录必须是提前创建好的,且必须填写绝对路径
WORKDIR /path/to/workdir
2.2.8、ENV
指定容器中的环境变量
# 格式
ENV <key> <value>
ENV <key>=<value>...
# 实例
ENV NODE_VERSION 12.18.3
RUN curl -SLO "https://nodejs.org/dist/v$NODE_VERSION/node-v$NODE_VERSION-linux-x64.tar.xz" && curl -SLO "https://nodejs.org/dist/v$NODE_VERSION/SHASUMS256.txt.asc"
2.2.9、USER
指定后续命令的执行用户及用户组
# 格式
USER <用户名>[:<用户组>]
# 实例
USER daemon
USER nginx
USER user
USER uid
USER user:group
USER uid:gid
USER user:gid
USER uid:group
2.2.10、ONBUILD
# 用于延迟构建命令的执行
- 简单点说就是,用这个dockerfile构建一个镜像时不会执行该命令。
- 只有当有人用这个dockerfile构建好的镜像进行二次构建时,才会执行该命令的内容
# 作用
为镜像添加触发器
# 实例
cat > index.html << 'EOF'
<html>
<head>
<title>page added to dockerfile</title>
</head>
<body>
<h1> ONBUILD </h1>
</body>
</html>
cat > onbuild_test << 'EOF'
FROM centos
MAINTAINER xianchao
RUN yum install wget -y
RUN yum install nginx -y
ONBUILD COPY index.html /usr/share/nginx/html/
EXPOSE 80
ENTRYPOINT ["/usr/sbin/nginx","-g","daemon off;"]
docker build -t="onbuild-nginx:v1" .
docker run -d --name html4 -p 80 onbuild-nginx:v1
docker ps | grep html4
查看网页内容
vim dockerfile
FROM onbuild-nginx:v1
MAINTAINER xianchao
ENTRYPOINT ["/usr/sbin/nginx","-g","daemon off;"]
EXPOSE 80
docker build -t="onbuild-nginx1" .
docker run -d --name htm5 -p 80 onbuild-nginx1
docker ps | grep htm5
查看网页内容
2.2.11、LABEL
添加容器元数据
# 格式
LABEL <key>=<value> <key>=<value> <key>=<value> ...
# 实例:添加镜像作者
LABEL org.opencontainers.image.authors="xu"
2.2.12、HEALEHCHECK
用于指定某个程序或指令来监控docker容器服务的运行状态
# 格式
HEALTHCHECK [选项] CMD <命令>:设置检查容器健康状况的命令,后面跟的命令格式和'CMD'相同
HEALTHCHECK NONE :如果基础镜像中指定了容器健康检查指令,可以使用该命令屏蔽掉
2.2.13、ARG
设置dockerfile构建过程中的环境变量,只在'docker build'过程中起作用
# 格式:
ARG <参数名>[=<默认值>]
# 该命令指定的环境变量,可以在docker build时使用 --build-arg <参数名>=<值> 选项进行覆盖
2.3、实战构建nginx镜像
mkdir nginx
cd nginx
cat > Dockerfile << 'EOF'
FROM centos
MAINTAINER xianchao
RUN rm -rf /etc/yum.repos.d/*
RUN curl -o /etc/yum.repos.d/Centos-vault-8.5.2111.repo https://mirrors.aliyun.com/repo/Centos-vault-8.5.2111.repo
RUN yum install wget -y
RUN yum install nginx -y
COPY index.html /usr/share/nginx/html/
EXPOSE 80
ENTRYPOINT ["/usr/sbin/nginx","-g","daemon off;"]
EOF
cat > index.html << 'EOF'
<html>
<head>
<title>page added to dockerfile</title>
</head>
<body>
<h1>Hello,My Name is Xianchao,My wechat is luckylucky421302 </h1>
</body>
</html>
EOF
docker build -t="test/nginx:v1" .
docker run --name nginx -p 8000:80 -dt test/nginx:v1
2.4、实战构建tomcat镜像
mkdir tomcat
cd tomcat
# 上传 apache-tomcat-8.0.26.tar.gz 和 jdk-8u45-linux-x64.rpm
cat > Dockerfile << 'EOF'
FROM centos
MAINTAINER xianchao
RUN rm -rf /etc/yum.repos.d/*
RUN curl -o /etc/yum.repos.d/Centos-vault-8.5.2111.repo https://mirrors.aliyun.com/repo/Centos-vault-8.5.2111.repo
RUN yum install wget -y
ADD jdk-8u45-linux-x64.rpm /usr/local/
ADD apache-tomcat-8.0.26.tar.gz /usr/local/
RUN cd /usr/local && rpm -ivh jdk-8u45-linux-x64.rpm
RUN mv /usr/local/apache-tomcat-8.0.26 /usr/local/tomcat8
EXPOSE 8080
docker build -t="tomcat8:v1" .
docker run --name tomcat8 -p 8080:8080 -dt tomcat8
docker exec -it tomcat8 /bin/bash
# 启动toncat
/usr/local/tomcat8/bin/startup.sh
# 若想开启容器直接启动服务,dockerfile如下
FROM centos
MAINTAINER xianchao
RUN rm -rf /etc/yum.repos.d/*
RUN curl -o /etc/yum.repos.d/Centos-vault-8.5.2111.repo https://mirrors.aliyun.com/repo/Centos-vault-8.5.2111.repo
RUN yum install wget -y
ADD jdk-8u45-linux-x64.rpm /usr/local/
ADD apache-tomcat-8.0.26.tar.gz /usr/local/
RUN cd /usr/local && rpm -ivh jdk-8u45-linux-x64.rpm
RUN mv /usr/local/apache-tomcat-8.0.26 /usr/local/tomcat8
ENTRYPOINT /usr/local/tomcat8/bin/startup.sh && tail -F /usr/local/tomcat8/logs/catalina.out
EXPOSE 8080
2.5、实战构建nginx镜像
刚开始接触docker,在利用dockerfile通过centos7的镜像构建nginx镜像时,最后的启动命令上面遇到很多启动失败。然后想了4种启动方法,有两种能正常运行。当时是想不明白为什么,继续深入学习后发现了其中的一些知识没学习到。作记录,分享相互学习。
构建nginx的Dockerfile上部分的内容为:
FROM centos:centos7
MAINTAINER xkj
RUN yum -y install gcc gcc-c++ pcre-devel openssl-devel make
ADD http://nginx.org/download/nginx-1.22.1.tar.gz .
RUN useradd -s /sbin/nologin nginx && cd nginx-1.22.1 && ./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_stub_status_module --with-http_ssl_module && make && make install
EXPOSE 80
ENV PATH /usr/local/nginx/sbin:$PATH
[root@master1 ~]# cat nginx
FROM nginx-xkj
MAINTAINER xkj
RUN /usr/local/nginx/sbin/nginx
ENTRYPOINT ["/usr/local/nginx/sbin/nginx","-g","daemon off;"]
ENV PATH $PATH:/usr/local/nginx/sbin/
EXPOSE 80
在Dockerfile的最后启动命令上纠结过4种启动方式: Dockerfile 启动命令
docker run -p 80:80 --name nginx1 -v /data/html:/usr/local/nginx/html -v /data/conf/nginx.conf:/usr/local/nginx/conf/nginx.conf -v /data/logs:/usr/local/nginx/logs -d nginx:v1
Dockerfile 启动命令 docker run 启动结果
1 | CMD nginx | 端口无映射 |
2 | CMD nginx -g ‘daemon off;’ | 端口正常映射 |
3 | CMD [“nginx”] | 端口无映射 |
4 | CMD [“nginx”, “-g”,“daemon off;”] | 端口正常映射 |
运行方式都是一样,并得出以下4种结果:
1 | ENTRYPOINT nginx | 端口无映射 |
2 | ENTRYPOINT nginx -g ‘daemon off;’ | 端口正常映射 |
3 | ENTRYPOINT [“nginx”] | 端口无映射 |
4 | ENTRYPOINT [“nginx”, “-g”,“daemon off;”] | 端口正常映射 |
经过继续深入的学习后发现了其中的问题。 第一种运行失败,是因为使用的是shell格式。使用shell的话,实际的命令会被包装为sh -c的参数的形式进行执行。比如:
ENTRYPOINT echo $HOME
在实际执行中,会将其变更为:
ENTRYPOINT [ "sh", "-c", "echo $HOME" ]
那么当我用第一种的时候,就相当于执行:
ENTRYPOINT [ "sh", "-c", "nginx"]
所以和第三种类似,经过查阅资料,执行没有运行起来是因为:
执行失败是因为docker容器默认会把容器内部第一个进程,也就是pid=1的程序作为docker容器是否正在运行的依据,如果docker容器里pid=1的进程结束了,那么docker容器便会直接退出。
docker run的时候把command为容器内部命令,如果使用nginx,那么nginx程序将后台运行,这个时候nginx并不是pid为1的程序,而是执行bash,这个bash执行了nginx指令后就结束了,所以容器也就退出,端口没有进行映射。
所以就需要加-g 'daemon off;'的启动参数。daemon的作用是否让nginx运行后台;默认为on,调试时可以设置为off,使得nginx运行在前台,所有信息直接输出控制台.
三、docker数据持久化及网络模式介绍
3.1、数据持久化
# 为容器添加数据卷
1.使用-v参数可以将物理机的文件夹挂载到容器中成为容器的数据卷,当指定的文件夹不存在时,会自动创建
docker run --name volume -v /data1:/data1 -dt centos /bin/bash
2.也可以指定数据卷的权限
docker run --name volume -v /data1:/data1:ro -dt centos /bin/bash
# 构建包含数据卷的镜像
1.dockerfile
FROM centos
VOLUME ["/data1","/data2"]
CMD /bin/bash
2.构建镜像
docker buidl -t='volume' .
3.启动容器
docker run --name volume -dt volume
通过以上方法构建出的容器即可称为数据卷容器,该容器中的数据卷('/data1、/data2')可以被其他容器挂载,从而实现数据共享
# 挂载数据卷容器
1.启动数据卷容器
docker run --name volume -dt volume
2.启动其他容器,同时挂载数据卷容器
docker run --name test --volumes-from volume -dt centos bash
3.进入容器并查看数据卷
[root@docker1 volume]# docker exec -it test bash
[root@f46b86442e77 /]# ls /
bin data1 data2 dev etc home lib lib64 lost+found media mnt opt proc root run sbin srv sys tmp usr var
[root@f46b86442e77 /]# cat /data1/love
i love you
# 数据卷的备份与还原
1.数据卷备份
docker run --name backup --volumes-from volume -v ~/backup:/backup centos tar -zcvf /backup/data1.tar.gz /data1/
2.数据卷还原
docker run --name backup --volumes-from volume -v ~/backup:/backup centos tar -zxvf /backup/data1.tar.gz -C /data1/
3.2、容器网络
3.2.1、四大网络模式
# 容器的网络模式
- 桥接模式:使用 --net=bridge指定,默认为桥接
- host模式:使用 --net=host指定,与物理机共享网络,容器中的网络即物理机的网络
- none模式:使用 --net=none指定,默认没有网口,需要自己设置
- container模式:使用 --net=container:[容器名或容器id]指定,与其他容器共享网络
# bridge模式
默认选择 bridge 的情况下,容器启动后会通过 DHCP 获取一个地址
docker run --name bridge -dti --privileged=true centos bash
# host模式
Docker 网络 host 模式是指共享宿主机的网络
docker run --name host -it --net=host --privileged=true centos bash
# none模式
Docker 网络 none 模式是指创建的容器没有网络地址,只有 lo 网卡
docker run -itd --name none --net=none --privileged=true centos
# container模式
Docker 网络 container 模式是指,创建新容器的时候,通过--net container 参数,指定其和已经存在的某个容器共享一个 Network Namespace。
docker run --name container2 --net=container:none -it --privileged=true centos
3.2.2、容器间相互访问
# 安装虚拟网桥管理工具
yum -y install bridge-utils
bridgectl show
# 允许所有容器互相访问
1.桥接
docker run --name test -itd test/nginx:v1
docker run --name test1 -itd test/nginx:v1
2.给容器网络设置别名(可以使容器IP地址发生变化后仍然找到对应容器)
docker run --name test -dt centos bash
docker run --name test1 --link=test:hh -dt centos bash
docker run --name test2 --link=test -dt centos bash
'可以通过容器名或别名访问其他容器'
'未进行别名定义则不可以通过容器名或别名进行访问'
四、docker资源配额及私有镜像仓库搭建
4.1、dockers资源配额
4.1.1、cpu
4.1.1.1、cpu份额(-c cpu-shares)
#查看配置份额的帮助命令:
[root@xianchaomaster1 ~]# docker run --help | grep cpu-shares
-c, --cpu-shares int CPU shares (relative weight)
例如: -c 1024 指定cpu份额为1024
- 默认每个 docker 容器的 cpu 份额值都是 1024。在同一个 CPU 核心上,同时运行多个容器时,容器的cpu 加权的效果才能体现出来。
# 说明
例: 两个容器 A、B 的 cpu 份额分别为 1000 和 500,结果会怎么样?
情况 1:A 和 B 正常运行,占用同一个 CPU,在 cpu 进行时间片分配的时候,容器 A 比容器 B 多一倍的机会获得 CPU 的时间片。
情况 2:分配的结果取决于当时其他容器的运行状态。比如容器 A 的进程一直是空闲的,那么容器 B 是可以获取比容器 A 更多的 CPU 时间片的; 比如主机上只运行了一个容器,即使它的 cpu 份额只有50,它也可以独占整个主机的 cpu 资源。
例 1:给容器实例分配 512 权重的 cpu 使用份额
参数: --cpu-shares 512
[root@xianchaomaster1 ~]# docker run -it --cpu-shares 512 centos /bin/bash
[root@df176dd75bd4 /]# cat /sys/fs/cgroup/cpu/cpu.shares
512
注:稍后,我们启动多个容器,测试一下是不是只能使用 512 份额的 cpu 资源。单独一个容器,看不出来使用的 cpu 的比例。 因没有 docker 实例同此 docker 实例竞争。
总结:
通过-c 设置的 cpu share 并不是 CPU 资源的绝对数量,而是一个相对的权重值。某个容器最终能分配到的 CPU 资源取决于它的 cpu share 占所有容器 cpu share 总和的比例。通过 cpu share 可以设置容器使用 CPU 的优先级。
比如在 host 中启动了两个容器:
docker run --name "container_A" -c 1024 ubuntu
docker run --name "container_B" -c 512 ubuntu
container_A 的 cpu share 1024,是 container_B 的两倍。当两个容器都需要 CPU 资源时,container_A 可以得到的 CPU 是 container_B 的两倍。
需要注意的是,这种按权重分配 CPU 只会发生在 CPU 资源紧张的情况下。如果 container_A 处于空闲状态,为了充分利用 CPU 资源,container_B 也可以分配到全部可用的 CPU。
4.1.1.2、cpu core:与cpu核心绑定,即容器只在这个核心上运行
# CPU core 核心控制
参数:--cpuset- 可以绑定 CPU
对多核 CPU 的服务器,docker 还可以控制容器运行限定使用哪些 cpu 内核和内存节点,即使用--cpuset-cpus 和--cpuset-mems 参数。对具有 NUMA 拓扑(具有多 CPU、多内存节点)的服务器尤其有用,可以对需要高性能计算的容器进行性能最优的配置。如果服务器只有一个内存节点,则--cpuset-mems 的配置基本上不会有明显效果。
# 扩展:
服务器架构一般分: SMP、NUMA、MPP 体系结构介绍
从系统架构来看,目前的商用服务器大体可以分为三类:
1. 即对称多处理器结构(SMP : Symmetric Multi-Processor) 例: x86 服务器,双路服务器。主板上有两个物理 cpu
2. 非一致存储访问结构 (NUMA : Non-Uniform Memory Access) 例: IBM 小型机pSeries 690
3. 海量并行处理结构 (MPP : Massive ParallelProcessing) 。 例: 大型机 Z14
4.1.1.3、CPU 配额控制参数的混合使用
在上面这些参数中,cpu-shares 控制只发生在容器竞争同一个 cpu 的时间片时有效。
如果通过 cpuset-cpus 指定容器 A 使用 cpu 0,容器 B 只是用 cpu1,在主机上只有这两个容器使用对应内核的情况,它们各自占用全部的内核资源,cpu-shares 没有明显效果。
# 如何才能有效果?
容器 A 和容器 B 配置上 cpuset-cpus 值并都绑定到同一个 cpu 上,然后同时抢占 cpu 资源,就可以
看出效果了。
例 1:测试 cpu-shares 和 cpuset-cpus 混合使用运行效果,就需要一个压缩力测试工具 stress 来让容器实例把 cpu 跑满。
如何把 cpu 跑满?
如何把 4 核心的 cpu 中第一和第三核心跑满?可以运行 stress,然后使用 taskset 绑定一下 cpu。
# 扩展:stress 命令
概述:linux 系统压力测试软件 Stress
[root@xianchaomaster1 ~]# yum install -y epel-release
[root@xianchaomaster1 ~]# yum install stress -y
stress 参数解释
-? 显示帮助信息
-v 显示版本号
-q 不显示运行信息
-n 显示已完成的指令情况
-t --timeout N 指定运行 N 秒后停止
--backoff N 等待 N 微妙后开始运行
-c 产生 n 个进程 :每个进程都反复不停的计算随机数的平方根,测试 cpu
-i 产生 n 个进程 :每个进程反复调用 sync(),sync()用于将内存上的内容写到硬盘上,测试磁盘 io
-m --vm n 产生 n 个进程,每个进程不断调用内存分配 malloc()和内存释放 free()函数 ,测试内存
--vm-bytes B 指定 malloc 时内存的字节数 (默认 256MB)
--vm-hang N 指定在 free 栈的秒数
-d --hadd n 产生 n 个执行 write 和 unlink 函数的进程
-hadd-bytes B 指定写的字节数
--hadd-noclean 不 unlink
注:时间单位可以为秒 s,分 m,小时 h,天 d,年 y,文件大小单位可以为 K,M,G
例 1:产生 2 个 cpu 进程,2 个 io 进程,20 秒后停止运行
[root@xianchaomaster1]# stress -c 2 -i 2 --verbose --timeout 20s
#如果执行时间为分钟,改 20s 为 1m
4.1.1.4、压测实验
# 压测实验
例 1:测试 cpuset-cpus 和 cpu-shares 混合使用运行效果,就需要一个压缩力测试工具 stress 来让容器实例把 cpu 跑满。 当跑满后,会不会去其他 cpu 上运行。 如果没有在其他 cpu 上运行,说明cgroup 资源限制成功。
实例 3:创建两个容器实例:docker10 和 docker20。 让 docker10 和 docker20 只运行在 cpu0 和
cpu1 上,最终测试一下 docker10 和 docker20 使用 cpu 的百分比。实验拓扑图如下:
运行两个容器实例
[root@xianchaomaster1 ~]# docker run -itd --name docker10 --cpuset-cpus 0,1 --cpu-shares 512 centos /bin/bash
[root@xianchaomaster1 ~]# docker run -itd --name docker20 --cpuset-cpus 0,1 --cpu-shares 1024 centos /bin/bash
- 指定 docker10 只能在 cpu0 和 cpu1 上运行,而且 docker10 的使用 cpu 的份额 512
- 参数-itd 就是又能打开一个伪终端,又可以在后台运行着 docker 实例
- 指定 docker20 只能在 cpu0 和 cpu1 上运行,而且 docker20 的使用 cpu 的份额 1024,比 dcker10 多一倍
测试 1: 进入 docker10,使用 stress 测试进程是不是只在 cpu0,1 上运行:
[root@xianchaomaster1 ~]# docker exec -it docker10 /bin/bash
[root@d1a431815090 /]# yum install -y epel-release
[root@d1a431815090 /]# yum install stress -y
[root@d1a431815090 /]# stress -c 2 -v -t 10m
- 运行 2 个进程,把两个 cpu 占满
- '在物理机另外一个虚拟终端上运行 top 命令,按 1 快捷键,查看每个 cpu 使用情况'
测试 2: 然后进入 docker20,使用 stress 测试进程是不是只在 cpu0,1 上运行,且 docker20 上运行的 stress 使用 cpu 百分比是 docker10 的 2 倍
[root@xianchaomaster1 ~]# docker exec -it docker20 /bin/bash
[root@d1a431815090 /]# yum install -y epel-release
[root@d1a431815090 /]# yum install stress -y
[root@f24e75bca5c0 /]# stress -c 2 -v -t 10m
- '在物理机另外一个虚拟终端上运行 top 命令,按 1 快捷键,查看每个 cpu 使用情况'
# 注:两个容器只在 cpu0,1 上运行,说明 cpu 绑定限制成功。而 docker20 是 docker10 使用 cpu 的 2倍。说明--cpu-shares 限制资源成功。
4.1.2、内存
Docker 提供参数-m, --memory=""限制容器的内存使用量。
例 1:允许容器使用的内存上限为 128M:
[root@xianchaomaster1 ~]# docker run -it -m 128m centos
查看:
[root@40bf29765691 /]# cat /sys/fs/cgroup/memory/memory.limit_in_bytes
134217728
注:也可以使用 tress 进行测试,到现在,我可以限制 docker 实例使用 cpu 的核心数和权重,可以限制内存大小。
例 2:创建一个 docker,只使用 2 个 cpu 核心,只能使用 128M 内存
[root@xianchaomaster1 ~]# docker run -it --cpuset-cpus 0,1 -m 128m centos
4.1.3、磁盘IO
[root@xianchaomaster1 ~]# docker run --help | grep write-b
--device-write-bps value 限制此设备上的写速度(bytes per second),单位可以是 kb、mb 或者 gb。
--device-read-bps value 限制此设备上的读速度(bytes per second),单位可以是 kb、mb 或者 gb。
情景:防止某个 Docker 容器吃光你的磁盘 I / O 资源
例 1:限制容器实例对硬盘的最高写入速度设定为 2MB/s。
--device 参数:将主机设备添加到容器
[root@xianchaomaster1 ~]# mkdir -p /var/www/html/
[root@xianchaomaster1 ~]# docker run -it -v /var/www/html/:/var/www/html --device /dev/sda:/dev/sda --device-write-bps /dev/sda:2mb centos /bin/bash
[root@bd79042dbdc9 /]# time dd if=/dev/sda of=/var/www/html/test.out bs=2M count=50 oflag=direct,nonblock
# dd 参数:
direct:读写数据采用直接 IO 方式,不走缓存。直接从内存写硬盘上。
nonblock:读写数据采用非阻塞 IO 方式,优先写 dd 命令的数据
50+0 records in
50+0 records out
52428800 bytes (52 MB) copied, 50.1831 s, 2.0 MB/s
real 0m50.201s
user 0m0.001s
sys 0m0.303s
注: 发现 1 秒写 2M。 限制成功。
4.2、私有镜像仓库harbor
4.2.1、为Harbor签发证书
# 服务器改名
hostnamectl set-hostname harbor && bash
# 安装openssl
yum -y install openssl
# 创建证书目录
mkdir -p /data/ssl
cd /data/ssl
# 生成ca证书
1.生成3072位私钥
openssl genrsa -out ca.key 3072
2.生成数字证书ca.pem
openssl req -new -x509 -days 3650 -key ca.key -out ca.pem
[root@harbor ssl]# openssl req -new -x509 -days 3650 -key ca.key -out ca.pem
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [XX]:CH
State or Province Name (full name) []:XA
Locality Name (eg, city) [Default City]:XA
Organization Name (eg, company) [Default Company Ltd]:
Organizational Unit Name (eg, section) []:
Common Name (eg, your name or your server's hostname) []:
Email Address []:
# 生成域名证书
1.生成3072位的私钥
openssl genrsa -out harbor.key 3072
2.生成数字证书
openssl req -new -key harbor.key -out harbor.csr
[root@harbor ssl]# openssl req -new -key harbor.key -out harbor.csr
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [XX]:CH
State or Province Name (full name) []:XA
Locality Name (eg, city) [Default City]:XA
Organization Name (eg, company) [Default Company Ltd]:
Organizational Unit Name (eg, section) []:
Common Name (eg, your name or your server's hostname) []:harbor
Email Address []:
Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:
An optional company name []:
# 签发证书
openssl x509 -req -in harbor.csr -CA ca.pem -CAkey ca.key -CAcreateserial -out harbor.pem -days 3650
4.2.2、安装docker
# 关闭防火墙
systemctl disable firewalld --now
# 关闭 iptables 防火墙
# 安装 iptables
yum install iptables-services -y
# 禁用 iptables
service iptables stop && systemctl disable iptables
# 清空防火墙规则
iptables -F
# 关闭 selinux
setenforce 0
sed -i 's/SELINUX=enforcing/SELINUX=disabled/g' /etc/selinux/config
# 注意:修改 selinux 配置文件之后,重启机器,selinux 才能永久生效
getenforce
# 显示 Disabled 表示 selinux 关闭成功
# 配置时间同步
yum install -y ntp ntpdate
ntpdate cn.pool.ntp.org
cat > /var/spool/cron/ntpdate << EOF
* */1 * * * /usr/sbin/ntpdate cn.pool.ntp.org
EOF
crontab -u root /var/spool/cron/ntpdate
systemctl restart crond
# 安装基础软件
yum install -y wget net-tools nfs-utils lrzsz gcc gcc-c++ make cmake libxml2-devel openssl-devel curl curl-devel unzip sudo ntp libaio-devel wget vim ncurses•devel autoconf automake zlib-devel python-devel epel-release openssh-server socat ipvsadm conntrack yum-utils
# 安装docker-ce
yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
yum install -y yum-utils device-mapper-persistent-data lvm2
yum install docker-ce -y
# 启动dockers服务
systemctl enable docker --now
# 内核参数修改:br_netfilter 模块用于将桥接流量转发至 iptables 链,br_netfilter 内核参数需要开启转发。
modprobe br_netfilter
cat > /etc/sysctl.d/docker.conf << END
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1
END
# 使参数生效
sysctl -p /etc/sysctl.d/docker.conf
# 重启后模块失效,下面是开机自动加载模块的脚本
cat > /etc/rc.sysinit << END
#!/bin/bash
for file in /etc/sysconfig/modules/*.modules ; do
[ -x $file ] && $file
done
END
# 在/etc/sysconfig/modules/目录下新建文件如下
cat > /etc/sysconfig/modules/br_netfilter.modules << END
modprobe br_netfilter
END
# 增加权限
chmod 755 /etc/sysconfig/modules/br_netfilter.modules
# 重启机器模块也会自动加载
lsmod | grep br_netfilter
# 注: Docker 安装后出现:WARNING: bridge-nf-call-iptables is disabled 的解决办法:
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1:
将 Linux 系统作为路由或者 VPN 服务就必须要开启 IP 转发功能。当 linux 主机有多个网卡时一个网卡收到的信息是否能够传递给其他的网卡 ,如果设置成 1 的话 可以进行数据包转发,可以实现 VxLAN 等功能。不开启会导致 docker 部署应用无法访问。
# 重启 docker
systemctl restart docker
4.2.3、安装harbor
# 创建安装目录
mkdir /data/install -p
cd /data/install/
将'harbor-offline-installer-v2.3.0-rc3.tgz'、'docker-harbor-2-3-0.tar.gz'、'docker-compose-Linux-x86_64.64'文件上传到该目录下
# /data/ssl 目录下有如下文件:
ca.key ca.pem ca.srl harbor.csr harbor.key harbor.pem
# 下载 harbor 离线包的地址:
https://github.com/goharbor/harbor/releases/tag/
# 解压harbor-offline,并修改配置文件
tar zxvf harbor-offline-installer-v2.3.0-rc3.tgz
cd harbor
cp harbor.yml.tmpl harbor.yml
vim harbor.yml
hostname: harbor
#修改 hostname,跟上面签发的证书域名保持一致
certificate: /data/ssl/harbor.pem
private_key: /data/ssl/harbor.key
# 注:harbor 默认的账号密码:admin/Harbor12345
# 安装docker-compose
cd /data/install
mv docker-compose-Linux-x86_64.64 /usr/bin/docker-compose
chmod +x /usr/bin/docker-compose
# 注: docker-compose 项目是 Docker 官方的开源项目,负责实现对 Docker 容器集群的快速编排。Docker-Compose 的工程配置文件默认为 docker-compose.yml,Docker-Compose 运行目录下的必要有一个docker-compose.yml。docker-compose 可以管理多个 docker 实例。
# 加载容器并安装
docker load -i docker-harbor-2-3-0.tar.gz
cd harbor
./install.sh
4.2.4、访问harbor
# 修改hosts文件
在'C:\Windows\System32\drivers\etc\hosts'文件中添加如下内容,即可在浏览器中访问'https://harbor'或'http://IP'
192.168.68.133(harborIP) harbor
# harbor服务启停
1.停止 harbor:
[root@harbor harbor]# cd /data/install/harbor
[root@harbor harbor]# docker-compose stop
2.启动 harbor:
[root@harbor harbor]# cd /data/install/harbor
[root@harbor harbor]# docker-compose start
4.2.5、使用harbor
# 修改docker配置
cat > /etc/docker/daemon.json << 'EOF'
{
"registry-mirrors": ["https://rsbud4vc.mirror.aliyuncs.com","https://registry.dockecn.com","https://docker.mirrors.ustc.edu.cn","https://dockerhub.azk8s.cn","http://humirror.c.163.com"],"insecure-registries": ["192.168.68.134","harbor"]
}
EOF
systemctl daemon-reload && systemctl restart docker
systemctl status docker
显示如下,说明启动成功:
Active: active (running) since Fri … ago
注意:
配置新增加了一行内容如下:
"insecure-registries":["192.168.68.134"]
上面增加的内容表示我们内网访问 harbor 的时候走的是 http,192.168.40.181 是安装 harbor 机器的 ip
# 登录harbor
docker login 192.168.68.134
Username:admin
Password: Harbor12345
# 上传镜像到harbor仓库:先打标签,再上传
docker tag nginx:v1 192.168.68.134/test/nginx:v1
docker push 192.168.68.134/test/nginx:v1
# 拉取镜像
docker pull 192.168.68.134/test/nginx:v1
4.3、FAQ-dockerharbor
4.3.1、docker login 报错 x509
- Error response from daemon: Get "https://gocd.lab.home/v2/": x509: certificate relies on legacy Common Name field, use SANs instead
# 编辑/etc/docker/daemon.json,将无法 login 的网址添加到 insecure-registries 即可
[root@gitlab gitlab]# vim /etc/docker/daemon.json
{
"registry-mirrors":["https://rsbud4vc.mirror.aliyuncs.com","https://registry.docker-cn.com","https://docker.mirrors.ustc.edu.cn","https://dockerhub.azk8s.cn","http://hub-mirror.c.163.com","ht
tp://qtid6917.mirror.aliyuncs.com", "https://rncxm540.mirror.aliyuncs.com","https://gocd.lab.home"],
"insecure-registries": ["https://gocd.lab.home"],
"exec-opts": ["native.cgroupdriver=systemd"]
}
# 编辑完成后需重启docker
[root@gitlab gitlab]# systemctl restart docker
# 再次进行 login 即可成功
[root@gitlab gitlab]# docker login gocd.lab.home
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
- 忘记密码
#1、进入[harbor-db]容器内部
docker exec -it harbor-db /bin/bash
#2、进入postgresql命令行,
psql -h postgresql -d postgres -U postgres #这要输入默认密码:root123 。
psql -U postgres -d postgres -h 127.0.0.1 -p 5432 #或者用这个可以不输入密码。
#3、切换到harbor所在的数据库
\c registry
#4、查看harbor_user表
select * from harbor_user;
#5、例如修改admin的密码,修改为初始化密码Harbor12345 ,修改好了之后再可以从web ui上再改一次。
update harbor_user set password='a71a7d0df981a61cbb53a97ed8d78f3e', salt='ah3fdh5b7yxepalg9z45bu8zb36sszmr' where username='admin';
#6、退出 \q 退出postgresql,exit退出容器。
\q
exit
完成后通过WEB UI,就可以使用admin\Harbor12345 这个密码登录了,记得修改这个默认密码哦,避免安全问题。
#方法二: 重置后为自己配置文件里设置的默认密码
1,进入[harbor-db]容器内部
docker exec -it harbor-db /bin/bash
2,进入postgresql命令行
psql -h postgresql -d postgres -U postgres
#这要输入默认密码:root123 。
3,切换到harbor所在的数据库
\c registry
4,查看harbor_user表
select * from harbor_user;
5,重置admin密码
update harbor_user set salt='', password='' where username='admin';
重新启动Harbor私有镜像仓库后,密码就会自动重置为之前安装时配置的Harbor12345
\q
exit
6,重新启动Harbor私有镜像仓库
# docker-compose down
#./prepare
# docker-compose up -d
# 方法三:查看Harbor设置的密码
docker exec -it harbor-core bash
printenv |grep PASSWORD
4.3.2、docker login 报错404
# 现象
[root@master1 istio]# docker login harbor.lab.home -u admin -p Harbor12345
WARNING! Using --password via the CLI is insecure. Use --password-stdin.
Error response from daemon: Get "https://harbor.lab.home:443/v2/": error parsing HTTP 404 response body: invalid character '<' looking for beginning of value: "\n<html>\n<head>\n <meta charset=\"utf-8\">\n <meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge,chrome=1\">\n <title>404 Not Found</title>\n <meta name=\"viewport\" content=\"width=device-width\">\n <style>\n .error-page-wrap {\n width: 400px;\n height: 400px;\n border-radius: 50%;\n background: #94399E;\n position: absolute;\n transform: translate(-50%, -50%);\n left: 50%;\n top: 50%;\n text-align: Center;\n display: flex;\n flex-direction: column;\n justify-content: center;\n }\n .error-page-wrap h1 {\n font-size: 100px;\n margin: 0;\n color: #fff;\n }\n .error-page-wrap h2 {\n margin: 0;\n color: #fff;\n margin: 20px 0;\n }\n .error-page-wrap a {\n color: #fff;\n display: block;\n }\n\n </style>\n</head>\n<body>\n<div class=\"error-page-wrap\">\n <h1>404</h1>\n <h2>Not Found</h2>\n</div>\n</body>\n</html>\n"
# 原因
更换了harobr的域名,但是harbor的配置未修改,导致报错
# 解决方法
vim /opt/harbor/common/config/core/env
EXT_ENDPOINT=http://harbor.lab.home
docker-compose down
docker-compose up -d
五、docker权限
docker默认开启的Linux功能权限列表
Capability Key | Capability Description |
AUDIT_WRITE | Write records to kernel auditing log. |
CHOWN | Make arbitrary changes to file UIDs and GIDs (see chown(2)). |
DAC_OVERRIDE | Bypass file read, write, and execute permission checks. |
FOWNER | Bypass permission checks on operations that normally require the file system UID of the process to match the UID of the file. |
FSETID | Don’t clear set-user-ID and set-group-ID permission bits when a file is modified. |
KILL | Bypass permission checks for sending signals. |
MKNOD | Create special files using mknod(2). |
NET_BIND_SERVICE | Bind a socket to internet domain privileged ports (port numbers less than 1024). |
NET_RAW | Use RAW and PACKET sockets. |
SETFCAP | Set file capabilities. |
SETGID | Make arbitrary manipulations of process GIDs and supplementary GID list. |
SETPCAP | Modify process capabilities. |
SETUID | Make arbitrary manipulations of process UIDs. |
SYS_CHROOT | Use chroot(2), change root directory. |
1、SKIP_NON_ROOT
SKIP_NON_ROOT=true
# 该环境变量设置为true后,将在容器中使用root用户执行所有命令
root@pve1:/etc/pve/virtual-guest# pwd /etc/pve/virtual-guest
root@pve1:/etc/pve/virtual-guest# cat cpu-models.conf
cpu-model: avx
flags +avx;+avx2;+ssse3;+sse4_1;+sse4_2
phys-bits host
hidden 0
hv-vendor-id proxmox
reported-model kvm64
这里的flags就是指令集,其中+是支持,-是去掉支持 记住!指令集的支持与否与物理机密切相关!先查看本机的指令集在做决定 cat /proc/cpuinfo|grep "xxxxx"
六、清理空间
# 查看docker 占用的存储空间: docker system df
# 该命令主要用来 删除停止的容器、无用的数据卷、网络和无tag的镜像:docker system prune