Docker基础

1、云原生

1.1、什么是云原生

云原生(CloudNative)指的是基于在云中构建、运行应用程序的理念,而打造的一套技术体系。不同于传统数据中心的软件开发、构建模式,云原生包含有“原生为云而设计”的含义,能够有效提升云上资源利用率、缩短开发周期

1.2、云原生架构

从技术的角度出发,云原生架构是基于云原生技术的一组架构原则和设计模式的集合,旨在帮助企业和开发人员充分利用云平台所提供的平台化能力和弹性资源能力
Docker基础_第1张图片
简单说就是业务代码和基础平台分割,进行指责划分。打造Paas(平台即服务)、技术产品化思维

1.3、虚拟技术发展

Docker基础_第2张图片
传统部署时代: 在物理服务器上运行应用程序

  • 应用程序无法定义资源边界,这会导致资源分配问题
  • 解决资源竞争,不同服务器上运行不同程序。维护成本、服务器成本提升

虚拟化部署时代:为了资源隔离问题,引入了虚拟化

  • 虚拟化很好地利用服务器资源,可伸缩性,轻松地管理应用程序,降低硬件成本等
  • 每个VM都是一台完整的计算机,包括其自己的操作系统
  • 主流虚拟技术 :
    Docker基础_第3张图片

容器部署时代:容器类似于VM,但是它们具有轻松的隔离属性

  • 容器被认为是轻质的。与VM相似,容器具有自己的文件系统,CPU,内存,进程空间等
  • 可以在应用程序之间共享操作系统
  • 主流容器技术 :
    Docker基础_第4张图片

2、Docker什么?

Docker基础_第5张图片
Docker是一个用于开发,交付和运行应用程序的开放平台
Docker是基于Go语言实现的开源容器项目。它诞生于2013年初,最初发起者是dotCloud公司,在2013年年底直接改名为Docker Inc。并专注于Docker相关技术和产品的开发,目前已经成为全球最大的Docker容器服务提供商。官方网站为docker.com

Docker的构想是要实现"Build, Ship and Run Any App, Anywhere",即通过对应用的封装(Packaging)、分发(Distribution)、部署(Deployment)、运行(Runtime)生命周期进行管理,达到应用组件级别的一次构建(封装),到处运行

3、Docker架构

Docker使用客户端-服务器架构。Docker客户端与Docker守护进程对话,后者负责构建、运行和分发Docker容器的繁重工作。Docker 客户端和守护程序可以运行在同一系统上,或者您可以将Docker客户端连接到远程Docker守护程序。Docker客户端和守护进程使用REST API、UNIX 套接字或网络接口进行通信。另一个Docker客户端是Docker Compose,它允许您使用由一组容器组成的应用程序
Docker基础_第6张图片

Docker架构升级

