一、什么是Docker
Docker 相比虚拟机的交付速度更快,资源消耗更低,Docker 采用客户端/服务端架构,使用远程API来管理和创建容器,其可以轻松的创建一个轻量级的、可移植的、自给自足的容器,docker 的三大理念是build(构建)、ship(运输)、 run(运行),Docker遵从apache 2.0协议,并通过(namespace及cgroup等)来提供容器的资源隔离与安全保障等,所以Docke容器在运行时不需要类似虚拟机(空运行的虚拟机占用物理机6-8%性能)的额外资源开销,因此可以大幅提高资源利用率,总而言之Docker是一种用了新颖方式实现的轻量级虚拟机.类似于VM但是在原理和应用上和VM的差别还是很大的,并且docker的专业叫法是应用容器(Application Container)。
二、Docker的组成
- Docker 主机(Host): 一个物理机或虚拟机,用于运行Docker服务进程和容器,也称为宿主机,node节点
- Docker 服务端(Server/daemon): Docker守护进程,运行docker容器
- Docker 客户端(Client): 客户端使用 docker 命令或其他工具调用docker API
- Docker 镜像(Images): 镜像可以理解为创建实例使用的模板,本质上就是一些程序文件的集合
- Docker 仓库(Registry): 保存镜像的仓库,官方仓库: https://hub.docker.com/,可以搭建私有仓库harbor
- Docker 容器(Container): 容器是从镜像生成对外提供服务的一个或一组服务,其本质就是将镜像中的程序启动后生成的进程
三、Namespace
Namespace(命名空间)是一种容器化技术中的概念,它允许不同容器或者容器中的进程共享一个 Linux 操作系统内核,同时隔离各自的资源与环境,让每个容器感觉自己在运行一个独立的操作系统。这样每个容器都有自己的命名空间,它们之间相互独立,互不影响。
1.命名空间的作用
隔离性:
通过命名空间,不同容器的进程可以共存于同一个 Linux 内核上,却不会相互干扰。每一个容器都有自己独立的文件系统、网络、进程树等,就像运行在独立的机器上一样。
资源管理:
通过命名空间,容器可以限制资源的使用,如 CPU、内存等。这样可以避免容器之间的资源争抢,同时也可以避免单个容器的错误或恶意行为影响到其他容器或宿主机的稳定运行。
部署维护:
由于命名空间提供了良好的隔离性,容器间的部署和维护可以更加简单和快速。
2.命名空间类型
隔离类型 | 功能 | 系统调用参数 | 内核版本 |
---|---|---|---|
MNT Namespace(mount) | 提供磁盘挂载点和文件系统的隔离能力 | CLONE_NEWNS | 2.4.19 |
IPC Namespace(Inter-Process Communication) | 提供进程间通信的隔离能力,包括信号量,消息队列和共享内存 | CLONE_NEWIPC | 2.6.19 |
UTS Namespace(UNIXTimesharing System) | 提供内核,主机名和域名隔离能力 | CLONE_NEWUTS | 2.6.19 |
PID Namespace(ProcessIdentification) | 提供进程隔离能力 | CLONE_NEWPID | 2.6.24 |
Net Namespace(network) | 提供网络隔离能力,包括网络设备,网络栈,端口等 | CLONE_NEWNET | 2.6.29 |
User Namespace(user) | 提供用户隔离能力,包括用户和组 | CLONE_NEWUSER | 3.8 |
TimeNamespace | 提供时间隔离能力 | CLONE_NEWTIME | 5.6 |
syslogNamespace | 提供syslog隔离能力 | syslognamespace是由华为工程师RuiXiang(瑞翔)提出的,但没有合并到linux内核中,后systemd在2020年2在2020年2 月实现了一个名为“journalnamespace”的类似功能 | |
Controlgroup(cgroup)Namespace | 提供进程所属的控制组的身份隔离 | Linux4.6 |
四、安装docker
yum install -y yum-utils device-mapper-persistent-data lvm2
yum install container-selinux slirp4netns fuse-overlayfs
yum-config-manager --add-repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
sed -i 's+download.docker.com+mirrors.aliyun.com/docker-ce+' /etc/yum.repos.d/docker-ce.repo
yum makecache fast
yum -y install docker-ce
systemctl start docker
镜像仓库加速
#镜像加速下载
浏览器访问 https://cr.console.aliyun.com/cn-hangzhou/instances/mirrors 获取镜像加速器配置
mkdir -p /etc/docker
tee /etc/docker/daemon.json <<-'EOF'
{
"registry-mirrors": ["https://oa8ljndt.mirror.aliyuncs.com"]
}
EOF
systemctl daemon-reload
systemctl restart docker
五、Control groups
Cgroups 最主要的作用,就是限制一个进程组能够使用的资源上限,包括CPU、内存、磁盘、网络带宽等等。此外,还能够对进程进行优先级设置,资源的计量以及资源的控制(比如:将进程挂起和恢复等操作)
六、docker命令
1.镜像命令
2.容器命令
docker run
七、镜像制作和管理
1.将现有容器通过docker commit手动构建镜像
docker commit 格式
docker commit [OPTIONS] CONTAINER [REPOSITORY[:TAG]]
常用选项:
-a, --author
说明:指定镜像的作者信息。
示例:docker commit -a “John Doe john.doe@example.com” my_container my_image:latest
用途:用于记录镜像的创建者信息。
-m, --message
说明:提供镜像提交时的说明信息。
示例:docker commit -m “Added new features” my_container my_image:latest
用途:记录提交的描述信息,帮助跟踪镜像的更改记录。
–change
说明:对镜像的 Dockerfile 指令进行更改,例如 CMD, ENTRYPOINT, ENV 等。
示例:docker commit --change='CMD ["new_command"]' my_container my_image:latest
用途:修改镜像的默认行为或配置。
实战案例:基于 busybox 制作httpd镜像
docker run -it --name cc busybox
mkdir -p /data/html
echo "cc" > /data/html/index.html
exit
#用busybox镜像创建一个名为cc的容器
docker commit -a "chen" -c 'CMD /bin/httpd -fv -h /data/html' -c "EXPOSE 80" cc httpd-busybox:v1
这条命令的含义:
从名为 cc 的容器中创建一个新的 Docker 镜像。
将镜像的作者设置为 "chen"。
将镜像的默认启动命令设置为 /bin/httpd -fv -h /data/html,这意味着容器启动时会运行 httpd 服务器,并以前台模式启动,输出详细日志,并将根目录设置为 /data/html。
将镜像的 EXPOSE 指令设置为 80 端口,表明镜像会监听 80 端口。
将新镜像命名为 httpd-busybox:v1
docker run -d --name web1 -P httpd-busybox:v1
docker port web1
#80/tcp -> 0.0.0.0:32768
#80/tcp -> [::]:32768
curl 192.168.10.101:32768
2.利用DockerFile文件执行docker build自动构建镜像
Dockerfile 文件说明
-
每一行以Dockerfile的指令开头,指令不区分大小写,但是惯例使用大写
-
使用 # 开始作为注释
-
每一行只支持一条指令,每条指令可以携带多个参数
-
指令按文件的顺序从上至下进行执行
-
每个指令的执行会生成一个新的镜像层,为了减少分层和镜像大小,尽可能将多条指令合并成一条指令
-
制作镜像一般可能需要反复多次,每次执行dockfile都按顺序执行,从头开始,已经执行过的指令已经缓存,不需要再执行,如果后续有一行新的指令没执行过,其往后的指令将会重新执行,所以为加速镜像制作,将最常变化的内容放下dockerfile的文件的后面
Dockerfile 相关指令
-
ADD:将文件或目录从构建上下文中复制到镜像的文件系统中,支持解压 tar 文件和从 URL 下载文件。
-
COPY:将文件或目录从构建上下文中复制到镜像的文件系统中,功能类似于 ADD,但不支持从 URL 下载或解压。
-
ENV:设置环境变量,这些变量可以在 Docker 镜像运行时使用。
-
EXPOSE:声明容器在运行时会监听的网络端口,但不会自动映射到宿主机的端口,需要通过 docker run 命令的 -p 选项进行映射。
-
FROM:指定基础镜像,用于构建当前镜像。每个 Dockerfile 必须以 FROM 开始,表示从哪个镜像继承。
-
LABEL:为镜像添加元数据,例如维护者信息、版本号等。
-
STOPSIGNAL:设置 Docker 停止容器时发送的信号,默认为 SIGTERM。
-
USER:指定运行容器时使用的用户或用户组。
-
VOLUME:创建一个挂载点,在容器和宿主机之间共享数据。
FROM ubuntu
LABEL maintainer="zhou"
VOLUME [ "/data1","/data2" ]
#给容器创建两个文件夹挂载到真机上
docker inspect 7d |grep volume -A 10 -i
#可以找到挂载到的真机的位置
- WORKDIR:设置工作目录,之后的指令都会在这个目录下执行。如果目录不存在,Docker 会自动创建。
#两次RUN独立运行,不在同一个目录,
RUN cd /app
RUN echo "hello" > world.txt
#如果想实现相同目录可以使用WORKDIR
WORKDIR /app
RUN echo "hello" > world.txt
-
RUN:在镜像构建过程中执行指定的命令,用于安装软件包、运行脚本等操作。
-
CMD:指定容器启动时默认执行的命令或可执行文件。CMD 指令可以被 docker run 命令提供的参数覆盖。
-
ENTRYPOINT:设置容器启动时的主命令,并且无法被 docker run 命令中的参数覆盖。ENTRYPOINT 与 CMD 可以结合使用,CMD 中的内容会作为参数传递给 ENTRYPOINT 指令指定的命令。
Docker Run、CMD和ENTRYPOINT之间的关系
ENTRYPOINT 定义了容器启动时的主命令,始终会被执行。
CMD 提供了 ENTRYPOINT 的默认参数。如果指定了 CMD,这些默认参数会传递给 ENTRYPOINT。
docker run 命令提供的参数会覆盖 CMD 的默认参数,但不会改变 ENTRYPOINT 的命令。因此,docker run 中的参数追加到 ENTRYPOINT 命令中,而 CMD 的值仅在 docker run 没有提供参数时才生效。
实际例子
mkdir /data/dockerfile/system/centos/centos7 -p
cd /data/dockerfile/system/centos/centos7/
vim Dockerfile
FROM centos:7.9.2009
LABEL author="zhou cloud" \
version="1.0" \
description="test"
RUN rm -rf /etc/yum.repos.d/*
RUN mkdir /app && cd /app
RUN echo "hello" > test.txt
ENV version="1.0" user=mysql\
name=zhou
RUN touch $name.txt
docker build -t centos7.9:v1.0 .
docker run -it --name c1 centos7.9:v1.0 bash
docker history centos7.9:v1.0
构建镜docker build 命令
docker build选项
-t, --tag
为构建的镜像指定标签(名称和可选版本号)。
docker build -t my_image:latest .
-f, --file
指定 Dockerfile 的路径。
docker build -f /path/to/Dockerfile .
- -build-arg
传递构建时的参数,这些参数在 Dockerfile 中使用 ARG 指令引用。
docker build --build-arg MY_VAR=value .
- -no-cache
构建镜像时不使用缓存。
docker build --no-cache .
–pull
强制从远程仓库拉取最新的基础镜像。
docker build --pull .
-q, --quiet
只输出镜像 ID,不显示详细的构建日志。
docker build -q .
–rm
在构建完成后移除临时中间容器。默认启用。
docker build --rm=false .
–target
指定多阶段构建中的构建目标(阶段)。
docker build --target intermediate-stage .
–squash
将所有中间层合并成一个层,减少镜像的层数(需启用实验功能)。
docker build --squash .
–label
为构建的镜像添加标签。
docker build --label key=value .
八、docker 网络管理
Docker 的网络模式:
- Host:容器将不会虚拟出自己的网卡,配置自己的IP等,而是使用宿主机的IP和端口。
- Container:创建的容器不会创建自己的网卡,配置自己的IP,而是和一个指定的容器共享IP、端口范围
- None:该模式关闭了容器的网络功能。
- Bridge:默认为该模式,此模式会为每一个容器分配、设置IP等,并将容器连接到一个docker0虚拟网桥,通过docker0网桥以及iptables nat 表配置与宿主机通信。
- 自定义网络
建立容器时选择相应的网络模式
使用docker run创建Docker容器时,可以用 --net 或 --network 选项指定容器的网络模式
- host模式:使用 --net=host 指定。
- none模式:使用 --net=none 指定
- container模式:使用 --net=container:NAME_or_ID 指定
- bridge模式:使用 --net=bridge 指定,默认设置,可省略
docker网络管理题目
1、创建容器nginx1,网络模式为host,可以通过宿主机的ip+端口,访问nginx的服务
docker run -d --network host --name nginx1 nginx
2、创建自定义网络,mynetwork,网段为192.18.0.0/16.
docker network create --driver bridge --subnet 192.18.0.0/16 mynetwork
3、创建容器nginx2,使用mynetwork,指定ip地址为192.18.0.10为ip地址,端口映射为3080:80,实现
内外网访问。
docker run -d --name nginx2 --network mynetwork --ip 192.18.0.10 -p 3080:80 nginx
4、创建nginx3和centos1容器,centos1可以在容器内部访问nginx3的页面
docker run -d --network mynetwork --name nginx3 -p 3309:80 nginx
docker run -it --network host --name centos1 centos7:v1 sh