k8s学习之路 | Day16 k8s 中的容器初探
文章目录
- 容器镜像
- 镜像名称
- 镜像拉取策略
- 私有仓库的拉取策略
- 容器的环境变量和启动命令
- 容器的环境变量
- 容器的启动命令
- 容器的生命周期钩子
- postStart
- preStop
- 容器的探针
- startupProbe
- livenessProbe
- readinessProbe
k8s 集群中最小的管理单元就是一个
Pod
,而Pod
里面才是容器,但是容器里面到底应该怎么写yaml
呢?这个就是我今天学习的目标
- 一个最简单的
Pod
资源清单类似于以下这种:
##pod-demo.yaml
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels: app: MYAPP
spec:containers:- name: pod-demoimage: nginx
- 我们通过
kubectl explain pod.spec.containers
解释了容器到底里面能写什么忒多了
[root@k8s-01 k8s-yaml]# kubectl explain pod.spec.containers
KIND: Pod
VERSION: v1RESOURCE: containers <[]Object>DESCRIPTION:List of containers belonging to the pod. Containers cannot currently beadded or removed. There must be at least one container in a Pod. Cannot beupdated.A single application container that you want to run within a pod.FIELDS:args <[]string>Arguments to the entrypoint. The docker image's CMD is used if this is notprovided. Variable references $(VAR_NAME) are expanded using thecontainer's environment. If a variable cannot be resolved, the reference inthe input string will be unchanged. The $(VAR_NAME) syntax can be escapedwith a double $$, ie: $$(VAR_NAME). Escaped references will never beexpanded, regardless of whether the variable exists or not. Cannot beupdated. More info:https://kubernetes.io/docs/tasks/inject-data-application/define-command-argument-container/#running-a-command-in-a-shell
...
容器镜像
镜像名称
kubectl explain pod.spec.containers
中的【image 】解释了有关镜像名称的含义和写法
- Docker image 的镜像名称
- string 数据类型
##所以在写yaml文件的时候,就应该以这种形式来确认你这个容器启动用的镜像
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels: app: MYAPP
spec:containers:- name: pod-demoimage: nginx#image: nginx:1.21-alpine#image: tomcat:latest
镜像拉取策略
kubectl explain pod.spec.containers
中的【imagePullPolicy】解释的就是镜像拉取策略
kubectl explain pod.spec.containers.imagePullPolicy
拉取策略
- Always:每当 kubelet 启动一个容器时,kubelet 会查询容器的镜像仓库, 将名称解析为一个镜像摘要。 如果 kubelet 有一个容器镜像,并且对应的摘要已在本地缓存,kubelet 就会使用其缓存的镜像; 否则,kubelet 就会使用解析后的摘要拉取镜像,并使用该镜像来启动容器。这也是默认拉取策略
- Never:Kubelet 不会尝试获取镜像。如果镜像已经以某种方式存在本地, kubelet 会尝试启动容器;否则,会启动失败。
- IfNotPresent:只有当镜像在本地不存在时才会拉取。
##所以在写yaml文件的时候,就应该以这种形式来确认要启动容器的镜像的来源
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels: app: MYAPP
spec:containers:- name: pod-demoimage: nginximagePullPolicy: Always ## 默认拉取策略:总是去下载
举个栗子
我有下面这个pod
文件,我尝试启动一下试试:
#####pod-test1.yaml
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels: app: MYAPP
spec:containers:- name: pod-demoimage: wordpressimagePullPolicy: Never
私有仓库的拉取策略
如果我们需要从自己的阿里云私人镜像仓库拉取镜像,又应该如何操作呢?看一下官方帮助文档kubectl explain pod.spec
中的【imagePullSecrets <[]Object>】
官方地址:
https://kubernetes.io/zh-cn/docs/concepts/containers/images/#specifying-imagepullsecrets-on-a-pod
官方是这样说的:
-
要创建一个
Secret
-
然后在 Pod 中引用
ImagePullSecrets
举个栗子
我要拉取我自己阿里云镜像仓库的镜像:
- 我需要先创建一个
Secret
,这个怎么创建呢?官方是这样说的
kubectl create secret docker-registry <name> \--docker-server=DOCKER_REGISTRY_SERVER \--docker-username=DOCKER_USER \--docker-password=DOCKER_PASSWORD \--docker-email=DOCKER_EMAIL
我就创建一个试试:
kubectl create secret docker-registry test \--docker-server=registry.cn-hangzhou.aliyuncs.com \--docker-username=tb330504_33 \--docker-password=xxxxxxxx \--docker-email=565616251@qq.com
我在准备一个Pod
文件
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels: app: MYAPP
spec:imagePullSecrets:- name: testcontainers:- name: pod-demoimage: registry.cn-hangzhou.aliyuncs.com/publiclibrary/tomcat:8.5-jdk11-temurin-focalimagePullPolicy: IfNotPresent
运行一下,看是否能拉取后正常运行:
- 正在拉取镜像
- 拉取成功,运行成功
容器的环境变量和启动命令
容器的环境变量
kubectl explain pod.spec.containers.env
- 按照官方描述,有关容器的环境变量就应该这样写了
####以mysql镜像为例
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels: app: MYAPP
spec:containers:- name: pod-mysql-demoimage: mysqlimagePullPolicy: Alwaysenv:- name: MYSQL_DATABASEvalue: my-test- name: MYSQL_ROOT_PASSWORDvalue: admin@123
- 尝试并验证一下:OK
容器的启动命令
kubectl explain pod.spec.containers.command
https://kubernetes.io/zh-cn/docs/tasks/inject-data-application/define-command-argument-container/#running-a-command-in-a-shell
- 尝试一下(覆盖容器默认的启动命令)
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels:app: MYAPP
spec:containers:- name: pod-demoimage: nginxcommand:- /bin/sh- -c- "echo hello world;sleep 3600;"
-
可以看到,如果设置了
command
字段信息,就会覆盖默认的容器启动命令,对于这个,官方有明确的说明:- 如果在配置文件中设置了容器启动时要执行的命令及其参数,那么容器镜像中自带的命令与参数将会被覆盖而不再执行。
- 如果配置文件中只是设置了参数,却没有设置其对应的命令,那么容器镜像中自带的命令会使用该新参数作为其执行时的参数。
-
从最新的文档发现,有些内容有所出入
容器的生命周期钩子
https://kubernetes.io/zh-cn/docs/concepts/containers/container-lifecycle-hooks/#container-hooks
kubectl explain pod.spec.containers.lifecycle
kubectl explain pod.spec.containers.lifecycle.postStart
kubectl explain pod.spec.containers.lifecycle.preStop
k8s 中提供了二个关于容器的生命周期钩子
- postStart
在容器创建后将立刻执行。但是,并不能保证该钩子函数在容器的 ENTRYPOINT 之前
执行。该钩子函数没有输入参数。
- preStop
在容器被 terminate(终止)之前执行
postStart
k8s 在容器启动后立刻发送postStart
事件,但是并不能确保postStart
事件处理程序在容器的EntryPoint
之前执行,意思就是容器启动了就会触发,不管容器执行是否成功?在 k8s 管理容器的时候,将一直等待 postStart
事件处理程序结束后,才会将容器的状态标记为Running
- exec:容器创建以后,钩子函数执行一个命令
- httpGet:容器创建以后,钩子函数发送一个http的get请求
- tcpSocket:容器创建以后,钩子函数连上一个TCP端口
我们以httpGet
为例
我们先启动一个 nginx pod
##pod-demo.yaml
apiVersion: v1
kind: Pod
metadata:name: pod-demolabels: app: MYAPP
spec:containers:- name: pod-demoimage: nginx
我们在准备一个示例yaml
##lifecycle-demo.yaml
apiVersion: v1
kind: Pod
metadata:name: lifecycle-demolabels: app: MYAPP
spec:containers:- name: lifecycle-demoimage: nginxlifecycle:postStart:httpGet:host: 192.168.0.190path: /lifecycle-testport: 80scheme: HTTP ####注意这个地方是大写
启动一下
查看一下钩子的设置是否生效
- 是有相关请求,证明是生效的
preStop
钩子函数在容器被terminate
之前执行,执行是同步的,执行完才删除容器,写法也是和postStart
一样
##lifecycle-demo.yaml
apiVersion: v1
kind: Pod
metadata:name: lifecycle-demolabels: app: MYAPP
spec:containers:- name: lifecycle-demoimage: nginxlifecycle:preStop:httpGet:host: 192.168.0.190path: /lifecycle-testport: 80scheme: HTTP ####注意这个地方是大写
我们先启动一个这样的 pod
我将这个pod杀死
kubectl delete -f lifecycle-demo.yaml
看下是否生效
容器的探针
健康检查机制
probe 是由 kubelet 对容器执行的定期诊断。 要执行诊断,kubelet 既可以在容器内执行代码,也可以发出一个网络请求。
-
startupProbe
:启动探针指示容器中的应用是否已经启动。如果提供了启动探针,则所有其他探针都会被禁用,直到此探针成功为止。如果启动探测失败,kubelet 将杀死容器, 而容器依其重启策略进行重启。 如果容器没有提供启动探测,则默认状态为 Success。
-
livenessProbe
:存活探针指示容器是否正在运行。如果存活态探测失败,则 kubelet 会杀死容器, 并且容器将根据其重启策略决定未来。如果容器不提供存活探针, 则默认状态为 Success。
-
readinessProbe
:就绪探针指示容器是否准备好为请求提供服务。如果就绪态探测失败, 端点控制器将从与 Pod 匹配的所有服务的端点列表中删除该 Pod 的 IP 地址。 初始延迟之前的就绪态的状态值默认为 Failure。 如果容器不提供就绪态探针,则默认状态为 Success。
-
写法是一致的
kubectl explain pod.spec.containers.startupProbe
-
initialDelaySeconds
:容器启动后要等待多少秒后才启动启动、存活和就绪探针, 默认是 0 秒,最小值是 0。 -
periodSeconds
:执行探测的时间间隔(单位是秒)。默认是 10 秒。最小值是 1。 -
timeoutSeconds
:探测的超时后等待多少秒。默认值是 1 秒。最小值是 1。 -
successThreshold
:探针在失败后,被视为成功的最小连续成功数。默认值是 1。 存活和启动探测的这个值必须是 1。最小值是 1。 -
failureThreshold
:探针连续失败了failureThreshold
次之后, Kubernetes 认为总体上检查已失败:容器状态未就绪、不健康、不活跃。 对于启动探针或存活探针而言,如果至少有failureThreshold
个探针已失败, Kubernetes 会将容器视为不健康并为这个特定的容器触发重启操作。 kubelet 会考虑该容器的terminationGracePeriodSeconds
设置。 对于失败的就绪探针,kubelet 继续运行检查失败的容器,并继续运行更多探针; 因为检查失败,kubelet 将 Pod 的Ready
状况设置为false
。 -
terminationGracePeriodSeconds
:为 kubelet 配置从为失败的容器触发终止操作到强制容器运行时停止该容器之前等待的宽限时长。 默认值是继承 Pod 级别的terminationGracePeriodSeconds
值(如果不设置则为 30 秒),最小值为 1。
-
-
检查机制
-
exec
在容器内执行指定命令。如果命令退出时返回码为 0 则认为诊断成功 -
httpGet
对容器的 IP 地址上指定端口和路径执行 HTTP GET 请求。如果响应的状态码大于等于 200 且小于 400,则诊断被认为是成功的
-
tcpSocket
对容器的 IP 地址上的指定端口执行 TCP 检查。如果端口打开,则诊断被认为是成功的。 如果远程系统(容器)在打开连接后立即将其关闭,这算作是健康的
-
-
探测结果
- Success(成功)
容器通过了诊断。 - Failure(失败)
容器未通过诊断。 - Unknown(未知)
诊断失败,因此不会采取任何行动。
- Success(成功)
startupProbe
我先启动了一个 pod-demo 的容器:
我现在准备一个另一个 pod:
apiVersion: v1
kind: Pod
metadata:name: probe-demolabels: app: MYAPP
spec:containers:- name: probe-demoimage: nginxstartupProbe:httpGet:host: 192.168.0.190path: /index2.htmlport: 80scheme: HTTP ####注意这个地方是大写initialDelaySeconds: 60failureThreshold: 3periodSeconds: 10
我们启动验证一下:
- 最开始肯定是失败的,因为探针设置的路径不存在的,所以pod的状态也是未就绪的
- 我们对pod-demo中的文件进行一个操作,让测试pod可以探针成功
livenessProbe
我们还是以上面的为例,准备一个测试 yaml
###每个1秒就去检查特定服务器的服务是否正常访问,
apiVersion: v1
kind: Pod
metadata:name: probe-demolabels: app: MYAPP
spec:containers:- name: probe-demoimage: nginxlivenessProbe:httpGet:host: 192.168.0.190path: /index.htmlport: 80scheme: HTTP ####注意这个地方是大写initialDelaySeconds: 60failureThreshold: 3periodSeconds: 1
- 查看一下各状态
- 我们删除探针里面需要用到的pod,再看下状态
- 看下探针的事件:检查失败就会一直重启
但是我不知道为啥pod还是处于READY的状态
readinessProbe
就绪探针,理论是和上面一样的
有时候,应用会暂时性地无法为请求提供服务。 例如,应用在启动时可能需要加载大量的数据或配置文件,或是启动后要依赖等待外部服务。 在这种情况下,既不想杀死应用,也不想给它发送请求。 Kubernetes 提供了就绪探针来发现并缓解这些情况。 容器所在 Pod 上报还未就绪的信息,并且不接受通过 Kubernetes Service 的流量。
后续实际应用中,我再来探一下更多的用法场景
相关文章:

