介绍

将容器化应用程序部署到 Kubernetes 集群时,由于从 registry 中提取必要的容器镜像需要时间,因此可能会出现延迟。在应用程序需要横向扩展或处理高速实时数据的情况下,这种延迟尤其容易造成问题。幸运的是,有几种工具和策略可以改善 Kubernetes 中容器镜像的可用性和缓存。在本篇文章中,我们将全面介绍这些工具和策略,包括 kube-fledged、kuik、Kubernetes 内置的镜像缓存功能、本地缓存以及监控和清理未使用的镜像。

前提

将工作负载部署到 Kubernetes 时,某个 Pod 中的容器自然会基于 OCI 容器镜像。这些镜像可以从多种私有/公共存储库中提取。Kubernetes 会在拉取镜像的每个节点上本地缓存镜像,以便其他 Pod 使用相同的镜像。

然而在大多数用例中,这还不够。如今,大多数云 Kubernetes 集群都需要自动扩展,并根据客户的使用情况动态分配节点。如果多个节点必须多次调用同一个镜像怎么办?如果这个镜像很重,那可能需要几分钟时间。在应用自动伸缩的情况下,需要相对较长的时间。

现有解决方案

预期的解决方案需要在 Kubernetes 上建立一个缓存层,这样 Kubernetes 就有了一个集中的镜像缓存,所有节点都能从其中 "提取 "镜像。但是,由于缓存需要非常快,因此缓存解决方案需要位于 Kubernetes 内部,所有节点都应该以最快的延迟到达缓存。

要解决从 registry 中提取容器镜像的延迟问题,广泛使用的方法是在集群内运行 registry 镜像。

两种广泛使用的解决方案是集群内自托管 registry推送缓存 (pull-through cache)

在前一种解决方案中,本地 registry 在 Kubernetes 集群内运行,并在容器运行时配置为镜像 registry。任何镜像拉取请求都会指向集群内的 registry。在后一种解决方案中,容器镜像的缓存直接在工作节点上构建和管理。

其他现有解决方案包括使用 kuik 等可靠的缓存解决方案、在 Kubernetes 中启用镜像缓存、使用本地缓存、优化容器镜像构建以及监控和清理未使用的镜像。

Harbor

Harbor 是一个 CNCF 毕业项目,它的功能是容器 registry ,但最重要的是它还是一个推送代理缓存 (Pull Through Proxy Cache)

推送代理缓存是一种缓存机制,旨在优化容器 registry 环境中容器镜像的分发和检索。它充当用户端(如容器运行时或构建系统)和上游容器 registry 之间的中介。

当用户端请求容器镜像时,直通式代理缓存会检查它是否已经拥有所请求镜像的本地副本。如果镜像存在,代理缓存会直接将其提供给客户端,而无需从上游 registry 下载。这样可以减少网络延迟并节省带宽。

如果本地缓存中没有请求的镜像,代理缓存就会充当普通代理,将请求转发到上游 registry。然后,代理缓存会从 registry 中检索镜像,并将其提供给客户端。此外,代理缓存还会在其本地缓存中存储一份镜像副本,以备将来请求之用

kube-fledged

kube-fledged 是一个 K8s 附加组件或 operator,用于直接在 Kubernetes 集群的工作节点上创建和管理容器镜像缓存。它允许用户定义镜像列表,并将这些镜像缓存到哪个工作节点上。kube-fledged 提供了 CRUD API 来管理镜像缓存的生命周期,并支持多个可配置参数,以便根据个人需求定制功能。

kube-fledged 是为管理 Kubernetes 中的镜像缓存而设计和构建的通用解决方案。虽然主要用例是实现 Pod 的快速启动和扩展,但该解决方案支持下列的各种实例。

工作原理

kube-fledged 定义了一种名为 “ImageCache” 的自定义资源,并实现了一个自定义控制器(名为 kubefledged-controller)。用户可以使用 kubectl 命令创建和删除 ImageCache 资源

Kubernetes-image-puller

