• Docker容器:网络模式与资源控制


    目录

    一、Docker 网络模式

    1、Docker 网络实现原理

    2、Docker 网络模式概述

    2.1 Host 模式

    2.2 Container 模式

    2.3 None 模式

    2.4 Bridge 模式

    2.5 自定义网络(user-defined network)

    3、配置 docker 网络模式

    3.1 查看网络基础命令

    3.1.1 查看 docker 网络列表

    3.1.2 搜索指定网络模式的容器

    3.1.3 查看容器的进程

    3.1.4 查看容器信息(包含配置、环境、网关、挂载、cmd等信息)  

    3.1.5 查看网桥bridge信息

    3.2 配置 host 网络模式

    3.3 配置 container 网络模式

    3.4 配置 none 网络模式

    3.5 配置 bridge 网络模式

    3.6 配置 user-defined network 模式(自定义网络)

    二、Docker 资源控制

    1、CPU 资源控制

    1.1 设置CPU使用率上限 

    1.2 设置CPU资源占用比(设置多个容器时才有效)

    1.3 设置容器绑定指定的CPU

    2、对内存使用的限制

    2.1 使用--memory标志

    2.2 使用--memory-swap标志

    3、对磁盘IO配额控制(blkio)的限制

    3.1 限制容器的读写速度 

    3.2 限制容器的读写次数

    三、Docker 故障造成大量日志导致磁盘爆满故障

    四、总结

    1、Docker 网络模式

    2、Docker 资源控制

    2.1 CPU资源控制

    2.2 内存资源限制

    2.3 磁盘IO配额限制


    一、Docker 网络模式

    1、Docker 网络实现原理

    Docker使用Linux桥接,在宿主机虚拟一个Docker容器网桥(docker0),Docker启动一个容器时会根据Docker网桥的网段分配给容器一个IP地址,称为Container-IP,同时Docker网桥是每个容器的默认网关。因为在同一宿主机内的容器都接入同一个网桥,这样容器之间就能够通过容器的 Container-IP 直接通信

    Docker网桥是宿主机虚拟出来的,并不是真实存在的网络设备,外部网络是无法寻址到的,这也意味着外部网络无法直接通过 Container-IP 访问到容器。如果容器希望外部访问能够访问到,可以通过映射容器端口到宿主主机(端口映射),即 docker run 创建容器时候通过 -p 或 -P 参数来启用,访问容器的时候就通过[宿主机IP]:[容器端口]访问容器

    端口映射:

    在启动容器的时候,如果不指定对应的端口,在容器外是无法通过网络来访问容器内的服务

    端口映射机制将容器内的服务提供给外部网络访问,实质上就是将宿主机的端口映射到容器中,使得外部网络访问宿主机的端口便可访问容器内的服务

    1. docker run -d --name test1 -P nginx #随机映射端口(从32768开始)
    2. docker run -d --name test2 -p 9999:80 nginx #指定映射端口
    3. docker ps -a #查看当前所有的容器

    浏览器访问:http://172.16.12.12:32768 和 http://172.16.12.12:9999

    1. #查看容器的输出和日志信息
    2. 格式:docker logs 容器的ID/名称
    3. 如:docker logs test1

    1. #使用 docker run -p 时,docker实际是在iptables做了DNAT规则,实现端口转发功能
    2. iptables -t nat -vnL

    2、Docker 网络模式概述

    Docker 提供了多种网络模式,用于在容器间和容器与外部网络之间建立通信。这些网络模式可以根据实际需求选择,下面是一些常见的 Docker 网络模式

    2.1 Host 模式

    • 相当于Vmware中的桥接模式,与宿主机在同一个网络中,但没有独立IP地址
    • Docker使用了Linux的Namespaces技术来进行资源隔离,如PID Namespace隔离进程,Mount Namespace隔离文件系统,Network Namespace隔离网络等
    • 一个Network Namespace提供了一份独立的网络环境,包括网卡、路由、iptable规则等都与其他的Network Namespace隔离。 一个Docker容器一般会分配一个独立的Network Namespace。 但如果启动容器的时候使用host模式,那么这个容器将不会获得一个独立的Network Namespace, 而是和宿主机共用一个Network Namespace。容器将不会虚拟出自己的网卡、配置自己的IP等,而是使用宿主机的IP和端口
    • 解决了ip地址不固定的情况

    优点:

    ① 性能优势:由于容器与宿主机共享网络栈,因此在host网络模式下,容器之间的通信不需要经过网络地址转换(NAT),可以提高网络性能

    ② 简化网络配置:使用host网络模式可以简化网络配置,容器可以直接访问宿主机上的所有网络服务,无需进行端口映射

    ③ 高吞吐量:由于容器直接使用宿主机的网络接口,可以获得更高的网络吞吐量,适用于对网络性能要求较高的场景

    缺点:

    ① 安全性:由于容器与宿主机共享网络栈,容器之间的隔离性降低,可能会增加一定的安全风险,特别是在多租户环境中

    ② 端口冲突:在host网络模式下,容器与宿主机共享相同的网络接口,可能会导致端口冲突,需要谨慎管理端口使用

    ③ 不适用于多主机环境:host网络模式适用于单个主机上的容器,不适用于跨主机通信的场景

    2.2 Container 模式

    • 这个模式指定新创建的容器和已经存在的一个容器共享一个Network Namespace,而不是和宿主机共享。新创建的容器不会创建自己的网卡,配置自己的IP,而是和一个指定的容器共享IP、端口范围(端口不能一致)等
    • 同样,两个容器除了网络方面,其他的如文件系统、进程列表等还是隔离的。两个容器的进程可以通过lo网卡设备通信

     优点

    ① 容器之间共享同一个网络命名空间,可以直接进行网络通信,无需通过网络层进行路由,提高了网络通信的效率

    ② 可以方便地实现容器之间的私有网络,适用于需要高度互联的容器组

    ③ 可以更好地控制容器之间的通信,增强了网络安全性

    缺点

    ① 容器之间共享网络命名空间,可能会导致网络隔离性不足,容器之间的通信可能会相互影响

    ② 不适合需要完全隔离的场景,因为容器共享网络命名空间,可能会导致安全性问题

    ③ 可能会增加网络配置和管理的复杂性,特别是在大规模部署时

    2.3 None 模式

    • 该模式关闭了容器的网络功能
    • 使用none模式,Docker容器拥有自己的Network Namespace,但是,并不为Docker容器进行任何网络配置。也就是说,这个Docker容器没有网卡、IP、路由等信息。需要我们自己为Docker容器添加网卡、配置IP等
    • 这种网络模式下容器 只有lo回环网络,没有其他网卡。 none模式可以在容器创建时通过–network=none来指定。这种类型的网络没有办法联网,封闭的网络能很好的保证容器的安全性
    • 可以安全的储存数据,不会被攻击,可以用来当个仓库

    优点

    ① 提供了最高级别的隔离性,适用于一些需要完全隔离的场景,如测试隔离性等。

    ② 可以防止容器与外部网络发生意外的通信,增强了安全性。

    缺点

    ① 容器无法与外部网络通信,除非手动配置网络连接或使用其他通信方式,这可能增加了管理和配置的复杂性。

    ② 不适合一般应用场景,因为容器无法访问外部资源,如互联网或其他容器服务。

    2.4 Bridge 模式

    • 此模式会为每一个容器分配、设置IP等,并将容器连接到一个docker0虚拟网桥,通过docker0网桥以及iptables nat表配置与宿主之间的关联
    • 当Docker进程启动时,会在主机上创建一个名为docker0的虚拟网桥,此主机上启动的Docker容器会连接到这个虚拟网桥上。虚拟网桥的工作方式和物理交换机类似,这样主机上的所有容器就通过交换机连在了一个二层网络中
    • 从docker0子网中分配一个IP给容器使用,并设置docker0的IP地址为容器的默认网关。在主机上创建一对虚拟网卡veth pair设备,Docker将veth pair设备的一端放在新创建的容器中,并命名为eth0(容器的网卡),另一端放在主机中,以vethxxx这样类似的名字命名,并将这个网络设备加入到docker0网桥中。可以通过brctl show命令查看
    • bridge模式是docker的默认网络模式,不写–net参数,就是bridge模式。使用docker run -p时,docker实际是在iptables做了DNAT规则,实现端口转发功能。可以使用iptables -t nat -vnL查看

    优点

    ① 桥接网络模式是默认的网络模式,易于使用和管理。

    ② 提供了一定程度的网络隔离,容器之间默认无法直接通信,增强了安全性。

    ③ 允许容器使用NAT(网络地址转换)来访问外部网络,同时也支持端口映射,方便从外部访问容器内的服务。

    缺点

    ① 需要进行端口映射才能从外部访问容器内的服务,可能会增加管理复杂性。

    ② 容器之间的通信需要通过桥接网络,可能会影响性能,尤其在大规模部署时。

    2.5 自定义网络(user-defined network)

    创建自定义的网络模式来满足特定的网络需求。自定义网络模式可以帮助您更好地管理容器之间的通信和隔离

    优点:

    ① 隔离性:自定义网络模式可以帮助实现容器之间的隔离,使它们可以在独立的网络环境中运行

    ② 灵活性:通过自定义网络模式,您可以根据应用程序需求定制网络配置,实现更灵活的网络管理

    ③ 安全性:自定义网络模式可以帮助您更好地控制容器之间的通信,提高网络安全性

    ④ 性能:自定义网络模式可以优化容器之间的通信性能,减少不必要的网络开销

    缺点:

    ① 需要用户自行创建和配置网络,可能增加管理复杂性

    3、配置 docker 网络模式

    使用docker run创建Docker容器时,可以用 --net 或 --network 选项指定容器的网络模式 

    host模式--net=host容器和宿主机共享Network namespace
    container模式--net=container:NAME_or_ID多个容器共享一个Network namespace
    none模式--net=none容器有独立的Network namespace,但并没有对其进行任何网络设置,如分配veth pair 和网桥连接,配置IP等。
    bridge模式--net=bridge默认为该模式,可省略

    3.1 查看网络基础命令

    3.1.1 查看 docker 网络列表

    安装Docker时,它会自动创建三个网络,bridge(创建容器默认连接到此网络)、 none 、host

    1. #查看docker网络列表
    2. docker network ls 或 docker network list

     3.1.2 搜索指定网络模式的容器
    1. 格式:docker ps --filter "network=网络模式" 或者 docker network ls|grep 网络模式
    2. #如:docker ps --filter "network=bridge" #搜索bridge模式的容器
    3. #如:docker network ls|grep bridge

    3.1.3 查看容器的进程
    docker inspect -f '{{.State.Pid}}' 容器ID/容器名称   #查看指定容器的进程号

    3.1.4 查看容器信息(包含配置、环境、网关、挂载、cmd等信息)  
    docker inspect  容器ID/容器名

    3.1.5 查看网桥bridge信息
    brctl show

    3.2 配置 host 网络模式

    1. #创建名为nginx01的容器网络模式为host
    2. docker run -d --name nginx01 --network host nginx:latest

    docker inspect nginx01  #查看容器详细信息,包括配置、环境、网络模式等信息

    1. #查看host模式的容器
    2. docker ps --filter "network=host"

    1. docker inspect -f '{{.State.Pid}}' nginx01 #查看指定容器的进程号
    2. lsof -i:80 #查看80端口是否被host模式的nginx01容器的进程占用

    浏览器访问:172.16.12.10,查看是否能访问nginx

    3.3 配置 container 网络模式

    (1)先创建一个bridge模式的容器

    docker run -itd --name centos01 centos:7 /bin/bash

    1. #搜索bridge模式的容器,是否有centos01
    2. docker ps --filter "network=bridge"

    1. #查看容器进程号
    2. docker inspect -f '{{.State.Pid}}' centos01
    3. #查看容器的进程、网络、文件系统等命名空间编号
    4. ls -l /proc/9684/ns

    (2)创建 container 模式的容器centos02,共享centos01容器的网卡

    docker run -itd --name centos02 --net=container:centos01 centos:7 /bin/bash

    1. #查看centos02容器的网络模式是否是container
    2. docker inspect centos02 | grep NetworkMode

    1. #查看容器进程号
    2. docker inspect -f '{{.State.Pid}}' centos02
    3. #查看容器的进程、网络、文件系统等命名空间编号
    4. ls -l /proc/9967/ns

    观察可以发现两个容器的 net namespace 编号相同

    3.4 配置 none 网络模式

    1. #创建网络模式为 none 的centos03容器
    2. docker run -itd --name centos03 --network=none centos:7 /bin/bash

    1. #查看centos03容器的网络模式是否是node
    2. docker inspect centos03

    1. #搜索网络模式为none的容器
    2. docker ps --filter "network=none"

    3.5 配置 bridge 网络模式

    bridge模式是docker的默认网络模式,不用--net参数,就是bridge模式

    1. #创建网络模式为 bridge(默认模式) 的centos04容器,不用--net参数指定
    2. docker run -itd --name centos04 centos:7 /bin/bash

    1. #查看centos04容器的网络模式是否是bridge
    2. docker inspect centos04

    1. #搜索网络模式为bridge的容器
    2. docker ps --filter "network=bridge"

     3.6 配置 user-defined network 模式(自定义网络)

    1. #直接使用bridge模式,是无法支持指定IP运行docker的,例如执行以下命令就会报错
    2. docker run -itd --name centos05 --network bridge --ip 172.17.0.100 centos:7 /bin/bash

    (1)创建自定义网络

    1. #可以先自定义网络,再使用指定IP运行docker
    2. docker network create --subnet=172.20.0.0/16 --opt "com.docker.network.bridge.name"="docker1" mynetwork
    3. #docker1 为执行 ifconfig -a 命令时,显示的网卡名,如果不使用 --opt 参数指定此名称,那你在使用 ifconfig -a 命令查看网络信息时,看到的是类似 br-110eb56a0b22 这样的名字,这显然不怎么好记
    4. #mynetwork 为执行 docker network list 命令时,显示的bridge网络模式名称

    brctl show   #查看网桥信息

    (2) 使用指定IP创建并运行docker

    docker run -itd --name centos05 --net mynetwork --ip 172.20.0.100 centos:7 /bin/bash

    1. #查看centos05容器的IP是否是我们设置的172.20.0.100
    2. docker inspect centos05

    二、Docker 资源控制

    1、CPU 资源控制

    Control Groups (cgroups):

    cgroups,是一个非常强大的linux内核工具,他不仅可以限制被 namespace 隔离起来的资源, 还可以为资源设置权重、计算使用量、操控进程启停等等。 所以 cgroups(Control groups)实现了对资源的配额和度量

    cgroups有四大功能:

    • 资源限制:可以对任务使用的资源总额进行限制
    • 优先级分配:通过分配的cpu时间片数量以及磁盘IO带宽大小,实际上相当于控制了任务运行优先级
    • 资源统计:可以统计系统的资源使用量,如cpu时长,内存用量等
    • 任务控制:cgroup可以对任务执行挂起、恢复等操作

    1.1 设置CPU使用率上限 

    • Linux通过CFS(Completely Fair Scheduler,完全公平调度器)来调度各个进程对CPU的使用。CFS默认的调度周期是100ms
    • 我们可以设置每个容器进程的调度周期,以及在这个周期内各个容器最多能使用多少 CPU 时间
    • 使用 --cpu-period 即可设置调度周期,使用 --cpu-quota 即可设置在每个周期内容器能使用的CPU时间。两者可以配合使用
    • CFS 周期的有效范围是 1ms~1s,对应的 --cpu-period 的数值范围是 1000~1000000。 周期100毫秒 
    • 而容器的 CPU 配额必须不小于 1ms,即 --cpu-quota 的值必须 >= 1000
    1. #创建并运行一个centos06容器
    2. docker run -itd --name centos06 centos:7 /bin/bash
    3. #切换到指定 Docker 容器的 CPU 控制组目录
    4. cd /sys/fs/cgroup/cpu/docker/a4a05d1b6b69644fec398777baa35daeb82606c4cc540d65be0d3e2259737f27/
    5. #/sys/fs/cgroup/cpu/docker/: 这是 Docker 容器的 CPU 控制组目录所在的路径。控制组是 Linux 内核提供的一种机制,用于对进程组进行资源控制和管理

    Docker 容器的 CPU 控制组目录说明
    cgroup.clone_children用于控制是否允许子 cgroup 继承父 cgroup 的配置。如果设置为 1,则子 cgroup 将继承父 cgroup 的配置;如果设置为 0,则子 cgroup 将不继承父 cgroup 的配置
    cgroup.procs列出了当前在该 cgroup 中运行的进程(任务)的 PID。可以通过向这个文件写入 PID,将进程移动到该 cgroup 中
    cpuacct.usage包含了容器在 CPU 上消耗的总时间,以纳秒为单位。可以用来监视容器在 CPU 上的实际使用情况
    cpu.cfs_period_us用于设置 CPU CFS(Completely Fair Scheduler)周期的长度,单位是微秒。决定了任务在一个周期内能够使用的 CPU 时间
    cpu.rt_period_us用于设置实时调度任务的周期长度,单位是微秒。用于限制实时任务在一个周期内的执行时间
    cpu.shares用于设置容器相对于其他容器的 CPU 分配权重。通过调整这个值,可以影响容器在 CPU 分配上的优先级
    notify_on_release用于控制当 cgroup 中的最后一个任务退出时是否通知。如果设置为 1,则当 cgroup 中的最后一个任务退出时会收到通知;如果设置为 0,则不会收到通知
    cgroup.event_control用于控制 cgroup 事件的通知。可以用来注册和取消事件通知
    cpuacct.stat包含了有关 CPU 账户的统计信息,例如用户态和内核态的 CPU 时间消耗
    cpuacct.usage_percpu包含了每个 CPU 核心上容器消耗的 CPU 时间,以纳秒为单位。可以用来查看每个 CPU 核心上的 CPU 使用情况
    cpu.cfs_quota_us用于设置容器在一个周期内能够使用的 CPU 时间配额,单位是微秒。超过这个配额的部分将被限制
    cpu.rt_runtime_us用于设置实时调度任务的运行时间配额,单位是微秒。用于限制实时任务的运行时间
    cpu.stat包含了有关 CPU 使用情况的统计信息,例如 CPU 时间消耗、时间片的使用情况等
    tasks列出了当前在该 cgroup 中运行的进程(任务)的 PID。可以通过向这个文件写入 PID,将进程移动到该 cgroup 中
    1. #查看容器在一个周期内能够使用的 CPU 时间配额
    2. cat cpu.cfs_quota_us
    3. #默认值 -1,表示该容器没有被限制在一个周期内可以使用的 CPU 时间配额
    4. #如果设为50000,表示占用50000/100000=50%的CPU
    5. #查看CPU CFS 调度器的周期长度,单位也是微秒(us)
    6. cat cpu.cfs_period_us
    7. #CPU CFS 调度器的周期长度为100毫秒。在一个周期内,容器的进程可以使用的 CPU 时间总量受限于这个周期的长度

    (1)设置50%的比例分配CPU使用时间上限

    1. echo 50000 > cpu.cfs_quota_us
    2. cat cpu.cfs_quota_us

    (2)进入到容器中,进行CPU压力测试

    1. #进入到centos06的容器内
    2. docker exec -it centos06 /bin/bash
    3. #编写压力测试的循环脚本
    4. vi cpu.sh
    5. #!/bin/bash
    6. i=0
    7. while true
    8. do
    9. let i++
    10. done
    11. #添加执行权限,并执行脚本
    12. chmod +x cpu.sh
    13. source cpu.sh

    (3)查看CPU占用资源 

    top     #查看这个压力测试的循环脚本占了50%左右的CPU资源

    docker stats  #查看容器占用的系统资源信息

    注:

    如果不对 cpu.cfs_quota_us 进行限制,则默认值为-1的情况下,进行压力测试,CPU资源使用率接近100%

    1. 总结:
    2. 设置设置50%的比例分配CPU使用时间上限的方法
    3. 方法一:创建并运行容器时指定分配CPU使用时间的比例进行限额
    4. docker run -itd --name test --cpu-quota 50000 centos:7 /bin/bash
    5. 方法二:进入Docker容器的 CPU 控制组目录,并更改cpu.cfs_quota_us文件内容为指定分配CPU使用时间的比例来进行限额
    6. cd /sys/fs/cgroup/cpu/docker/a4a05d1b6b69644fec398777baa35daeb82606c4cc540d65be0d3e2259737f27/
    7. echo 50000 > cpu.cfs_quota_us

    1.2 设置CPU资源占用比(设置多个容器时才有效)

    Docker 通过 --cpu-shares 指定 CPU 份额,默认值为1024,值为1024的倍数

    虚拟机修改成单核CPU才有明显的效果

    (1)创建并运行两个容器为 c1 和 c2,并设置容器的权重,使得c1和c2的CPU资源占比为1/3和2/3

    1. #创建并运行两个容器为 c1 和 c2,若只有这两个容器,设置容器的权重,使得c1和c2的CPU资源占比为1/3和2/3
    2. docker run -itd --name c1 --cpu-shares 512 centos:7
    3. docker run -itd --name c2 --cpu-shares 1024 centos:7

    (2)分别进入这两个容器,并进行压力测试 

    1. #分别进入这两个容器,并进行压力测试
    2. docker exec -it c1 /bin/bash #进入到c1容器内
    3. yum install -y epel-release #安装额外源
    4. yum install -y stress #安装stress压力测试工具
    5. stress -c 4 #产生四个进程,每个进程都反复不停的计算随机数的平方根
    6. docker exec -it c2 /bin/bash ##进入到c2容器内
    7. yum install -y epel-release
    8. yum install -y stress
    9. stress -c 4

    (3)查看容器运行状态(动态更新)

    docker stats  #查看容器占用的系统资源信息

    1.3 设置容器绑定指定的CPU

    先分配虚拟机4个CPU核数

    (1)创建并运行bak容器绑定CPU1和CPU3

    docker run -itd --name bak --cpuset-cpus 1,3 centos:7 /bin/bash

    (2) 进入容器,进行压力测试

    1. #进入容器,进行压力测试
    2. docker exec -it bak /bin/bash #进入到c1容器内
    3. yum install -y epel-release #安装额外源
    4. yum install -y stress #安装stress压力测试工具
    5. stress -c 4 #产生四个进程,每个进程都反复不停的计算随机数的平方根

    (3)使用top查看CPU绑定情况

    2、对内存使用的限制

    2.1 使用--memory标志

    在Docker中,可以使用内置的功能来限制容器可以使用的内存量

    可以在运行容器时使用--memory标志来设置容器可以使用的内存量,单位可以是字节、千字节、兆字节、千兆字节或者吉字节

    1. #-m(--memory=) 选项用于限制容器可以使用的最大内存
    2. docker run -itd --name nc -m 512m centos:7 /bin/bash
    3. #限制新容器nc的最大使用内存为512MB

    docker stats  #查看容器占用的系统资源信息

    2.2 使用--memory-swap标志

    --memory-swap标志可以用来设置容器可以使用的交换空间大小。强调一下,--memory-swap 是必须要与 --memory 一起使用的

    正常情况下,--memory-swap 的值包含容器可用内存和可用 swap。所以 -m 300m --memory-swap=1g 的含义为:容器可以使用 300M 的物理内存,并且可以使用 700M(1G - 300)的 swap

    • 如果 --memory-swap 设置为 0 或者 不设置,则容器可以使用的 swap 大小为 -m 值的两倍
    • 如果 --memory-swap 的值和 -m 值相同,则容器表示禁用交换空间swap
    • 如果 --memory-swap 值为 -1,它表示容器程序使用的内存受限,而可以使用的 swap 空间使用不受限制(宿主机有多少 swap 容器就可以使用多少)
    1. docker run -itd --name swp -m 200m --memory-swap=1g nginx:latest --vm 1 --vm-bypes 100m
    2. #--vm 1:启动1个内容工作线程
    3. #--vm-bypes:每个线程分配100M

    3、对磁盘IO配额控制(blkio)的限制

    1. --device-read-bps:限制某个设备上的读速度bps(数据量),单位可以是kb、mb(M)或者gb
    2. 例:docker run -itd --name test9 --device-read-bps /dev/sda:1M  centos:7 /bin/bash
    3. --device-write-bps : 限制某个设备上的写速度bps(数据量),单位可以是kb、mb(M)或者gb
    4. 例:docker run -itd --name test10 --device-write-bps /dev/sda:1mb centos:7 /bin/bash
    5. --device-read-iops :限制读某个设备的iops(次数)
    6.  
    7. --device-write-iops :限制写入某个设备的iops(次数)

    3.1 限制容器的读写速度 

    此测试只能在旧版本的docker有效,如20.10.17版本,新版本可能会有问题

    1. #创建容器,并同时限制读取和写入速率
    2. docker run -it --name wre --device-read-bps=/dev/sda:5MB --device-write-bps=/dev/sda:1MB centos:7 /bin/bash
    1. #通过dd来验证写速度
    2. dd if=/dev/zero of=test.out bs=1M count=10 oflag=direct                
    3. #添加oflag参数以规避掉文件系统cache

    3.2 限制容器的读写次数

    用于限制容器中指定设备的每秒读取和写入操作数 (IOPS)

    1. #限制读取和写入次数,指定了对 /dev/sda 设备的最大读取 IOPS 为 300,指定了对 /dev/sda 设备的最大写入 IOPS 为 300
    2. docker run -it --name cis --device-read-iops=/dev/sda:300 --device-read-iops=/dev/sda:300 centos:7 /bin/bash

    三、Docker 故障造成大量日志导致磁盘爆满故障

    处理Docker故障导致磁盘爆满的问题通常需要一系列步骤

     (1)停止Docker服务

    首先,停止Docker服务以阻止持续写入造成的进一步磁盘使用

    docker stop 容器ID/名称

    (2)删除不必要的容器和镜像

    删除不再需要的容器、镜像和数据卷,以释放磁盘空间

    1. #删除所有已停止的容器
    2. docker container prune
    3. #删除不再使用的镜像
    4. docker image prune
    5. #删除未被任何容器使用的数据卷
    6. docker volume prune
    7. #清理docker占用的磁盘空间
    8. docker system prune -a
    9. #可以用于清理磁盘,删除关闭的容器、无用的数据卷和网络

    (3)清理日志文件

    1. #编写脚本,清除日志
    2. vim /opt/clean.sh
    3. #!/bin/bash
    4. logs=$(find /var/lib/docker/containers/ -name *-json.log*)
    5. for log in $logs
    6. do
    7. cat /dev/null > $log
    8. done

    (4)设置docker日志文件数量及每个日志大小

    1. #设置docker日志文件数量及每个日志大小
    2. vim /etc/docker/daemon.json
    3. {
    4. "registry-mirrors": ["http://f613ce8f.m.daocloud.io"],
    5. "log-driver": "json-file", #日志格式
    6. "log-opts": { "max-size" : "500m", "max-file" : "3"}
    7. #日志的参数最大500M,最大容器中有三个日志文件,每个日志文件大小是500M
    8. }
    9. #修改完需要重新加载
    10. systemctl daemon-reload

    (5)定期清理

    建立计划任务:crontab -e,设定时间执行清除日志的脚步

    1. crontab -e
    2. * */3 1 * * /usr/bin/bash /opt/clean.sh

    (6)监控和预防措施

    最后,确保实施监控和预防措施以避免未来的磁盘爆满问题。可以使用监控工具来追踪磁盘使用情况,并且可以设置警报,以便在磁盘使用接近极限时采取行动

    完成这些步骤后,您可以重新启动Docker服务,并且应该能够恢复正常运行

    (1)模拟新建容器一直在后台持续运行占用资源 

    1. #在后台持续运行 docker run 创建的容器
    2. #需要在 docker run 命令之后添加 -d 选项让 Docker 容器以守护形式在后台运行。并且容器所运行的程序不能结束
    3. docker run -itd centos:7 /usr/bin/bash -c "while true;do echo hello;done"

    1. #切换至存放docker运行中的容器的相关数据的目录
    2. cd /var/lib/docker/containers/
    3. #查看文件所占磁盘空间的大小
    4. du -sh *

     此时CPU利用率过高,会导致卡顿等问题

    (2)停止运行有问题的容器

    docker stop a5e663466278

    (3) 清理日志文件

    1. #编写脚本,清除日志
    2. vim /opt/clean.sh
    3. #!/bin/bash
    4. logs=$(find /var/lib/docker/containers/ -name *-json.log*)
    5. for log in $logs
    6. do
    7. cat /dev/null > $log
    8. done
    9. #添加执行权限,并执行脚本
    10. chmod +x /opt/clean.sh
    11. . /opt/clean.sh

    四、总结

    1、Docker 网络模式

    • host:容器使用宿主机的网络直接公开服务

    这意味着如果你在容器中运行一个web服务,那么它就直接绑定到主机的网络接口上,而不是通过docker进行任何网络转发

    与宿主机共享网络名称空间 

    • container

    这种模式允许容器去共享另一个容器网络命名空间,这说明两个容器可以相同的网络接口和IP地址,他们共享的是同一网络命名空间

    多个容器之间共享一个network namespace(命名空间) 

    • none:是最简单的网络模式

    此网络模式表示将容器拥有自己的网路命名空间,但不会进行任何网络配置,这实际给了用户完全的自主权来给自己配置容器的网络

    自闭空间 

    • bridge:默认的网络模式

    每个新创建的容器都将该网络分配一个IP地址,此网络模式允许所有docker容器之间以及docker宿主机之间进行互相通信

    默认模式,通过VETH对连接容器docker0网桥,网桥分配给容器IP,同时docker0作为局域网内容器的网关,最后与宿主机网卡进行通讯 

    • user-defined network:自定义网络

    docker允许用户创建自己的定义的网络,用户可以定义的网络范围、子网、路由等参数,这种类型网络使用用户可以更好地对容器网络进行控住和隔离(生产业务需求;注:根据甲方指定或领导指定)

     根据业务需求指定静态IP地址

    2、Docker 资源控制

    2.1 CPU资源控制

    control groups:是一个1inux内核的一个特性,用于限制记录和隔离进程组系统资源使用(cpu、内存、磁盘I/0等)

    cpu-period 周期:指的是CPU在给与当前管理 控制容器的分配资源时 ,cpu 分配周期默认1s,此配置可以在运行时直接指定

    cpu-quota(cpu 配额):直接限制了cgroups可以使用cpu的时间,如果设置了cgroup的配额100000us(微秒),那么在每个100ms(毫秒)的是时间窗口 cgroups是最多只能使用 100000us(微秒)的cpu 时间

    cpuset-cpu:指定容器仅能使用指定CPU,按照CPU的下标来表示

    2.2 内存资源限制

    --memory设置容器可以使用的内存量,单位可以是字节、千字节、兆字节、千兆字节或者吉字节

    --memory-swap可以用来设置容器可以使用的交换空间大小。强调一下,--memory-swap 是必须要与 --memory 一起使用的

    2.3 磁盘IO配额限制

    --device-read-bps:限制某个设备上的读速度bps(数据量),单位可以是kb、mb(M)或者gb
    例:docker run -itd --name test9 --device-read-bps /dev/sda:1M  centos:7 /bin/bash

    --device-write-bps : 限制某个设备上的写速度bps(数据量),单位可以是kb、mb(M)或者gb
    例:docker run -itd --name test10 --device-write-bps /dev/sda:1mb centos:7 /bin/bash

    --device-read-iops :限制读某个设备的iops(次数)
     
    --device-write-iops :限制写入某个设备的iops(次数)

  • 相关阅读:
    教程图文详解 - 下一代互联网(第七章)
    [微前端实战]---037 后端服务
    五种数据提交方式的优化
    因为内存溢出,我差点被优化
    区间映射算法
    在 Windows 上利用Qwen大模型搭建一个 ChatGPT 式的问答小助手
    Parsing R-CNN(CVPR2019)-人体实例分析论文解读
    论文阅读-《MHFormer: Multi-Hypothesis Transformer for 3D Human Pose Estimation》
    算法常见知识点(持续更新)
    Nginx 在 Linux 系统上安装 - 细节狂魔
  • 原文地址:https://blog.csdn.net/m0_71815887/article/details/138156906