k8s学习之路 | Day16 k8s 中的容器初探
文章目录容器镜像镜像名称镜像拉取策略私有仓库的拉取策略容器的环境变量和启动命令容器的环境变量容器的启动命令容器的生命周期钩子postStartpreStop容器的探针startupProbelivenessProbereadinessProbek8s 集群中最小的管理单元就是一个Pod,而Pod里面才是容器&am…...
export、import、commit、save、load的区别
目录1. docker export 和 docker import2. docker commit3.docker save 和 docker load1. docker export 和 docker import docker export 容器ID/容器Name > xxx.tar 导出一个容器快照 docker import xxx.tar NewImageName:tag 导入一个容器快照到本地镜像库 适用场景&a…...

多部委联合举办中国人工智能大赛启动会在厦召开,快商通亮相发言
站在“第二个百年奋斗目标”的新起点上,为深入推动我国人工智能产业创新发展,发掘一批人工智能优秀团队, 国家互联网信息办公室、工业和信息化部、公安部、国家广播电视总局、厦门市人民政府将联合主办第四届中国人工智能大赛 。快商通联合创…...

js红宝书学习笔记(1-6章)
就按照原书中写的章节顺序记笔记了, 还有可能我学过js一段时间了,可能有些对于新手的细节会忽略,但是会尽量写全的~ 1.第一章 什么是JavaScript 1.1讲了一些历史,所以我们从1.2开始看 1.2 JavaScript的实现 完整的JaveScript包…...
第十四届蓝桥杯第三期官方模拟赛C\C++题解
文章目录A-填空题题意算法参考代码(C)B-填空题题意算法参考代码(C)C-填空题题意算法参考代码(C)D-填空题题意算法参考代码(C)E-填空题题意算法参考代码(C)F题…...
API接口安全
目前项目都是前后端分离或者有对外提供接口的需求,在这些情况下,就要考虑接口安全。 如果不重视接口安全,可能导致严重的危害,例如数据盗取,服务宕机等。 可能的安全问题: 1.明文密码被攻击者抓包看到 前端可对密码或…...