Docker首次发布时,Docker引擎由两个核心组件构成:LXC(Linux Container)和Docker daemon
Docker daemon是单一的二进制文件,包含诸如Docker客户端、Docker API、容器运行时、镜像构建等
LXC提供了对诸如命名空间(Namespace)和控制组(CGroup等基础工具的操作能力,它们是基于Linux内核的容器虚拟化技术Linux Container容器是一种内核虚拟化技术,可以提供轻量级的虚拟化,以便隔离进程和资源
Docker基础_第7张图片

首先,LXC是基于Linux的。这对于一个立志于跨平台的项目来说是个问题,其次,如此核心的组件依赖于外部工具,这会给项目带来巨大风险,甚至影响其发展

因此,Docker公司开发了名为Libcontainer的自研工具,用于替代LXC。Libcontainer的目标是成为与平台无关的工具,可基于不同内核为Docker上层提供必要的容器交互功能。在Docker 0.9版本中,Libcontainer取代LXC成为默认的执行驱动

OCI:当Docker公司正在进行Docker daemon进程的拆解和重构的时候,OCI也正在着手定义两个容器相关的规范(或者说标准)。比如:镜像规范和容器运行时规范。两个规范均于2017年7月发布了1.0版

所有的容器运行代码在一个单独的OCI兼容层中实现。默认情况下,Docker使用runc来实现这一点。runc是OCI容器运行时标准的参考实现

Runc : runc是OCI容器运行时规范的参考实现。Docker公司参与了规范的制定以及runc的开发。去粗取精,会发现runc实质上是一个轻量级的、针对Libcontainer进行了包装的命令行交互工具(Libcontainer取代了早期Docker架构中的LXC)。

containerd在Linux和Windows中以daemon的方式运行,从1.11版本之后Docker就开始在Linux上使用它。Docker引擎技术栈中,containerd位于daemon和runc所在的OCI层之间。Kubernetes也可以通过cri-containerd使用containerd。containerd是由Docker公司开发的,并捐献给了云原生计算基金会(CloudNative Computing Foundation, CNCF)

Docker整体架构

[root@node1 ~]# docker images
REPOSITORY     TAG            IMAGE ID       CREATED         SIZE
nginx          v1             a80567189207   2 days ago      141MB
bjbfd/nginx    latest         605c77e624dd   17 months ago   141MB
bjbfd/nginx    v1             605c77e624dd   17 months ago   141MB
nginx          latest         605c77e624dd   17 months ago   141MB
wordpress      latest         c3c92cc3dcb1   17 months ago   616MB
mariadb        10.6.4-focal   12e05d5da3c5   19 months ago   409MB
bjbfd/stress   latest         89e5b79daa74   7 years ago     215MB
[root@node1 ~]# docker run -itd nginx:latest
2d95b4eee9cd96a5e47b132e884eb0f4697db593d4275f2324e6b0224e38314b
[root@node1 ~]# docker run -itd bjbfd/nginx:v1
ae04ef37f2c1367117fdf4ac7e6f7167103b18a617c0f3b5b06a88c5c3bb6a84
[root@node1 ~]# docker ps -a
CONTAINER ID   IMAGE            COMMAND                   CREATED          STATUS          PORTS     NAMES
ae04ef37f2c1   bjbfd/nginx:v1   "/docker-entrypoint.…"   2 seconds ago    Up 1 second     80/tcp    interesting_gates
2d95b4eee9cd   nginx:latest     "/docker-entrypoint.…"   13 seconds ago   Up 13 seconds   80/tcp    funny_bartik

以上启动了两个nginx容器,看一下Linux中的进程

[root@node1 ~]# ps -ef | grep container
root      1262     1  0 09:00 ?        00:00:00 /usr/bin/containerd
root      1271     1  0 09:00 ?        00:00:00 /usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock
root      1629  1209  0 09:02 pts/1    00:00:00 grep --color=auto container
[root@node1 ~]# ps -ef | grep container
root      1262     1  0 09:00 ?        00:00:00 /usr/bin/containerd
root      1271     1  0 09:00 ?        00:00:00 /usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock
root      1676     1  0 09:02 ?        00:00:00 /usr/bin/containerd-shim-runc-v2 -namespace moby -id 2d95b4eee9cd96a5e47b132e884eb0f4697db593d4275f2324e6b0224e38314b -address /run/containerd/containerd.sock
root      1768     1  0 09:03 ?        00:00:00 /usr/bin/containerd-shim-runc-v2 -namespace moby -id ae04ef37f2c1367117fdf4ac7e6f7167103b18a617c0f3b5b06a88c5c3bb6a84 -address /run/containerd/containerd.sock
root      1853  1209  0 09:03 pts/1    00:00:00 grep --color=auto container

Docker基础_第8张图片
Docker通过DockerDaemon的管理,libcontainer的执行,最终创建Docker容器

模块解说 :

模块 职责 进程
DockerClient 容器的管理客户端 Docker run......
DockerDaemon 服务端的能力,包括:Docker Server、Egine和Job。主负责接收Client请求,并通过Engine的Job完成任务执行,比如镜像下载等 Dockerd
DockerRegistry Docker注册服务器,主要负责仓库管理
Graph 容器镜像的保管者,包括下载、构建镜像以及镜像的分层存储管理 Dockerd
Driver Docker架构中的驱动模块,实现对Docker容器运行环境的定制,定制的维度主要有网络环境、存储方式以及容器的执行方式。实现包括graphdriver、networkdriver和execdriver Dockerd
Libcontainer Libcontainer是一套独立的容器管理解决方案。主要是与Linux内核特征的封装,包括 : namespaces、cgroups以及capabilities等 Containerd
DockerContainer Docker容器运行时,功能类似于传统意义上的虚拟机,具备资源受限、环境与外界隔离的特点。启动几个容器就有几个containerd-shim-runc containerd-shim-runc

Docker run时序图

Docker基础_第9张图片

4、Docker安装

1、卸载老的版本
sudo yum remove docker \
                  docker-client \
                  docker-client-latest \
                  docker-common \
                  docker-latest \
                  docker-latest-logrotate \
                  docker-logrotate \
                  docker-engine

2、设置仓库
sudo yum install -y yum-utils
sudo yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo

3、安装docker引擎
sudo yum install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin

注意 : 
1、老版本需要docker compose的单独安装,新版本docker集成了docker compose,不需要单独安装

2、如果是阿里云ECS云主机,中文乱码解决方式参考 : https://blog.csdn.net/qq_41661056/article/details/105730143

3、阿里云镜像加速器
阿里云 -> 页面搜索 -> 容器镜像服务 -> 镜像工具 -> 镜像加速器
sudo mkdir -p /etc/docker
sudo tee /etc/docker/daemon.json <<-'EOF'
{
  "registry-mirrors": ["https://xxx.com"]
}
EOF
sudo systemctl daemon-reload
sudo systemctl restart docker

5、Docker组件

5.1、镜像

Docker基础_第10张图片

  • 把Docker镜像理解为VM模板,VM模板就像停止运行的VM,而Docker镜像就像停止运行的容器
  • 镜像由多个层组成,每层叠加之后,从外部看来就如一个独立的对象
  • 镜像内部是一个精简的操作系统(OS),同时还包含应用运行所必须的文件和依赖包

5.2、镜像分层

Docker基础_第11张图片
Docker镜像由一些松耦合的只读镜像层组成。所有的Docker镜像都起始于一个基础镜像层,当进行修改或增加新的内容时,就会在当前镜像层之上,创建新的镜像层

示例 :

[root@node1 wordpress]# docker run -itd nginx
Unable to find image 'nginx:latest' locally
latest: Pulling from library/nginx
Digest: sha256:0d17b565c37bcbd895e9d92315a05c1c3c9a29f762b011a10c54a66cd53c9b31
Status: Downloaded newer image for nginx:latest
0131fa2a222628418fe7462dfadcb2ccec2c3a333a58b8f875d211a7ec4772e1
[root@node1 wordpress]# docker images
REPOSITORY     TAG            IMAGE ID       CREATED         SIZE
bjbfd/nginx    latest         605c77e624dd   17 months ago   141MB
nginx          latest         605c77e624dd   17 months ago   141MB
wordpress      latest         c3c92cc3dcb1   17 months ago   616MB
mariadb        10.6.4-focal   12e05d5da3c5   19 months ago   409MB
bjbfd/stress   latest         89e5b79daa74   7 years ago     215MB
[root@node1 wordpress]#
[root@node1 nginx]# cat Dockerfile
FROM nginx
RUN echo '这是一个本地构建的nginx镜像' > /usr/share/nginx/html/index.html

基于nginx基础镜像构建一个镜像
[root@node1 nginx]# docker build -t nginx:v1 .
[+] Building 0.1s (6/6) FINISHED
 => [internal] load build definition from Dockerfile                                                                                                                                                                                                                       0.0s
 => => transferring dockerfile: 133B                                                                                                                                                                                                                                       0.0s
 => [internal] load .dockerignore                                                                                                                                                                                                                                          0.0s
 => => transferring context: 2B                                                                                                                                                                                                                                            0.0s
 => [internal] load metadata for docker.io/library/nginx:latest                                                                                                                                                                                                            0.0s
 => [1/2] FROM docker.io/library/nginx                                                                                                                                                                                                                                     0.0s
 => CACHED [2/2] RUN echo '这是一个本地构建的nginx镜像' > /usr/share/nginx/html/index.html                                                                                                                                                                                            0.0s
 => exporting to image                                                                                                                                                                                                                                                     0.0s
 => => exporting layers                                                                                                                                                                                                                                                    0.0s
 => => writing image sha256:a805671892075472b21360ead42fb53a2ad798b0ab56bab450c52d428ce1441b                                                                                                                                                                               0.0s
 => => naming to docker.io/library/nginx:v1                                                                                                                                                                                                                                0.0s
[root@node1 nginx]#

[root@node1 nginx]# docker images
REPOSITORY     TAG            IMAGE ID       CREATED         SIZE
nginx          v1             a80567189207   2 days ago      141MB
bjbfd/nginx    latest         605c77e624dd   17 months ago   141MB
nginx          latest         605c77e624dd   17 months ago   141MB
wordpress      latest         c3c92cc3dcb1   17 months ago   616MB
mariadb        10.6.4-focal   12e05d5da3c5   19 months ago   409MB
bjbfd/stress   latest         89e5b79daa74   7 years ago     215MB
[root@node1 nginx]#

对比两个镜像的层
Docker基础_第12张图片

docker inspect nginx:latest
LowerDir 如下 :
/var/lib/docker/overlay2/b00f6bf28e2dc408c796f09ad94d3f28c64e0a28cbdd6964087e2b26228b2328/diff:
/var/lib/docker/overlay2/ca904171aa0883178d573b413ca24013e624e90395197a2e4914ebbae8388e7d/diff:
/var/lib/docker/overlay2/4885892662a64db663878aee6f36c32d8196195e47a20ff2e0680256e28c20ac/diff:
/var/lib/docker/overlay2/4eb0162b58d4f18bca9c0d48fb39f275dfbf92a59227dc380b7d36f614b45a4e/diff:
/var/lib/docker/overlay2/a8c3e0d43b8b27fd19a575c3051c9cea6450d39d8fbb58c3d34c7d8b898d3b97/diff

docker inspect nginx:v1
LowerDir 如下 :
/var/lib/docker/overlay2/9d155c02707c57771128e397e6e43c9c9691a544e8e5749b87da9ebc5857f554/diff:
/var/lib/docker/overlay2/b00f6bf28e2dc408c796f09ad94d3f28c64e0a28cbdd6964087e2b26228b2328/diff:
/var/lib/docker/overlay2/ca904171aa0883178d573b413ca24013e624e90395197a2e4914ebbae8388e7d/diff:
/var/lib/docker/overlay2/4885892662a64db663878aee6f36c32d8196195e47a20ff2e0680256e28c20ac/diff:
/var/lib/docker/overlay2/4eb0162b58d4f18bca9c0d48fb39f275dfbf92a59227dc380b7d36f614b45a4e/diff:
/var/lib/docker/overlay2/a8c3e0d43b8b27fd19a575c3051c9cea6450d39d8fbb58c3d34c7d8b898d3b97/diff

看到不一样了么?就是v1比latest多了一层,/var/lib/docker/overlay2/9d155c02707c57771128e397e6e43c9c9691a544e8e5749b87da9ebc5857f554/diff:

5.3、容器

Docker基础_第13张图片

  • 在虚拟机模型中,一旦启动,就会占有机器上的全部物理资源,如CPU、RAM、存储等
  • 容器引擎可以获取系统资源,比如进程树、文件系统以及网络栈,接着将资源分割为安全的互相隔离的资源结构,称之为容器

5.4、容器测试

[root@node1 ~]# docker images
REPOSITORY     TAG            IMAGE ID       CREATED         SIZE
nginx          v1             a80567189207   2 days ago      141MB
bjbfd/nginx    latest         605c77e624dd   17 months ago   141MB
nginx          latest         605c77e624dd   17 months ago   141MB
wordpress      latest         c3c92cc3dcb1   17 months ago   616MB
mariadb        10.6.4-focal   12e05d5da3c5   19 months ago   409MB
bjbfd/stress   latest         89e5b79daa74   7 years ago     215MB
[root@node1 ~]# docker run -itd nginx:v1
7d63e23cd145290fd49108049940b470f00bea5fc78f5a5dd83288493356415b
[root@node1 ~]# docker ps -a
CONTAINER ID   IMAGE          COMMAND                   CREATED          STATUS          PORTS     NAMES
7d63e23cd145   nginx:v1       "/docker-entrypoint.…"   3 seconds ago    Up 2 seconds    80/tcp    stupefied_fermi
10cc2cc80377   nginx:latest   "/docker-entrypoint.…"   31 seconds ago   Up 30 seconds   80/tcp    great_edison
[root@node1 ~]# docker exec -it 7d63e23cd145 /bin/bash
root@7d63e23cd145:/# curl 127.0.0.1
这是一个本地构建的nginx镜像
root@7d63e23cd145:/#

5.5、容器生命周期

Docker基础_第14张图片

5.6、docker仓库

  • 仓库(Repository)是集中存放镜像的地方,又分公共仓库和私有仓库
  • 注册服务器(Register)是来保存仓库的服务器。一个Register可以支持多个仓库
  • Docker运行中使用的默认仓库是Docker Hub公共仓库
    简单说,就像maven仓库一样,有本地仓库和原生仓库,本地仓库用来缓存一些包,远程仓库用来保存第三方包,供自己远程发布让别人使用及使用别人的第三方包
登录,输入用户名/密码,因为我已经登录,所以直接success
[root@node1 ~]# docker login
Authenticating with existing credentials...
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
[root@node1 ~]# docker images
REPOSITORY     TAG            IMAGE ID       CREATED         SIZE
nginx          v1             a80567189207   2 days ago      141MB
bjbfd/nginx    latest         605c77e624dd   17 months ago   141MB
nginx          latest         605c77e624dd   17 months ago   141MB
wordpress      latest         c3c92cc3dcb1   17 months ago   616MB
mariadb        10.6.4-focal   12e05d5da3c5   19 months ago   409MB
bjbfd/stress   latest         89e5b79daa74   7 years ago     215MB
[root@node1 ~]# docker tag bjbfd/nginx:latest  bjbfd/nginx:v1
[root@node1 ~]# docker push bjbfd/nginx:v1
The push refers to repository [docker.io/bjbfd/nginx]
d874fd2bc83b: Layer already exists
32ce5f6a5106: Layer already exists
f1db227348d0: Layer already exists
b8d6e692a25e: Layer already exists
e379e8aedd4d: Layer already exists
2edcec3590a4: Layer already exists
v1: digest: sha256:ee89b00528ff4f02f2405e4ee221743ebc3f8e8dd0bfd5c4c20a2fa2aaa7ede3 size: 1570
[root@node1 ~]#

查看 http://hub.docker.com/
Docker基础_第15张图片

6、详说Libcontainer

上面说到Libcontainer是一套独立的容器管理解决方案,里面包含什么组件呢?

6.1、namespace

namespace是对全局系统资源的一种封装隔离,使得处于不同namespace的进程拥有独立的全局系统资源,改变一个namespace中的系统资源只会影响当前namespace里的进程,对其他namespace中的进程没有影响

Docker基础_第16张图片

[root@node1 ~]# ls -l /proc/1/ns
总用量 0
lrwxrwxrwx 1 root root 0 5月  30 09:56 ipc -> ipc:[4026531839]
lrwxrwxrwx 1 root root 0 5月  30 09:56 mnt -> mnt:[4026531840]
lrwxrwxrwx 1 root root 0 5月  30 09:00 net -> net:[4026531956]
lrwxrwxrwx 1 root root 0 5月  30 09:56 pid -> pid:[4026531836]
lrwxrwxrwx 1 root root 0 5月  30 09:56 user -> user:[4026531837]
lrwxrwxrwx 1 root root 0 5月  30 09:56 uts -> uts:[4026531838]
[root@node1 ~]# ls -l /proc/2/ns
总用量 0
lrwxrwxrwx 1 root root 0 5月  30 09:56 ipc -> ipc:[4026531839]
lrwxrwxrwx 1 root root 0 5月  30 09:56 mnt -> mnt:[4026531840]
lrwxrwxrwx 1 root root 0 5月  30 09:56 net -> net:[4026531956]
lrwxrwxrwx 1 root root 0 5月  30 09:56 pid -> pid:[4026531836]
lrwxrwxrwx 1 root root 0 5月  30 09:56 user -> user:[4026531837]
lrwxrwxrwx 1 root root 0 5月  30 09:56 uts -> uts:[4026531838]

看到进程1和进程2是在同一个命名空间的

  • namespace是libcontainer的左膀右臂,可以说没有隔离即不存在容器
  • 容器的本质也是进程,故在派生进程时,Docker Daemon传入了与namespace相关的flag参数,实现namespace的创建,确保容器(进程)被执行之后,也就是在进程在运行时达到namespace隔离的效果
  • 容器的整个生命周期中,namespace是最为基础的一块。Docker容器的很多功能均在namespace的基础上完成。简单的理解是:隔离的环境创建完毕之后,内部环境的初始化才能登场
[root@node1 ~]# docker ps -a
CONTAINER ID   IMAGE            COMMAND                   CREATED             STATUS             PORTS     NAMES
ae04ef37f2c1   bjbfd/nginx:v1   "/docker-entrypoint.…"   About an hour ago   Up About an hour   80/tcp    interesting_gates
2d95b4eee9cd   nginx:latest     "/docker-entrypoint.…"   About an hour ago   Up About an hour   80/tcp    funny_bartik
[root@node1 ~]# ps -ef | grep nginx
root      1697  1676  0 09:02 pts/0    00:00:00 nginx: master process nginx -g daemon off;
101       1746  1697  0 09:02 pts/0    00:00:00 nginx: worker process
101       1747  1697  0 09:02 pts/0    00:00:00 nginx: worker process
root      1790  1768  0 09:03 pts/0    00:00:00 nginx: master process nginx -g daemon off;
101       1834  1790  0 09:03 pts/0    00:00:00 nginx: worker process
101       1835  1790  0 09:03 pts/0    00:00:00 nginx: worker process
root      3312  1193  0 10:16 pts/0    00:00:00 grep --color=auto nginx
[root@node1 ~]# ls -l /proc/1697/ns
总用量 0
lrwxrwxrwx 1 root root 0 5月  30 10:16 ipc -> ipc:[4026532295]
lrwxrwxrwx 1 root root 0 5月  30 10:16 mnt -> mnt:[4026532293]
lrwxrwxrwx 1 root root 0 5月  30 09:02 net -> net:[4026532298]
lrwxrwxrwx 1 root root 0 5月  30 09:03 pid -> pid:[4026532296]
lrwxrwxrwx 1 root root 0 5月  30 10:16 user -> user:[4026531837]
lrwxrwxrwx 1 root root 0 5月  30 10:16 uts -> uts:[4026532294]
[root@node1 ~]# ls -l /proc/1790/ns
总用量 0
lrwxrwxrwx 1 root root 0 5月  30 10:16 ipc -> ipc:[4026532358]
lrwxrwxrwx 1 root root 0 5月  30 10:16 mnt -> mnt:[4026532356]
lrwxrwxrwx 1 root root 0 5月  30 09:03 net -> net:[4026532361]
lrwxrwxrwx 1 root root 0 5月  30 09:03 pid -> pid:[4026532359]
lrwxrwxrwx 1 root root 0 5月  30 10:16 user -> user:[4026531837]
lrwxrwxrwx 1 root root 0 5月  30 10:16 uts -> uts:[4026532357]
[root@node1 ~]#

不同容器命名空间一般不相同,但是也是可以相同的
简单来说,命名空间就是用来隔离进程的

6.2、Cgroup

cgroup(control group)是控制组群,是Linux内核的一个特性功能,用来限制、控制与分离一个进程组的资源

内存

准备环境
yum install -y libcgroup libcgroup-tools 

修改下内核,让程序可以随便申请内存
echo 1 > /proc/sys/vm/overcommit_memory

关闭交换分区
swapoff -a
1、创建一个cgroup限制
cd /sys/fs/cgroup/memory/
mkdir journey
cd journey
[root@node1 journey]# ll
总用量 0
-rw-r--r-- 1 root root 0 5月  30 15:11 cgroup.clone_children
--w--w--w- 1 root root 0 5月  30 15:11 cgroup.event_control
-rw-r--r-- 1 root root 0 5月  30 15:11 cgroup.procs
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.failcnt
--w------- 1 root root 0 5月  30 15:11 memory.force_empty
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.kmem.failcnt
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.kmem.limit_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.kmem.max_usage_in_bytes
-r--r--r-- 1 root root 0 5月  30 15:11 memory.kmem.slabinfo
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.kmem.tcp.failcnt
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.kmem.tcp.limit_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.kmem.tcp.max_usage_in_bytes
-r--r--r-- 1 root root 0 5月  30 15:11 memory.kmem.tcp.usage_in_bytes
-r--r--r-- 1 root root 0 5月  30 15:11 memory.kmem.usage_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.limit_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.max_usage_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.memsw.failcnt
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.memsw.limit_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.memsw.max_usage_in_bytes
-r--r--r-- 1 root root 0 5月  30 15:11 memory.memsw.usage_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.move_charge_at_immigrate
-r--r--r-- 1 root root 0 5月  30 15:11 memory.numa_stat
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.oom_control
---------- 1 root root 0 5月  30 15:11 memory.pressure_level
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.soft_limit_in_bytes
-r--r--r-- 1 root root 0 5月  30 15:11 memory.stat
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.swappiness
-r--r--r-- 1 root root 0 5月  30 15:11 memory.usage_in_bytes
-rw-r--r-- 1 root root 0 5月  30 15:11 memory.use_hierarchy
-rw-r--r-- 1 root root 0 5月  30 15:11 notify_on_release
-rw-r--r-- 1 root root 0 5月  30 15:11 tasks

2、修改配置,限制内存在100MB内
echo $((100*1024*1024)) > memory.limit_in_bytes

3、编译一个程序来测试下,看能否限制在100M内,代码如下:
#include 
#include 
#include 

int main(int argc, char **argv)
{
    int max = -1;
    int mb = 0;
    char *buffer;
    int i;
#define SIZE 500
    unsigned int *p = malloc(1024 * 1024 * SIZE);

    printf("malloc buffer: %p\n", p);

    for (i = 0; i < 1024 * 1024 * (SIZE/sizeof(int)); i++) {
        p[i] = 123;
        if ((i & 0xFFFFF) == 0) {
            printf("%dMB written\n", i >> 18);
            usleep(100000);
        }
    }
    pause();
    return 0;
}

编译一下
gcc oom.c

使用cgroup来测试下
cgexec -g memory:journey ./a.out

[root@node1 cgroup]# cgexec -g memory:journey ./a.out
malloc buffer: 0x7f7cf9772010
0MB written
4MB written
8MB written
12MB written
16MB written
20MB written
24MB written
28MB written
32MB written
36MB written
40MB written
44MB written
48MB written
52MB written
56MB written
60MB written
64MB written
68MB written
72MB written
76MB written
80MB written
84MB written
88MB written
92MB written
96MB written
已杀死
[root@node1 cgroup]#

注意 : 说白了其实就是把当前的进程id让如到了journey下的tasks中
[root@node1 journey]# cat tasks
9131
[root@node1 journey]# cat tasks
9131
清除环境

删除cgroup下的journey目录的步骤如下:

rmdir /sys/fs/cgroup/memory/journey

如果报错没权限,看看是不是把当前会话的pid放进去了,如果是则把它移出来,命令如下 :

echo $$ > /sys/fs/cgroup/memory/tasks 

之后再删除journey目录

CPU

1、安装cgcreate
yum install -y libcgroup
yum install -y libcgroup-tools

2、自定义cgroup
cd /sys/fs/cgroup/cpu
sudo cgcreate -g cpu:journey
cd journey
echo 50000 > cpu.cfs_quota_us

3、模拟消耗CPU进程
while true;do i=i+1;i=i;done

Docker基础_第17张图片

4、给进程设置tasks
cgclassify -g cpu:erikguan 1189

image.png

Docker基础_第18张图片

Docker资源隔离

[root@node1 journey]# docker run -it --rm -c 512 bjbfd/stress --cpu 2
stress: info: [1] dispatching hogs: 2 cpu, 0 io, 0 vm, 0 hdd

Docker基础_第19张图片

[root@node1 journey]# docker run -it --cpu-period=100000 --cpu-quota=50000 --rm -c 512 bjbfd/stress --cpu 2
stress: info: [1] dispatching hogs: 2 cpu, 0 io, 0 vm, 0 hdd

Docker基础_第20张图片

[root@node1 journey]# docker run -it --cpu-period=100000 --cpu-quota=100000 --rm -c 512 bjbfd/stress --cpu 2
stress: info: [1] dispatching hogs: 2 cpu, 0 io, 0 vm, 0 hdd

Docker基础_第21张图片

可以看到,如果--cpu-period 和 --cpu-quota 是可以针对多个CPU设置的,如果是多个CPU,那么就会进行资源的平衡分配
比如说如果是一个CPU,那如果--cpu-period=--cpu-quota,自然会让CPU飙到100%左右

如果是--cpu-period等于--cpu-quota,但是CPU设置的是2个,那么各自CPU资源50%左右

如果是--cpu-period是--cpu-quota的一倍,但是CPU设置的是2个,那么各自CPU资源25%左右

Network

[root@node1 wordpress]# cat docker-compose.yml
services:
  db:
    # We use a mariadb image which supports both amd64 & arm64 architecture
    image: mariadb:10.6.4-focal
    # If you really want to use MySQL, uncomment the following line
    #image: mysql:8.0.27
    command: '--default-authentication-plugin=mysql_native_password'
    volumes:
      - db_data:/var/lib/mysql
    restart: always
    environment:
      - MYSQL_ROOT_PASSWORD=somewordpress
      - MYSQL_DATABASE=wordpress
      - MYSQL_USER=wordpress
      - MYSQL_PASSWORD=wordpress
    expose:
      - 3306
      - 33060
  wordpress:
    image: wordpress:latest
    volumes:
      - wp_data:/var/www/html
    ports:
      - 80:80
    restart: always
    environment:
      - WORDPRESS_DB_HOST=db
      - WORDPRESS_DB_USER=wordpress
      - WORDPRESS_DB_PASSWORD=wordpress
      - WORDPRESS_DB_NAME=wordpress
volumes:
  db_data:
  wp_data:
[root@node1 wordpress]# docker compose up -d
[+] Building 0.0s (0/0)
[+] Running 3/3
 ✔ Network wordpress_default        Created                                                                                                                                                            0.0s
 ✔ Container wordpress-wordpress-1  Started                                                                                                                                                            0.6s
 ✔ Container wordpress-db-1         Started                                                                                                                                                            0.5s
[root@node1 wordpress]# docker ps -a
CONTAINER ID   IMAGE                  COMMAND                   CREATED         STATUS         PORTS                               NAMES
241beb742e3a   wordpress:latest       "docker-entrypoint.s…"   6 seconds ago   Up 5 seconds   0.0.0.0:80->80/tcp, :::80->80/tcp   wordpress-wordpress-1
df4edffe6f14   mariadb:10.6.4-focal   "docker-entrypoint.s…"   6 seconds ago   Up 5 seconds   3306/tcp, 33060/tcp                 wordpress-db-1

注意: docker-compose.yml 其中 WORDPRESS_DB_HOST=db,为什么会配置成db呢?

登录 wordpress 容器中,ping一下db看网络是不是通的?

[root@node1 ~]# docker ps -a
CONTAINER ID   IMAGE                  COMMAND                   CREATED          STATUS          PORTS                               NAMES
241beb742e3a   wordpress:latest       "docker-entrypoint.s…"   18 minutes ago   Up 18 minutes   0.0.0.0:80->80/tcp, :::80->80/tcp   wordpress-wordpress-1
df4edffe6f14   mariadb:10.6.4-focal   "docker-entrypoint.s…"   18 minutes ago   Up 18 minutes   3306/tcp, 33060/tcp                 wordpress-db-1
[root@node1 ~]# docker exec -it 241beb742e3a /bin/bash
root@241beb742e3a:/var/www/html# ping db
bash: ping: command not found
root@241beb742e3a:/var/www/html# cp /etc/apt/sources.list /etc/apt/sources.list.bak && sed -i "s@http://deb.debian.org@http://mirrors.aliyun.com@g" /etc/apt/sources.list && rm -rf /var/lib/apt/lists/* && apt-get update
Get:1 http://mirrors.aliyun.com/debian bullseye InRelease [116 kB]
Get:2 http://mirrors.aliyun.com/debian bullseye-updates InRelease [44.1 kB]
Get:3 http://security.debian.org/debian-security bullseye-security InRelease [48.4 kB]
Get:4 http://mirrors.aliyun.com/debian bullseye/main amd64 Packages [8183 kB]
Get:5 http://security.debian.org/debian-security bullseye-security/main amd64 Packages [245 kB]
Get:6 http://mirrors.aliyun.com/debian bullseye-updates/main amd64 Packages [14.8 kB]
Fetched 8650 kB in 5s (1684 kB/s)
Reading package lists... Done
root@241beb742e3a:/var/www/html# apt-get install iputils-ping
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
The following additional packages will be installed:
  libcap2 libcap2-bin libpam-cap
The following NEW packages will be installed:
  iputils-ping libcap2 libcap2-bin libpam-cap
0 upgraded, 4 newly installed, 0 to remove and 77 not upgraded.
Need to get 121 kB of archives.
After this operation, 348 kB of additional disk space will be used.
Do you want to continue? [Y/n] Y
Get:1 http://mirrors.aliyun.com/debian bullseye/main amd64 libcap2 amd64 1:2.44-1 [23.6 kB]
Get:2 http://mirrors.aliyun.com/debian bullseye/main amd64 libcap2-bin amd64 1:2.44-1 [32.6 kB]
Get:3 http://mirrors.aliyun.com/debian bullseye/main amd64 iputils-ping amd64 3:20210202-1 [49.8 kB]
Get:4 http://mirrors.aliyun.com/debian bullseye/main amd64 libpam-cap amd64 1:2.44-1 [15.4 kB]
Fetched 121 kB in 0s (391 kB/s)
debconf: delaying package configuration, since apt-utils is not installed
Selecting previously unselected package libcap2:amd64.
(Reading database ... 16124 files and directories currently installed.)
Preparing to unpack .../libcap2_1%3a2.44-1_amd64.deb ...
Unpacking libcap2:amd64 (1:2.44-1) ...
Selecting previously unselected package libcap2-bin.
Preparing to unpack .../libcap2-bin_1%3a2.44-1_amd64.deb ...
Unpacking libcap2-bin (1:2.44-1) ...
Selecting previously unselected package iputils-ping.
Preparing to unpack .../iputils-ping_3%3a20210202-1_amd64.deb ...
Unpacking iputils-ping (3:20210202-1) ...
Selecting previously unselected package libpam-cap:amd64.
Preparing to unpack .../libpam-cap_1%3a2.44-1_amd64.deb ...
Unpacking libpam-cap:amd64 (1:2.44-1) ...
Setting up libcap2:amd64 (1:2.44-1) ...
Setting up libcap2-bin (1:2.44-1) ...
Setting up libpam-cap:amd64 (1:2.44-1) ...
debconf: unable to initialize frontend: Dialog
debconf: (No usable dialog-like program is installed, so the dialog based frontend cannot be used. at /usr/share/perl5/Debconf/FrontEnd/Dialog.pm line 78.)
debconf: falling back to frontend: Readline
Setting up iputils-ping (3:20210202-1) ...
Processing triggers for libc-bin (2.31-13+deb11u2) ...
root@241beb742e3a:/var/www/html# ping db
PING db (172.18.0.2) 56(84) bytes of data.
64 bytes from wordpress-db-1.wordpress_default (172.18.0.2): icmp_seq=1 ttl=64 time=0.093 ms
64 bytes from wordpress-db-1.wordpress_default (172.18.0.2): icmp_seq=2 ttl=64 time=0.076 ms
^C
--- db ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1002ms
rtt min/avg/max/mdev = 0.076/0.084/0.093/0.008 ms
root@241beb742e3a:/var/www/html# cat /etc/hosts
127.0.0.1    localhost
::1    localhost ip6-localhost ip6-loopback
fe00::0    ip6-localnet
ff00::0    ip6-mcastprefix
ff02::1    ip6-allnodes
ff02::2    ip6-allrouters
172.18.0.3    241beb742e3a
root@241beb742e3a:/var/www/html#

注意,ubuntu加速器 :

cp /etc/apt/sources.list /etc/apt/sources.list.bak && sed -i "s@http://deb.debian.org@http://mirrors.aliyun.com@g" /etc/apt/sources.list && rm -rf /var/lib/apt/lists/* && apt-get update

发现直接ping db是通的

[root@node1 wordpress]# docker inspect wordpress-db-1
[
    {
        "Id": "df4edffe6f1440a55fe7368d304ff4f5bb3f7b2dfe991372c81d7510de847aed",
        "Created": "2023-05-31T03:02:26.234155577Z",
        "Path": "docker-entrypoint.sh",
        "Args": [
            "--default-authentication-plugin=mysql_native_password"
        ],
        "State": {
            "Status": "running",
            "Running": true,
            "Paused": false,
            "Restarting": false,
            "OOMKilled": false,
            "Dead": false,
            "Pid": 1696,
            "ExitCode": 0,
            "Error": "",
            "StartedAt": "2023-05-31T03:02:26.766497036Z",
            "FinishedAt": "0001-01-01T00:00:00Z"
        },
        "Image": "sha256:12e05d5da3c5223e9877e8eb90d68560ff66cedcb955131061d60d093a908f0c",
        "ResolvConfPath": "/var/lib/docker/containers/df4edffe6f1440a55fe7368d304ff4f5bb3f7b2dfe991372c81d7510de847aed/resolv.conf",
        "HostnamePath": "/var/lib/docker/containers/df4edffe6f1440a55fe7368d304ff4f5bb3f7b2dfe991372c81d7510de847aed/hostname",
        "HostsPath": "/var/lib/docker/containers/df4edffe6f1440a55fe7368d304ff4f5bb3f7b2dfe991372c81d7510de847aed/hosts",
        "LogPath": "/var/lib/docker/containers/df4edffe6f1440a55fe7368d304ff4f5bb3f7b2dfe991372c81d7510de847aed/df4edffe6f1440a55fe7368d304ff4f5bb3f7b2dfe991372c81d7510de847aed-json.log",
        "Name": "/wordpress-db-1",
        "RestartCount": 0,
        "Driver": "overlay2",
        "Platform": "linux",
        "MountLabel": "",
        "ProcessLabel": "",
        "AppArmorProfile": "",
        "ExecIDs": null,
        "HostConfig": {
            "Binds": null,
            "ContainerIDFile": "",
            "LogConfig": {
                "Type": "json-file",
                "Config": {}
            },
            "NetworkMode": "wordpress_default",
            "PortBindings": {},
            "RestartPolicy": {
                "Name": "always",
                "MaximumRetryCount": 0
            },
            "AutoRemove": false,
            "VolumeDriver": "",
            "VolumesFrom": null,
            "ConsoleSize": [
                0,
                0
            ],
            "CapAdd": null,
            "CapDrop": null,
            "CgroupnsMode": "host",
            "Dns": null,
            "DnsOptions": null,
            "DnsSearch": null,
            "ExtraHosts": [],
            "GroupAdd": null,
            "IpcMode": "private",
            "Cgroup": "",
            "Links": null,
            "OomScoreAdj": 0,
            "PidMode": "",
            "Privileged": false,
            "PublishAllPorts": false,
            "ReadonlyRootfs": false,
            "SecurityOpt": null,
            "UTSMode": "",
            "UsernsMode": "",
            "ShmSize": 67108864,
            "Runtime": "runc",
            "Isolation": "",
            "CpuShares": 0,
            "Memory": 0,
            "NanoCpus": 0,
            "CgroupParent": "",
            "BlkioWeight": 0,
            "BlkioWeightDevice": null,
            "BlkioDeviceReadBps": null,
            "BlkioDeviceWriteBps": null,
            "BlkioDeviceReadIOps": null,
            "BlkioDeviceWriteIOps": null,
            "CpuPeriod": 0,
            "CpuQuota": 0,
            "CpuRealtimePeriod": 0,
            "CpuRealtimeRuntime": 0,
            "CpusetCpus": "",
            "CpusetMems": "",
            "Devices": null,
            "DeviceCgroupRules": null,
            "DeviceRequests": null,
            "MemoryReservation": 0,
            "MemorySwap": 0,
            "MemorySwappiness": null,
            "OomKillDisable": false,
            "PidsLimit": null,
            "Ulimits": null,
            "CpuCount": 0,
            "CpuPercent": 0,
            "IOMaximumIOps": 0,
            "IOMaximumBandwidth": 0,
            "Mounts": [
                {
                    "Type": "volume",
                    "Source": "wordpress_db_data",
                    "Target": "/var/lib/mysql",
                    "VolumeOptions": {}
                }
            ],
            "MaskedPaths": [
                "/proc/asound",
                "/proc/acpi",
                "/proc/kcore",
                "/proc/keys",
                "/proc/latency_stats",
                "/proc/timer_list",
                "/proc/timer_stats",
                "/proc/sched_debug",
                "/proc/scsi",
                "/sys/firmware"
            ],
            "ReadonlyPaths": [
                "/proc/bus",
                "/proc/fs",
                "/proc/irq",
                "/proc/sys",
                "/proc/sysrq-trigger"
            ]
        },
        "GraphDriver": {
            "Data": {
                "LowerDir": "/var/lib/docker/overlay2/e3318886258229021434b6efcb9a5a13d10c44ff8e9ec0c670518af592273512-init/diff:/var/lib/docker/overlay2/9f6770cf9af716ae27c68881ee5858253a65ad6fa0f49554cbf49039b12b391f/diff:/var/lib/docker/overlay2/5a8d99a9b8f7de0449343243b04a1e7dbd78ad76f3a45c209f442cedc71533ae/diff:/var/lib/docker/overlay2/4c84801e8550ff953f976d734abb86f437124fbf67031943e732d68f3ed2e303/diff:/var/lib/docker/overlay2/215f31fe18a49c02cf3f14897d8f7fc689354666b06ec55222c4ff3ceeed348f/diff:/var/lib/docker/overlay2/3d0b32da1b848f2e1baad8e6aee469d757aeb990333033299fec356160139a53/diff:/var/lib/docker/overlay2/95a21c51856d00bfc79de70dabcc798eb866ff5c0ec93128cc39fe7a8170cf2b/diff:/var/lib/docker/overlay2/df2dfff8612dbe3c56ca544418d9c7cdacb0bd06d94118b9e8283b3115ed3023/diff:/var/lib/docker/overlay2/374bc7160fbc3f6b1f391a9a1ce05d9210dbb5627bc7e0eca1534d64bc982b51/diff:/var/lib/docker/overlay2/a9777594ba1d0930e43bf7ffc84be1db32419feb61d7e692b73e7a58ca4295f7/diff:/var/lib/docker/overlay2/9ea529592dbb052f869f8ab86a3d7169ea9dd107d49465d84c8d87aa68913785/diff",
                "MergedDir": "/var/lib/docker/overlay2/e3318886258229021434b6efcb9a5a13d10c44ff8e9ec0c670518af592273512/merged",
                "UpperDir": "/var/lib/docker/overlay2/e3318886258229021434b6efcb9a5a13d10c44ff8e9ec0c670518af592273512/diff",
                "WorkDir": "/var/lib/docker/overlay2/e3318886258229021434b6efcb9a5a13d10c44ff8e9ec0c670518af592273512/work"
            },
            "Name": "overlay2"
        },
        "Mounts": [
            {
                "Type": "volume",
                "Name": "wordpress_db_data",
                "Source": "/var/lib/docker/volumes/wordpress_db_data/_data",
                "Destination": "/var/lib/mysql",
                "Driver": "local",
                "Mode": "z",
                "RW": true,
                "Propagation": ""
            }
        ],
        "Config": {
            "Hostname": "df4edffe6f14",
            "Domainname": "",
            "User": "",
            "AttachStdin": false,
            "AttachStdout": true,
            "AttachStderr": true,
            "ExposedPorts": {
                "3306": {},
                "3306/tcp": {},
                "33060": {}
            },
            "Tty": false,
            "OpenStdin": false,
            "StdinOnce": false,
            "Env": [
                "MYSQL_ROOT_PASSWORD=somewordpress",
                "MYSQL_DATABASE=wordpress",
                "MYSQL_USER=wordpress",
                "MYSQL_PASSWORD=wordpress",
                "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin",
                "GOSU_VERSION=1.13",
                "MARIADB_MAJOR=10.6",
                "MARIADB_VERSION=1:10.6.4+maria~focal"
            ],
            "Cmd": [
                "--default-authentication-plugin=mysql_native_password"
            ],
            "Image": "mariadb:10.6.4-focal",
            "Volumes": {
                "/var/lib/mysql": {}
            },
            "WorkingDir": "",
            "Entrypoint": [
                "docker-entrypoint.sh"
            ],
            "OnBuild": null,
            "Labels": {
                "com.docker.compose.config-hash": "1a931c5225f4f77e1bc71a07a8f2f658f90aba92bcdb6b64dd98afe54569e3b7",
                "com.docker.compose.container-number": "1",
                "com.docker.compose.depends_on": "",
                "com.docker.compose.image": "sha256:12e05d5da3c5223e9877e8eb90d68560ff66cedcb955131061d60d093a908f0c",
                "com.docker.compose.oneoff": "False",
                "com.docker.compose.project": "wordpress",
                "com.docker.compose.project.config_files": "/opt/docker-compose/wordpress/docker-compose.yml",
                "com.docker.compose.project.working_dir": "/opt/docker-compose/wordpress",
                "com.docker.compose.service": "db",
                "com.docker.compose.version": "2.18.1"
            }
        },
        "NetworkSettings": {
            "Bridge": "",
            "SandboxID": "f67ea95d2e2f40c27e142f49f592632c48f2163a9b3c7af1afd11cf420831993",
            "HairpinMode": false,
            "LinkLocalIPv6Address": "",
            "LinkLocalIPv6PrefixLen": 0,
            "Ports": {
                "3306/tcp": null,
                "33060/tcp": null
            },
            "SandboxKey": "/var/run/docker/netns/f67ea95d2e2f",
            "SecondaryIPAddresses": null,
            "SecondaryIPv6Addresses": null,
            "EndpointID": "",
            "Gateway": "",
            "GlobalIPv6Address": "",
            "GlobalIPv6PrefixLen": 0,
            "IPAddress": "",
            "IPPrefixLen": 0,
            "IPv6Gateway": "",
            "MacAddress": "",
            "Networks": {
                "wordpress_default": {
                    "IPAMConfig": null,
                    "Links": null,
                    "Aliases": [
                        "wordpress-db-1",
                        "db",
                        "df4edffe6f14"
                    ],
                    "NetworkID": "b9c6885f3d356548ec1cb4425bdf5b4667517952a1be99a5fce866fe4031366e",
                    "EndpointID": "860ab7e75760b245f736458c8d5193582a6ada76236ec49e7c288865c533fd0a",
                    "Gateway": "172.18.0.1",
                    "IPAddress": "172.18.0.2",
                    "IPPrefixLen": 16,
                    "IPv6Gateway": "",
                    "GlobalIPv6Address": "",
                    "GlobalIPv6PrefixLen": 0,
                    "MacAddress": "02:42:ac:12:00:02",
                    "DriverOpts": null
                }
            }
        }
    }
]

查看容器wordpress-wordpress-1的元数据,发现

"Aliases": [
    "wordpress-db-1",
    "db",
    "df4edffe6f14"
],

看到db和df4edffe6f14有一个别名映射,具体之后再说,现在就知道有映射就可以通过db别名,找到对应容器主机了哈

Docker容器通讯网络

[root@node1 wordpress]# docker ps -a
CONTAINER ID   IMAGE                  COMMAND                   CREATED         STATUS         PORTS                               NAMES
21c2026e2432   wordpress:latest       "docker-entrypoint.s…"   3 seconds ago   Up 2 seconds   0.0.0.0:80->80/tcp, :::80->80/tcp   wordpress-wordpress-1
2ea884834c25   mariadb:10.6.4-focal   "docker-entrypoint.s…"   3 seconds ago   Up 2 seconds   3306/tcp, 33060/tcp                 wordpress-db-1
[root@node1 wordpress]# docker network ls
NETWORK ID     NAME                DRIVER    SCOPE
13cca099cd6e   bridge              bridge    local
4882bc599fcc   docker_gwbridge     bridge    local
06d4d17eacbf   host                host      local
zylych55j9kk   ingress             overlay   swarm
276755b5e003   none                null      local
36ca37c22576   wordpress_default   bridge    local
Name Driver Desc
bridge bridge 容器配置veth网络接口对,并配置loopback接口
host host 不为容器创建网络命名空间
none null 容器创建网络命名空间,配置loopback接口
wordpress_default bridge 自定义网络,同一个网络内容器可以互连互通
ingress overlay 集群外网,不同节点的容器互通
docker_gwbridge bridge 集群网络,集群的中转网络

网络分析

1、启动wordpress,使用docker compose
[root@node1 wordpress]# cat docker-compose.yml
services:
  db:
    # We use a mariadb image which supports both amd64 & arm64 architecture
    image: mariadb:10.6.4-focal
    # If you really want to use MySQL, uncomment the following line
    #image: mysql:8.0.27
    command: '--default-authentication-plugin=mysql_native_password'
    volumes:
      - db_data:/var/lib/mysql
    restart: always
    environment:
      - MYSQL_ROOT_PASSWORD=somewordpress
      - MYSQL_DATABASE=wordpress
      - MYSQL_USER=wordpress
      - MYSQL_PASSWORD=wordpress
    expose:
      - 3306
      - 33060
  wordpress:
    image: wordpress:latest
    volumes:
      - wp_data:/var/www/html
    ports:
      - 80:80
    restart: always
    environment:
      - WORDPRESS_DB_HOST=db
      - WORDPRESS_DB_USER=wordpress
      - WORDPRESS_DB_PASSWORD=wordpress
      - WORDPRESS_DB_NAME=wordpress
volumes:
  db_data:
  wp_data:
[root@node1 wordpress]# docker compose up -d
[+] Building 0.0s (0/0)
[+] Running 3/3
 ✔ Network wordpress_default        Created                                                                                                                                                                                                                                0.0s
 ✔ Container wordpress-wordpress-1  Started                                                                                                                                                                                                                                0.5s
 ✔ Container wordpress-db-1         Started                                                                                                                                                                                                                                0.5s

2、启动nginx容器
[root@node1 wordpress]# docker run -itd nginx:v1
aa4debaeb394d3463eb73bcd42d135e30bc3d209557ff6837ca48254ea3048e1

[root@node1 wordpress]# docker ps -a
CONTAINER ID   IMAGE                  COMMAND                   CREATED          STATUS          PORTS                               NAMES
aa4debaeb394   nginx:v1               "/docker-entrypoint.…"   35 minutes ago   Up 35 minutes   80/tcp                              jolly_volhard
3fa6d26fe395   wordpress:latest       "docker-entrypoint.s…"   36 minutes ago   Up 36 minutes   0.0.0.0:80->80/tcp, :::80->80/tcp   wordpress-wordpress-1
580586a0ec98   mariadb:10.6.4-focal   "docker-entrypoint.s…"   36 minutes ago   Up 36 minutes   3306/tcp, 33060/tcp                 wordpress-db-1
[root@node1 wordpress]#

3、查看宿主机的网卡
[root@node1 wordpress]# ip a
1: lo:  mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0:  mtu 1500 qdisc mq state UP group default qlen 1000
    link/ether 00:16:3e:0e:fb:d8 brd ff:ff:ff:ff:ff:ff
    inet 172.24.251.132/20 brd 172.24.255.255 scope global dynamic eth0
       valid_lft 315354942sec preferred_lft 315354942sec
    inet6 fe80::216:3eff:fe0e:fbd8/64 scope link
       valid_lft forever preferred_lft forever
3: docker0:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:83:63:06:bd brd ff:ff:ff:ff:ff:ff
    inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0
       valid_lft forever preferred_lft forever
    inet6 fe80::42:83ff:fe63:6bd/64 scope link
       valid_lft forever preferred_lft forever
4: docker_gwbridge:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:27:54:34:5a brd ff:ff:ff:ff:ff:ff
    inet 172.19.0.1/16 brd 172.19.255.255 scope global docker_gwbridge
       valid_lft forever preferred_lft forever
    inet6 fe80::42:27ff:fe54:345a/64 scope link
       valid_lft forever preferred_lft forever
14: veth3093d94@if13:  mtu 1500 qdisc noqueue master docker_gwbridge state UP group default
    link/ether fa:3a:5d:53:b9:b8 brd ff:ff:ff:ff:ff:ff link-netnsid 3
    inet6 fe80::f83a:5dff:fe53:b9b8/64 scope link
       valid_lft forever preferred_lft forever
25: br-0e99973cc931:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:10:ff:d9:3e brd ff:ff:ff:ff:ff:ff
    inet 172.21.0.1/16 brd 172.21.255.255 scope global br-0e99973cc931
       valid_lft forever preferred_lft forever
    inet6 fe80::42:10ff:feff:d93e/64 scope link
       valid_lft forever preferred_lft forever
27: vethd41b331@if26:  mtu 1500 qdisc noqueue master br-0e99973cc931 state UP group default
    link/ether f6:c3:92:e4:27:9d brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet6 fe80::f4c3:92ff:fee4:279d/64 scope link
       valid_lft forever preferred_lft forever
29: veth3d7965e@if28:  mtu 1500 qdisc noqueue master br-0e99973cc931 state UP group default
    link/ether 46:dd:7c:1a:81:19 brd ff:ff:ff:ff:ff:ff link-netnsid 1
    inet6 fe80::44dd:7cff:fe1a:8119/64 scope link
       valid_lft forever preferred_lft forever
31: vethff85fdb@if30:  mtu 1500 qdisc noqueue master docker0 state UP group default
    link/ether aa:17:c7:84:22:dd brd ff:ff:ff:ff:ff:ff link-netnsid 4
    inet6 fe80::a817:c7ff:fe84:22dd/64 scope link
       valid_lft forever preferred_lft forever


宿主机的网卡,每台机器都有回环地址和网卡:
1: lo:  mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0:  mtu 1500 qdisc mq state UP group default qlen 1000
    link/ether 00:16:3e:0e:fb:d8 brd ff:ff:ff:ff:ff:ff
    inet 172.24.251.132/20 brd 172.24.255.255 scope global dynamic eth0
       valid_lft 315354942sec preferred_lft 315354942sec
    inet6 fe80::216:3eff:fe0e:fbd8/64 scope link
       valid_lft forever preferred_lft forever

docker0 是默认的桥接网络。是运行了 docker 这个软件就会有 docker0
3: docker0:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:83:63:06:bd brd ff:ff:ff:ff:ff:ff
    inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0
       valid_lft forever preferred_lft forever
    inet6 fe80::42:83ff:fe63:6bd/64 scope link
       valid_lft forever preferred_lft forever

br开头是 docker-compose 创建的网络
25: br-0e99973cc931:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:10:ff:d9:3e brd ff:ff:ff:ff:ff:ff
    inet 172.21.0.1/16 brd 172.21.255.255 scope global br-0e99973cc931
       valid_lft forever preferred_lft forever
    inet6 fe80::42:10ff:feff:d93e/64 scope link
       valid_lft forever preferred_lft forever
查看ningx网络
[root@node1 wordpress]# docker exec -it aa4debaeb394 /bin/bash
root@aa4debaeb394:/# ip a
bash: ip: command not found
root@aa4debaeb394:/# cp /etc/apt/sources.list /etc/apt/sources.list.bak && sed -i "s@http://deb.debian.org@http://mirrors.aliyun.com@g" /etc/apt/sources.list && rm -rf /var/lib/apt/lists/* && apt-get update
Get:1 http://mirrors.aliyun.com/debian bullseye InRelease [116 kB]
Get:2 http://mirrors.aliyun.com/debian bullseye-updates InRelease [44.1 kB]
Get:3 http://mirrors.aliyun.com/debian bullseye/main amd64 Packages [8183 kB]
Get:4 http://security.debian.org/debian-security bullseye-security InRelease [48.4 kB]
Get:5 http://security.debian.org/debian-security bullseye-security/main amd64 Packages [245 kB]
Get:6 http://mirrors.aliyun.com/debian bullseye-updates/main amd64 Packages [14.8 kB]
Fetched 8651 kB in 23s (369 kB/s)
Reading package lists... Done
root@aa4debaeb394:/# ip a
1: lo:  mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
30: eth0@if31:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:ac:11:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 172.17.0.2/16 brd 172.17.255.255 scope global eth0
       valid_lft forever preferred_lft forever
是不是发现 ip 是 172.17.0.2,docker0的ip 是 172.17.0.1,同一个网段
看wordpress
root@3fa6d26fe395:/var/www/html# ip a
1: lo:  mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
28: eth0@if29:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:ac:15:00:03 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 172.21.0.3/16 brd 172.21.255.255 scope global eth0
       valid_lft forever preferred_lft forever

看 mariadb:10.6.4-focal
[root@node1 wordpress]# docker exec -it 580586a0ec98 /bin/bash
root@580586a0ec98:/# ip a
1: lo:  mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
26: eth0@if27:  mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:ac:15:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 172.21.0.2/16 brd 172.21.255.255 scope global eth0
       valid_lft forever preferred_lft forever
root@580586a0ec98:/#
是不是发现 ip 是 172.21.0.2和172.21.0.3,br-0e99973cc931的ip 是 172.21.0.1,同一个网段

总结 :

  • docker0 是默认的桥接网络。是运行了 docker 这个软件就会有docker0
  • veth开头是docker0的儿子
  • br开头是docker-compose创建的网络
  • br就是bridge 的缩写,docker0 也是 bridge。br和docker0是并列的

如感兴趣,点赞加关注,谢谢!!!

你可能感兴趣的:(docker云原生)