为了缓存镜像,Kubernetes Image Puller 会在所需集群上创建一个 Daemonset,然后在集群中的每个节点上创建一个 pod,其中包含一个命令 sleep 720h 的容器列表。这样就能确保集群中的所有节点都缓存了这些镜像。使用的 sleep 二进制基于 golang(请参阅 Scratch Images:https://github.com/che-incubator/kubernetes-image-puller#scratch-images)。

我们还会定期检查守护进程集的健康状况,并在必要时重新创建它。

可以通过 Helm 或处理和应 OpenShift 模板来部署应用程序。此外,OperatorHub 上还有一个社区支持的 Operator。

kubernetes-image-puller 部署了大量容器(每个镜像和每个节点一个容器,缓存机制使用 daemonset),以实现缓存功能。

举个例子:缓存中有 5 个节点和 10 个镜像,而我们在集群中已经有 50 个容器专门用于缓存功能。

Tugger

Tugger 使用单一配置文件,通过其 Helm 文件值定义。它不允许我们将“系统”配置(例如:从缓存系统中排除特定图片)和 “用户”配置分开。

Tugger 使用通过 Helm 文件值定义的单一配置文件。它不允许分离 "系统 "配置,比如从缓存系统中排除特定镜像,和 "用户 "配置。

kube-image-keeper (kuik)

kube-image-keeper(又名 kuik,类似于 “quick”)是 Kubernetes 的容器镜像缓存系统。它能将 pod 使用的容器镜像保存在自己的本地 registry 中,这样在原始镜像不可用时,这些镜像仍可使用。

工作原理

创建 pod 时,kuik 的 webhook 会即时重写其镜像,并添加 localhost:{port}/ 前缀(默认 port 为 7439,可配置)。

localhost:{port} 上有一个镜像代理,它从 kuik 的缓存 registry (当镜像已被缓存时)或直接从原始 registry (当镜像尚未被缓存时)提供镜像。

控制器负责监控 pod,当发现新的镜像时,就会为这些镜像创建 CachedImage 自定义资源。另一个控制器会监测这些 CachedImage 自定义资源,并相应地将镜像从源 registry 复制到 kuik 的缓存 registry 中。

架构和组件

在 kuik 的命名空间中,您可以找到:

  • 运行 kuik 控制器的 Deployment
  • 运行 kuik 镜像代理的 DaemonSet
  • 当该组件在 HA 模式下运行时,会使用 StatefulSet 来运行 kuik 的镜像缓存,而不是Deployment

运行镜像缓存显然需要一定的磁盘空间(请参考 Garbage collection and limitations:https://github.com/enix/kube-image-keeper#garbage-collection-and-limitations)。除此之外,就计算资源而言,kuik 组件是相当轻量级的。这显示了默认设置下的 CPU 和 RAM 使用情况,其中两个控制器处于 HA 模式:

$ kubectl top pods
NAME CPU(cores) MEMORY(bytes)
kube-image-keeper-0 1m 86Mi
kube-image-keeper-controllers-5b5cc9fcc6-bv6cp 1m 16Mi
kube-image-keeper-controllers-5b5cc9fcc6-tjl7t 3m 24Mi
kube-image-keeper-proxy-54lzk 1m 19Mi

Warm-image

WarmImage CRD 获取镜像参考,并将其预取到集群中的每个节点上。

要在集群中安装这一自定义资源,只需运行:

# Install the CRD and Controller.
curl https://raw.githubusercontent.com/mattmoor/warm-image/master/release.yaml \
| kubectl create -f -

或者,您也可以 git clone 该仓库并运行:

# Install the CRD and Controller.
kubectl create -f release.yaml

结论

在这篇文章中,我们向您展示了如何通过在节点上缓存镜像来加快 Pod 的启动速度。通过在 kubernetes 集群的工作节点上预取容器镜像,您可以显著缩短 Pod 的启动时间,即使是大型镜像,也可以缩短到几秒钟。这项技术能让运行机器学习、仿真、数据分析和代码构建等工作负载的客户受益匪浅,提高容器启动性能和整体工作负载效率。

由于无需额外管理基础设施或 Kubernetes 资源,这种方法为解决基于 Kubernetes 的环境中容器启动缓慢的问题提供了一种经济高效的解决方案。

容器镜像加速指南:探索 Kubernetes 缓存最佳实践的更多相关文章

  1. 在 Kubernetes 容器集群,微服务项目最佳实践

    转载自:https://mp.weixin.qq.com/s/WYu3gDwKKf06f_FYbO9YRg 本文主要介绍我个人在使用 Kubernetes 的过程中,总结出的一套「Kubernetes ...

  2. Kubernetes Deployment 最佳实践

    零.示例 首先给出一个 Deployment+HPA+ PodDisruptionBudget 的完整 demo,后面再详细介绍其中的每一个部分: apiVersion: apps/v1 kind: ...

  3. Kubernetes YAML最佳实践和策略

    Kubernetes工作负载最常用YAML格式的文件来定义. YAML的问题之一就是很难描述清单文件之间的约束或关系. 如果你希望检查是否已从受信任的注册表中提取部署到群集中的所有映像,该怎么办? 如 ...

  4. 探索云数据库最佳实践 阿里云开发者大会数据库专场邀你一起Code up!

    盛夏.魔都.科技 三者在一起有什么惊喜? 7月24日,阿里云峰会·上海——开发者大会将在上海世博中心盛大启程,与未来世界的开发者们分享数据库.云原生.开源大数据等领域的技术干货,共同探讨前沿科技趋势, ...

  5. vue项目缓存最佳实践

    需求 在开发vue的项目中有遇到了这样一个需求:一个视频列表页面,展示视频名称和是否收藏,点击进去某一项观看,可以收藏或者取消收藏,返回的时候需要记住列表页面的页码等状态,同时这条视频的收藏状态也需要 ...

  6. [转载]三小时学会Kubernetes:容器编排详细指南

    原翻译by梁晓勇 原英文:Learn Kubernetes in Under 3 Hours: A Detailed Guide to Orchestrating Containers 我很奇怪,为什 ...

  7. 生产环境容器落地最佳实践 --JFrog 内部K8s落地旅程

    引言 Kubernetes已经成为市场上事实上领先的编配工具,不仅对技术公司如此,对所有公司都是如此,因为它允许您快速且可预测地部署应用程序.动态地伸缩应用程序.无缝地推出新特性,同时有效地利用硬件资 ...

  8. ImageApparate(幻影)镜像加速服务让镜像分发效率提升 5-10 倍

    作者介绍 李昂,腾讯高级开发工程师,主要关注容器存储和镜像存储相关领域,目前主要负责腾讯容器镜像服务和镜像存储加速系统的研发和设计工作. 李志宇,腾讯云后台开发工程师.负责腾讯云 TKE 集群节点和运 ...

  9. Kubernetes生产环境最佳实践

    点击上方"开源Linux",选择"设为星标" 回复"学习"获取独家整理的学习资料! 众所周知,Kubernetes很难! 以下是在生产中使用 ...

  10. 制作 Python Docker 镜像的最佳实践

    概述 ️Reference: 制作容器镜像的最佳实践 这篇文章是关于制作 Python Docker 容器镜像的最佳实践.(2022 年 12 月更新) 最佳实践的目的一方面是为了减小镜像体积,提升 ...

随机推荐

  1. 同一份代码怎能在不同环境表现不同?记一个可选链因为代码压缩造成的bug

    壹 ❀ 引 某一天,CSM日常找我反馈客户紧急工单,说有一个私有部署客户升级版本后,发现一个功能使用不太正常.因为我们公司客户分为两种,一种是SaaS客户,客户侧使用的版本被动跟随主版本变动,而私有部 ...

  2. JS leetcode 杨辉三角 超详细题解分析

    壹 ❀ 引 刷leetcode的第四天,原题出处为杨辉三角,题目描述如下: 给定一个非负整数 numRows,生成杨辉三角的前 numRows 行. 在杨辉三角中,每个数是它左上方和右上方的数的和. ...

  3. NC51097 Parity game

    题目链接 题目 题目描述 Now and then you play the following game with your friend. Your friend writes down a se ...

  4. Javascript中的var变量声明作用域问题

    先看一下这两段代码的执行结果 var name2 = 'What!'; function a() { if (typeof name2 === 'undefined') { console.log(' ...

  5. Swoole从入门到入土(8)——协程初探

    这一章节"协程"话题的讨论是为了让我们对之后协程风格服务端有更全面的了解.所以我们需要先一起了解一下什么是协程?协程有什么作用? 当大家第一次看到"协程"这个词 ...

  6. Oracle 分析函数详解(Analytic Functions)--示例部分

    Analytic functions are commonly used in data warehousing environments. In the list of analytic funct ...

  7. 【MySQL】数据库设计(一)三大范式

    三大范式 1NF 第一范式 强调列的原子性,即列不可分 例如: 2NF 第二范式 前提是1NF,另外包含两个部分: 表必须具有一个主键: 没有包含在主键中的列必须完全依赖于主键,而不是只依赖主键的一部 ...

  8. 【LeetCode二叉树#08】寻找树左下角的值(回溯机制X深度)

    找树左下角的值 力扣题目链接(opens new window) 给定一个二叉树,在树的最后一行找到最左边的值. 示例 1: 示例 2: 思路 层序遍历 这个是很自然的思路,因为层序遍历可以避免对于& ...

  9. 在矩池云安装使用PaddleHub 和 PaddlePaddle

    之前在安装 PaddleHub 导入的时候遇到各种错误,不是这个包没这个模块,就是哪个包没这个属性 ...很头痛,网上也没有 PaddleHub 和 PaddlePaddle 对应的版本,只能自己慢慢 ...

  10. 配置Nexus 3服务器作为Nuget包的仓库

    1.进入Nexus的Web界面 在右上角点"Login" 根据提示,去服务器上查看初始密码 root@dns-server:/mnt/data# cd nexus-data roo ...