Docker容器生产实践1——永远设置容器内存限制

简介: 背景在默认情况下,docker容器并不会对容器内部进程使用的内存大小进行任何限制。对于PaaS系统而言,或者对于直接使用docker的用户而言,这非常危险。

背景

在默认情况下,docker容器并不会对容器内部进程使用的内存大小进行任何限制。对于PaaS系统而言,或者对于直接使用docker的用户而言,这非常危险。如果哪个业务容器,出现了内存泄漏;那么它可能会危害到整个主机系统,导致业务app容器所在的主机出现oom。本文将介绍着眼于docker对内存资源的使用,解释背后的原理。同时也给出k8s上如何配置内存限制的方法。

docker run、create时刻对容器使用内存大小进行限制

-m硬限制容器使用的内存

通过下面参数可以为容器设置一个内存使用量硬大小,当超出这个大小时刻,linux系统会根据配置设置决定是否进入oom-killer状态。
docker run --name zxy-docker -m 1g -it busybox bash
单位为:b,k,m和g
如果设置了-m参数,通常情况下如果容器使用内存量超过了设置的硬水线,那么linux的oom-killer触发,它将根据oom-score对容器内部进程进行oom kill。但是不影响宿主机上其他进程。

--oom-kill-disable

这个参数设置一定需要在容器run或者create过程中使用了-m参数才可以设置。设置了-m参数,如果容器使用内存超限了,那么oom-kill将触发。如果设置了--oom-kill-disable,那么容器不会oom,但是此时容器内部申请内存的进程将hang,直到他们可以申请到内存(容器内其他进程释放了内存)
绝对不要在没有使用-m的时候设置--oom-kill-disable 因为这会影响到宿主机的oom-killer

背后的原理

docker 设置容器的-m是通过设置memory cgoup的memory.limit_in_bytes实现的。在没有设置-m的时候这个值为-1,表示容器使用的内存不受限制。
例如:
`bash>docker run --name zxy-memorylimit -it -m 1g docker-build:12.06 bash
bash>docker inspect zxy-memorylimit|grep -i pid
“Pid”:24360

bash>cat /proc/24360/cgroup|grep memory
9:memory:/docker/xxxxx
bash>cd /sys/fs/cgroups/memory/docker/xxxx
bash> cat memory.limit_in_bytes
1073741824`

--oom-kill-disable参数实际设置的就是这是了同级目录之下的memory.oom_control,设置此参数就相当于做了如下动作
bash> echo 1 >memory.oom_control
对linux memory cgroup感兴趣的朋友可以参考:
https://segmentfault.com/a/1190000008125359 一文

--memory-reservation 软限制容器使用的内存

在上一节中,我们介绍了-m硬限制容器使用的内存资源。一旦设置了这个-m参数,那么容器内进程使用量超过这个数值,就会被杀或者hang住。docker还提供了一种soft limit就是--memory-reservation,单位和-m一致。当设置了这个参数以后,如果宿主机系统内存不足,有新的内存请求时刻,那么linux会尝试从设置了此参数的容器里回收内存,回收的办法就是swap了。那么如果此容器还在继续使用内存,那么此容器会遇到很大的性能下降
通常实践是设置--memory-reservevation 的值小于-m的值。

背后的原理

和-m参数一致,此参数docker也是借助于memory cgroup的memory.soft_limit_in_bytes 实现。

其他内存资源参数

  • --memory-swap
    配置容器可以设置的swap大小。此值为-m值加上能达到的swap区大小,例如--memory-swap = 500M
    -m =300M,意味着真正的swap大小可以的到200M。默认情况下容器可以得到最大swap大小为-m参数设置的两倍,此参数设置为0,为无效参数。如果--m和--memory-swap相等,相当于关闭容器的swap。值-1表示swap大小为不限
  • --memory-swappiness
    配置容器的swappiness属性,从0到100。0表示无论何种情况下都不要启动swap,100表示只要有可能就启动swap。
    此参数和系统的
    /proc/sys/vm/swappiness
    含义一致,不过它设置的容器所在memory cgroup的swappiness。
    默认情况下容器的此值继承自主机侧的swappiness配置。对于centos系统和ubuntu系统,内存充裕可以设置为10.
    swappiness设置的是匿名页(anonymous page,也就是malloc和mmap以map_anonymous方式申请的内存)是否愿意交换出去

docker做了什么

docker做的工作实际上是由runc完成的,docker 创建的hostconfig.json文件(也就是oci接口文件)中,有如下字段描述-m,--memory-reservation等内存资源限制参数:
memory MemoryReservation MemorySwap MemorySwappiness

docker生产实践

  • 永远需要设置-m
  • 不要轻易设置--oom-kill-disable,memory-swappiness,memory-swap和memory-reservation,因为一半情况下,你不太容易理解它们真正如何作用于系统。

k8s如何使用docker限制内存的参数

下文节选自https://mp.weixin.qq.com/s/j2FfqUHSRTzczNcfPuwRQw