2023前端一面vue面试题合集
函数式组件优势和原理 函数组件的特点 函数式组件需要在声明组件是指定 functional:true不需要实例化,所以没有this,this通过render函数的第二个参数context来代替没有生命周期钩子函数,不能使用计算属性,watch不能通过$emit 对外暴露事件&…...

【Leetcode 剑指Offer】第 5 天 查找算法(中等)
查找算法剑指 Offer 04. 二维数组中的查找剑指 Offer 11. 旋转数组的最小数字剑指 Offer 50. 第一个只出现一次的字符Python字典基础哈希表(python中是dict())有序哈希表第一个中等,后两个简单题。剑指 Offer 04. 二维数组中的查找 题&#…...
薯条投放适合哪些笔记?小红书薯条投放的3种模式
随着小红书平台的种草推广模式兴盛,薯条投放这个词也渐渐进入大众的视野,今天就来给大家讲讲什么是薯条投放,以及薯条投放适合哪些笔记。一、什么是薯条投放?薯条是一款为小红书用户打造的笔记推广工具,用户可选择推广目标&#…...

记录第一个Python练习的过程
题目如下 编写一个名为collatz()的函数,它有一个名为number的参数。如果参数是偶数,那么collatz()就打印出number // 2,并返回该值。如果number是奇数,collatz()就打印并返回3 * number 1。 然后编写一个程序,让用户…...

【Python】3.3实现多线程
程序Program进程Process线程Thread为完成特定任务而用计算机语言编写的一组计算机能识别和执行的指令的集合。程序是指令、数据及其组织形式的描述,一段静态代码,静态对象。计算机中的程序关于某数据集合上的一次执行过程。进程是程序的实体,…...

在linux中使用lftp和sftp下载文件(夹)
一、首先确保你的系统中已经下载了lftp和sftp。 1.安装lftp sudo apt install lftp sudo apt install screen 2.安装sftp 在Linux系统中,一般RedHat系统默认已经安装了openssh-client和openssh-server,即默认已经集成了sftp服务,不需要重…...

Docker简介与用法
文章目录1、Docker简介1.1、Docker能解决什么问题1.2、什么是虚拟机技术1.2.1、虚拟机的缺点1.3、什么是容器1.3.1、容器与虚拟机比较1.4、分析 Docker 容器架构1.4.1、Docker客户端和服务器1.4.2、Docker 镜像(Image)1.4.3、Docker 容器(Container)1.4.4、Docker 仓库(reposit…...

基于海鸥算法改进的DELM分类-附代码
海鸥算法改进的深度极限学习机DELM的分类 文章目录海鸥算法改进的深度极限学习机DELM的分类1.ELM原理2.深度极限学习机(DELM)原理3.海鸥算法4.海鸥算法改进DELM5.实验结果6.参考文献7.Matlab代码1.ELM原理 ELM基础原理请参考:https://blog.c…...

linux基本功系列之mount命令实战
文章目录前言一. mount命令的介绍二. 语法格式及常用选项三. 参考案例3.1 将iso镜像挂载到/mnt上3.2 把某个分区挂载到/sdb1上3.3 用只读的形式把/dev/sdb2挂载到/sdb2上3.4 设置自动挂载总结前言 大家好,又见面了,我是沐风晓月,本文是专栏【…...

力扣Top100题之两数相加(Java解法)
0 题目描述 给你两个 非空 的链表,表示两个非负的整数。它们每位数字都是按照 逆序 的方式存储的,并且每个节点只能存储 一位 数字。 请你将两个数相加,并以相同形式返回一个表示和的链表。 你可以假设除了数字 0 之外,这两个数…...

【测试】Python手机自动化测试库uiautomator2和weditor的详细使用
1.说明 我们之前在电脑操作手机进行自动化测试,基本上都是通过Appium的,这个工具确实强大,搭配谷歌官方的UiAutomator基本上可以完成各种测试,但缺点也很明显,配置环境太麻烦了,需要jdk、sdk等,…...
《NFL橄榄球》:旧金山49人·橄榄1号位
旧金山四九人(San Francisco 49ers,又译旧金山淘金者) 是美国全国橄榄球联盟球队。成立于1946年,最初作为全美橄榄球联合会(AAFC)的一员参加比赛,后于1950年与克利夫兰布朗一同加入由美国橄榄球联合会合并而成的NFL。现任主教练为…...

spark为什么比hadoop快
网上一堆人根本对计算框架一知半解就出来糊弄人,常见解答有: spark是基于内存计算,所以快。这跟废话似的,mr计算的时候不也是基于内存? mr shuffle落盘。这也是胡扯, spark shuffle不落盘? 实际…...

跨境人都在用的指纹浏览器到底有什么魔力?三分钟带你了解透彻
什么是指纹浏览器?这是东哥近期收到最多的粉丝私信咨询,指纹两个字大家都很熟悉,指纹浏览器就变得陌生起来。之前东哥也跟大家分享过很多次指纹浏览器的用法,鉴于还是很多人不认识这个好用的工具,东哥今天就来详细给大…...

3.3.1_1 检错编码(奇偶校验码)
从这节课开始,我们会探讨数据链路层的差错控制功能,差错控制功能的主要目标是要发现并且解决一个帧内部的位错误,我们需要使用特殊的编码技术去发现帧内部的位错误,当我们发现位错误之后,通常来说有两种解决方案。第一…...

【第二十一章 SDIO接口(SDIO)】
第二十一章 SDIO接口 目录 第二十一章 SDIO接口(SDIO) 1 SDIO 主要功能 2 SDIO 总线拓扑 3 SDIO 功能描述 3.1 SDIO 适配器 3.2 SDIOAHB 接口 4 卡功能描述 4.1 卡识别模式 4.2 卡复位 4.3 操作电压范围确认 4.4 卡识别过程 4.5 写数据块 4.6 读数据块 4.7 数据流…...
Golang dig框架与GraphQL的完美结合
将 Go 的 Dig 依赖注入框架与 GraphQL 结合使用,可以显著提升应用程序的可维护性、可测试性以及灵活性。 Dig 是一个强大的依赖注入容器,能够帮助开发者更好地管理复杂的依赖关系,而 GraphQL 则是一种用于 API 的查询语言,能够提…...

高危文件识别的常用算法:原理、应用与企业场景
高危文件识别的常用算法:原理、应用与企业场景 高危文件识别旨在检测可能导致安全威胁的文件,如包含恶意代码、敏感数据或欺诈内容的文档,在企业协同办公环境中(如Teams、Google Workspace)尤为重要。结合大模型技术&…...

第一篇:Agent2Agent (A2A) 协议——协作式人工智能的黎明
AI 领域的快速发展正在催生一个新时代,智能代理(agents)不再是孤立的个体,而是能够像一个数字团队一样协作。然而,当前 AI 生态系统的碎片化阻碍了这一愿景的实现,导致了“AI 巴别塔问题”——不同代理之间…...

【单片机期末】单片机系统设计
主要内容:系统状态机,系统时基,系统需求分析,系统构建,系统状态流图 一、题目要求 二、绘制系统状态流图 题目:根据上述描述绘制系统状态流图,注明状态转移条件及方向。 三、利用定时器产生时…...

BCS 2025|百度副总裁陈洋:智能体在安全领域的应用实践
6月5日,2025全球数字经济大会数字安全主论坛暨北京网络安全大会在国家会议中心隆重开幕。百度副总裁陈洋受邀出席,并作《智能体在安全领域的应用实践》主题演讲,分享了在智能体在安全领域的突破性实践。他指出,百度通过将安全能力…...
Python如何给视频添加音频和字幕
在Python中,给视频添加音频和字幕可以使用电影文件处理库MoviePy和字幕处理库Subtitles。下面将详细介绍如何使用这些库来实现视频的音频和字幕添加,包括必要的代码示例和详细解释。 环境准备 在开始之前,需要安装以下Python库:…...
【RockeMQ】第2节|RocketMQ快速实战以及核⼼概念详解(二)
升级Dledger高可用集群 一、主从架构的不足与Dledger的定位 主从架构缺陷 数据备份依赖Slave节点,但无自动故障转移能力,Master宕机后需人工切换,期间消息可能无法读取。Slave仅存储数据,无法主动升级为Master响应请求ÿ…...
【C++从零实现Json-Rpc框架】第六弹 —— 服务端模块划分
一、项目背景回顾 前五弹完成了Json-Rpc协议解析、请求处理、客户端调用等基础模块搭建。 本弹重点聚焦于服务端的模块划分与架构设计,提升代码结构的可维护性与扩展性。 二、服务端模块设计目标 高内聚低耦合:各模块职责清晰,便于独立开发…...