K8s资源限制是通过每个容器containerSpec的resources字段进行设置的,它是v1版本的ResourceRequirements类型的API对象。每个指定了"limits"和"requests"的对象都可以控制对应的资源。目前只有CPU和内存两种资源。大多数情况下,deployment、statefulset、daemonset的定义里都包含了podSpec和多个containerSpec。这里有个完整的v1资源对象的yaml格式配置:
`resources:
requests:
cpu: 50m
memory: 50Mi
limits:
cpu: 100m
memory: 100Mi

`

其中limits节限制memory设置的就是docker 容器的-m,而且k8s仅仅使用了-m参数其他参数都没有使用。

相关实践学习
深入解析Docker容器化技术
Docker是一个开源的应用容器引擎,让开发者可以打包他们的应用以及依赖包到一个可移植的容器中,然后发布到任何流行的Linux机器上,也可以实现虚拟化,容器是完全使用沙箱机制,相互之间不会有任何接口。Docker是世界领先的软件容器平台。开发人员利用Docker可以消除协作编码时“在我的机器上可正常工作”的问题。运维人员利用Docker可以在隔离容器中并行运行和管理应用,获得更好的计算密度。企业利用Docker可以构建敏捷的软件交付管道,以更快的速度、更高的安全性和可靠的信誉为Linux和Windows Server应用发布新功能。 在本套课程中,我们将全面的讲解Docker技术栈,从环境安装到容器、镜像操作以及生产环境如何部署开发的微服务应用。本课程由黑马程序员提供。     相关的阿里云产品:容器服务 ACK 容器服务 Kubernetes 版(简称 ACK)提供高性能可伸缩的容器应用管理能力,支持企业级容器化应用的全生命周期管理。整合阿里云虚拟化、存储、网络和安全能力,打造云端最佳容器化应用运行环境。 了解产品详情: https://www.aliyun.com/product/kubernetes
目录
相关文章
|
10月前
|
Kubernetes Docker Python
Docker 与 Kubernetes 容器化部署核心技术及企业级应用实践全方案解析
本文详解Docker与Kubernetes容器化技术,涵盖概念原理、环境搭建、镜像构建、应用部署及监控扩展,助你掌握企业级容器化方案,提升应用开发与运维效率。
1288 108
|
8月前
|
监控 Kubernetes 安全
还没搞懂Docker? Docker容器技术实战指南 ! 从入门到企业级应用 !
蒋星熠Jaxonic,技术探索者,以代码为笔,在二进制星河中书写极客诗篇。专注Docker与容器化实践,分享从入门到企业级应用的深度经验,助力开发者乘风破浪,驶向云原生新世界。
792 51
还没搞懂Docker? Docker容器技术实战指南 ! 从入门到企业级应用 !
|
8月前
|
NoSQL 算法 Redis
【Docker】(3)学习Docker中 镜像与容器数据卷、映射关系!手把手带你安装 MySql主从同步 和 Redis三主三从集群!并且进行主从切换与扩容操作,还有分析 哈希分区 等知识点!
Union文件系统(UnionFS)是一种**分层、轻量级并且高性能的文件系统**,它支持对文件系统的修改作为一次提交来一层层的叠加,同时可以将不同目录挂载到同一个虚拟文件系统下(unite several directories into a single virtual filesystem) Union 文件系统是 Docker 镜像的基础。 镜像可以通过分层来进行继承,基于基础镜像(没有父镜像),可以制作各种具体的应用镜像。
856 6
|
8月前
|
监控 Linux 调度
【赵渝强老师】Docker容器的资源管理机制
本文介绍了Linux CGroup技术及其在Docker资源管理中的应用。通过实例演示了如何利用CGroup限制应用程序的CPU、内存和I/O带宽使用,实现系统资源的精细化控制,帮助理解Docker底层资源限制机制。
781 6
|
10月前
|
缓存 Ubuntu Docker
Ubuntu环境下删除Docker镜像与容器、配置静态IP地址教程。
如果遇见问题或者想回滚改动, 可以重启系统.
606 16
|
10月前
|
传感器 数据采集 监控
Python生成器与迭代器:从内存优化到协程调度的深度实践
简介:本文深入解析Python迭代器与生成器的原理及应用,涵盖内存优化技巧、底层协议实现、生成器通信机制及异步编程场景。通过实例讲解如何高效处理大文件、构建数据流水线,并对比不同迭代方式的性能特点,助你编写低内存、高效率的Python代码。
366 0
|
10月前
|
边缘计算 算法 Java
Java 绿色计算与性能优化:从内存管理到能耗降低的全方位优化策略与实践技巧
本文探讨了Java绿色计算与性能优化的技术方案和应用实例。文章从JVM调优(包括垃圾回收器选择、内存管理和并发优化)、代码优化(数据结构选择、对象创建和I/O操作优化)等方面提出优化策略,并结合电商平台、社交平台和智能工厂的实际案例,展示了通过Java新特性提升性能、降低能耗的显著效果。最终指出,综合运用这些优化方法不仅能提高系统性能,还能实现绿色计算目标,为企业节省成本并符合环保要求。
313 0