云原生容器编排边缘计算【免费下载链接】k0sk0s - The Zero Friction Kubernetes项目地址https://gitcode.com/gh_mirrors/k0/k0s点击查看免费下载导读本文以 k0s 的 Autopilot 组件为核心深入讲解Multi-Command Plans多命令计划的完整执行模型一个Plan如何由多个Command组成、如何按顺序调度到Signal Node可接收 Autopilot 更新的控制器或工作节点、如何通过一组固定的处理状态Processing States驱动执行以及失败时如何通过错误状态Error States安全中止。读完本文你将能够编写并应用包含airgapupdate与k0supdate组合的实战 Plan理解 Plan 状态上报的读取方法并结合仓库源码理解底层状态机与调度逻辑。一、核心概念Plan / Command / Signal NodeAutopilot 依赖Plan来定义应当执行的Commands、每个 Command 应当作用于哪些Signal Nodes以及每个 Command 的执行状态。三个核心抽象定义可对照 pkg/apis/autopilot/v1beta2/types.goPlan计划定义一条或多条 Command指明每个 Command 如何发现 Signal Nodes并按解析出的 Signal Nodes 保存整个 Plan 的执行状态。Command命令Plan 内部的一个指令步骤会被应用到 Signal Node 上。当前支持两种命令类型k0supdate升级 k0s 二进制与airgapupdate升级离线 airgap bundle。Signal Node信号节点任何能够通过 Autopilot 接收更新的节点包括 controller控制器与 worker工作节点。控制器节点对应ControlNode对象工作节点对应 KubernetesNode对象。从源码看PlanCommand结构体types.go正是以这两个字段承载命令定义type PlanCommand struct { K0sUpdate *PlanCommandK0sUpdate json:k0supdate,omitempty AirgapUpdate *PlanCommandAirgapUpdate json:airgapupdate,omitempty }二、执行模型Command 按顺序串行推进一个 Plan 的执行本质上是让每条 Command 依次经过若干Processing States的处理过程。Plan 中的 Command 严格按照在 Plan 中出现的顺序执行。只有当当前 Command 上报状态为Completed时Plan 才会推进到下一条 Command。任何 Command 一旦进入被识别的Error States错误状态当前 Command 与整个 Plan 都会中止处理其状态会如实反映这一结果。只有当所有Command 都上报CompletedPlan 才被视为完成。这一顺序推进、逐条完成的语义在源码中有直接对应核心处理器 planstatehandler.go 会遍历plan.Spec.Commands跳过已经处于Completed的命令找到第一个未完成的 Command 交给对应的PlanCommandProvider处理只有全部命令都标记为Completed后才会把整个 Plan 的状态置为Completed。三、状态Status命令与状态同索引对齐Plan 的进度与每条 Command 的状态都会被记录在 Plan 的status字段中。Plan 中的每条 Command 都有一个与之索引相同的状态条目。例如Plan 中第二条 Command 的索引为1它的状态条目索引同样为1。判断 Plan 是否完成时会综合所有Command 的状态进行考量。PlanStatus与PlanCommandStatus的定义types.go证实了这一点Commands是一个按索引顺序维护的状态数组每条状态带有id、state以及对应命令类型的细分状态。四、完整示例一个双命令 Plan 的解剖下面是一个已被应用、且正在被 Autopilot 处理的 Plan 示例行号为注释方便讲解1: apiVersion: autopilot.k0sproject.io/v1beta2 2: kind: Plan 3: metadata: 4: annotations: 5: omitted 6: spec: 7: commands: 8: - airgapupdate: 9: version: {{{ k0s_version }}} 10: platforms: 11: linux-amd64: 12: url: https://github.com/k0sproject/k0s/releases/download/{{{ k0s_version }}}/k0s-airgap-bundle-{{{ k0s_version }}}-amd64 13: workers: 14: discovery: 15: static: 16: nodes: 17: - worker0 18: - k0supdate: 19: version: {{{ k0s_version }}} 20: platforms: 21: linux-amd64: 22: url: https://github.com/k0sproject/k0s/releases/download/{{{ k0s_version }}}/k0s-{{{ k0s_version }}}-amd64 23: targets: 24: controllers: 25: discovery: 26: static: 27: nodes: 28: - controller0 29: workers: 30: discovery: 31: static: 32: nodes: 33: - worker0 34: id: id123 35: timestamp: now 36: status: 37: commands: 38: - airgapupdate: 39: workers: 40: - lastUpdatedTimestamp: 2022-05-11T19:13:02Z 41: name: worker0 42: state: SignalSent 43: id: 0 44: state: SchedulableWait 45: - id: 1 46: k0supdate: 47: controllers: 48: - lastUpdatedTimestamp: 2022-05-11T19:13:02Z 49: name: controller0 50: state: SignalPending 51: workers: 52: - lastUpdatedTimestamp: 2022-05-11T19:13:02Z 53: name: worker0 54: state: SignalPending 55: state: SchedulableWait 56: state: SchedulableWait解读第 7-33 行是组成该 Plan 的两条 Command一条airgapupdate离线 bundle 升级和一条k0supdatek0s 版本升级。第 38-55 行是这两条 Command 各自的状态条目。当前 Plan 的状态是Autopilot 已经成功处理了该 Plan并已开始处理airgapupdateCommand。其airgapupdate状态为SignalSent表示已向该 Signal Nodeworker0发送了执行 airgap 更新的信令信息而k0supdate的目标controller0、worker0仍处于SignalPending等待被发送信令。五、处理状态Processing States无论是Plan还是Command都遵循下面这组状态其中Errors* 状态将在下文错误状态一节详细展开。NewPlan当一个名为autopilot的 Plan 被创建时会进入NewPlan状态处理。NewPlan的职责是确保所有Command 的状态都体现在 Plan 状态中——这份 Plan 状态在后续处理中用于判断整个 Plan 是否完成。NewPlan 与其他状态最大的区别在于它会遍历所有 Command而其他状态只处理当前激活的那条 Command。SchedulableWait用于评估一条 Command 是否可以进入调度处理。如果判定该 Command 可以处理状态被置为Schedulable。Schedulable由SchedulableWait置位表示该 Command 应当执行。处于此状态时Command 的执行逻辑取决于各 Command 自身的定义例如k0supdate执行版本升级airgapupdate执行离线包信令发送。该状态结束时要么转入SchedulableWait继续处理并检测完成要么转入某个错误状态。Completed表示命令已完成处理。一旦 Plan/Command 进入Completed后续不再对该 Plan/Command 做任何处理。这些状态常量在源码 pkg/autopilot/controller/plans/core/types.go 中有明确声明PlanSchedulable、PlanSchedulableWait、PlanCompleted以及PlanIncompleteTargets、PlanRestricted、PlanApplyFailed等错误态。状态机在源码中的落地每个 Command 类型都实现了一个PlanCommandProvider接口types.go它提供NewPlan、Schedulable、SchedulableWait三个方法分别对应上述状态的处理逻辑。以airgapupdate为例NewPlannewplan.go校验版本可更新性填充 worker 状态列表若存在无法解析的目标则返回IncompleteTargets若目标类型被--exclude-from-plans排除则返回Restricted。Schedulableschedulable.go找出下一个处于SignalPending的节点向该节点的对象写入带url、version、sha256的信令数据并把状态更新为SignalSent随后回到SchedulableWait。SchedulableWaitschedulablewait.go回读各 Signal Node 上的信令结果把完成/失败的状态同步回 Plan 状态再决定进入Schedulable继续调度、Completed全部完成还是ApplyFailed不可恢复的失败。六、错误状态Error States当 Plan 或 Command 处理进入任一被指定的错误状态时被视为致命错误Plan/Command 处理将终止。错误状态一般由各Command 实现定义核心 Autopilot 逻辑只关心 4 个核心状态NewPlan、SchedulableWait、Schedulable、Completed并将其余一切状态都当作错误处理。错误状态适用 Command出现状态描述IncompleteTargetsairgapupdate、k0supdateNewPlan、Schedulable表示在NewPlan发现阶段存在的某个 Signal Node 已不再存在例如对应的ControlNode或Node对象消失Restrictedairgapupdate、k0supdateNewPlan表示 Plan 请求更新的 Signal Node 类型与启动时的排除项--exclude-from-plans参数冲突MissingSignalNodeairgapupdate、k0supdateSchedulable旧版本 k0s 用于表示IncompleteTargets的遗留状态现已不再使用关于--exclude-from-plans参数从源码看控制器启动注册时会把该参数传入两个命令提供方pkg/autopilot/controller/plans/init.goairgapupdate与k0supdate的 provider 构造时会将其转换为排除集合provider.go并在 NewPlan 阶段判断目标类型是否被排除。七、时序推演双命令 Plan 的完整执行序列以上一节示例为参照下面给出状态转移与对象操作的基本时序时序要点NewPlan 阶段两条 Command 依次完成NewPlan全部进入SchedulableWaitPlan 状态初始化完毕。airgapupdate 阶段对 worker0 完成Wait → Schedulable → 发送信令 → Wait → Completed的完整循环。k0supdate 阶段先调度 controller0控制器优先再调度 worker0各自经历同样的状态循环。最后整个 Plan 进入Completed。注意时序中控制器先于 worker 更新的调度纪律并非偶然——k0supdate的SchedulableWait实现schedulablewait.go明确注释只有当controllersDone为真时才会允许调度 worker这是为了遵守 Kubernetes 的版本偏差策略Kubelet 版本不得高于 API Server 版本。八、Plan 配置全字段参考k0supdate 与 airgapupdate下面的 Plan 更完整地展示了字段全貌含sha256校验与limits.concurrentapiVersion: autopilot.k0sproject.io/v1beta2 kind: Plan metadata: name: autopilot spec: id: id1234 timestamp: now commands: - k0supdate: version: {{{ k0s_version }}} platforms: linux-amd64: url: https://github.com/k0sproject/k0s/releases/download/{{{ k0s_version }}}/k0s-{{{ k0s_version }}}-amd64 sha256: 0000000000000000000000000000000000000000000000000000000000000000 targets: controllers: discovery: static: nodes: - ip-172-31-44-131 - ip-172-31-42-134 - ip-172-31-39-65 workers: limits: concurrent: 5 discovery: selector: labels: environmentstaging fields: metadata.nameworker2核心字段apiVersionstring必填当前 Autopilot API 版本为v1beta2完整 group-version 为autopilot.k0sproject.io/v1beta2。metadata.namestring必填Plan 的名称必须始终为autopilot。⚠️ 不遵循此约定Plan 将不会执行。Spec 字段spec.idstring可选创建者提供的标识符用于信息记录与追踪。spec.timestampstring可选创建者提供的创建时间戳纯信息用途Autopilot 不会处理它。spec.commands[]必填包含 Plan 需要执行的全部命令。k0supdate命令字段spec.commands[].k0supdate.versionstring必填要升级到的 k0s 二进制版本号。该版本用于在升级前后与已安装版本比对以确认升级成功。spec.commands[].k0supdate.platforms.*.urlstring必填指定平台下更新二进制的下载地址。平台命名由$GOOS与$GOARCH以连字符-组合而成例如linux-amd64、linux-arm64、linux-arm。注意主要支持平台为linuxAutopilot 在其他平台可能可用但未经测试。spec.commands[].k0supdate.platforms.*.sha256string可选若提供二进制的 SHA256 哈希下载完成后会据此校验。spec.commands[].k0supdate.targets.controllersobject可选定义控制器如何被更新。spec.commands[].k0supdate.targets.controllers.limits.concurrentint固定为 1虽然配置项允许指定控制器并发更新数但对控制器目标而言始终固定为 1。确保同一时刻只更新一个控制器避免破坏 etcd 仲裁quorum。spec.commands[].k0supdate.targets.workersobject可选定义工作节点如何被更新。spec.commands[].k0supdate.targets.workers.limits.concurrentint可选默认 1指定 worker 并发更新数量不提供时按1处理。airgapupdate命令字段spec.commands[].airgapupdate.versionstring必填要升级的 airgap bundle 版本。spec.commands[].airgapupdate.platforms.*.urlstring必填指定平台下离线包的下载地址平台命名规则同上linux-amd64等主要支持linux。spec.commands[].airgapupdate.platforms.*.sha256string可选提供后用于下载完成后的哈希校验。spec.commands[].airgapupdate.workersobject可选定义 worker 如何被离线更新。spec.commands[].airgapupdate.workers.limits.concurrentint可选默认 1worker 并发更新数量默认1。静态发现Static Discoverystatic发现方式依赖.nodes中定义的一组固定主机名。要求存在同名对象worker 对应Node对象controller 对应ControlNode对象。static: nodes: - ip-172-31-44-131 - ip-172-31-42-134 - ip-172-31-39-65spec.commands[].k0supdate.targets.*.discovery.static.nodes[]stringstatic 方式下必填应纳入目标集合controllers/workers的主机名列表。选择器发现Selector Target Discoveryselector发现方式通过对 Kubernetes API 的动态查询使用标签labels与字段fields产生应被更新的主机集合。labels与fields同时提供时二者取逻辑与AND。selector: labels: environmentstaging fields: metadata.nameworker2指定空选择器selector: {}将选中该目标集合的所有节点。spec.commands[].k0supdate.targets.*.discovery.selector.labelsstring可选用于查找目标节点的 name/value 标签集合。spec.commands[].k0supdate.targets.*.discovery.selector.fieldsstring可选用于查找目标节点的 name/value 字段集合。注意目前仅metadata.name可用作查询字段。并发限制的源码佐证并发限制的默认值与语义在 types.go 中通过 kubebuilder 标记声明Concurrent默认值为1含义为最多同时执行 N 个目标。调度判断时isSchedulable会对比待发信令数与已发信令数是否小于并发上限k0supdate/schedulablewait.go而控制器由于signalingSentCount 0的硬性条件天然保证同一时刻只有一个控制器在途。九、状态上报Status ReportingPlan 应用后可通过其.status查看进度kubectl get plan autopilot -oyaml一个 Plan 状态示例status: state: SchedulableWait commands: - state: SchedulableWait k0supdate: controllers: - lastUpdatedTimestamp: 2022-04-07T15:52:44Z name: controller0 state: SignalCompleted - lastUpdatedTimestamp: 2022-04-07T15:52:24Z name: controller1 state: SignalCompleted - lastUpdatedTimestamp: 2022-04-07T15:52:24Z name: controller2 state: SignalPending workers: - lastUpdatedTimestamp: 2022-04-07T15:52:24Z name: worker0 state: SignalPending - lastUpdatedTimestamp: 2022-04-07T15:52:24Z name: worker1 state: SignalPending - lastUpdatedTimestamp: 2022-04-07T15:52:24Z name: worker2 state: SignalPending解读该状态整体更新状态为SchedulableWaitAutopilot 正在等待下一次处理 Command 的机会。共有三个控制器节点两个已成功完成信令SignalCompleted一个等待被信令SignalPending。共有三个 worker 节点全部处于等待信令状态SignalPending。Plan 状态.status.state代表整个 Autopilot 更新操作的总体状态状态描述是否结束 PlanIncompleteTargets解析后的 Plan 中存在没有对应Nodeworker或ControlNodecontroller对象的节点是Schedulable表示可以重新评估 Plan以决定下一个更新哪个节点否SchedulableWait调度操作正在进行中不应再进行更新调度否CompletedPlan 已成功运行完成是RestrictedPlan 包含违反--exclude-from-plans限制的节点类型controller 或 worker是节点状态与 Plan 状态类似单个节点也有自己的状态状态描述SignalPending节点可用等待更新信令SignalSent更新信令已成功应用到该节点SignalMissingPlatform该节点的平台没有为其提供更新SignalMissingNode该节点没有关联的Nodeworker或ControlNodecontroller对象十、多命令编排的配套能力UpdateConfig 与安全护栏Multi-Command Plans 是 Autopilot 手动升级的载体若想在此基础上实现自动更新可创建UpdateConfig对象完整字段定义见 updateconfig.go其中ToPlan方法会把配置实时转换为PlanapiVersion: autopilot.k0sproject.io/v1beta2 kind: UpdateConfig metadata: name: example namespace: default spec: channel: edge_release updateServer: https://updates.k0sproject.io/ upgradeStrategy: type: periodic periodic: # 仅在周二或周三的 13:00-15:00 触发更新 days: [Tuesdays,Wednesday] startTime: 13:00 length: 2h planSpec: # 若存在可用更新则按此生成 Plan commands: - k0supdate: targets: controllers: discovery: static: nodes: - ip-172-31-44-131 workers: limits: concurrent: 5 discovery: selector: labels: environmentstaging fields: metadata.nameworker2UpdateConfig 关键字段spec.channelstring可选更新频道支持stable默认与unstable。spec.updateServerstring可选更新服务器地址默认https://updates.k0sproject.io。spec.upgradeStrategy.typeenumcron|periodic选择更新策略。spec.upgradeStrategy.cronstring可选已弃用crontab 格式的检查更新调度。spec.upgradeStrategy.periodicobject包含days每周哪几天检查、startTime每天何时开始、length更新窗口时长。spec.planSpecstring可选描述 Autopilot 自动生成的 Plan 的行为未提供任何命令时ToPlan会自动生成一个覆盖集群全部控制器与 worker 的默认k0supdate命令。多命令 Plan 之所以安全离不开 Autopilot 内置的护栏设计无状态组件Autopilot 不依赖重型状态或大规模同步控制器消失后备用控制器可以无缝接管 Autopilot 操作。Worker 只在 Controller 之后更新基于 Kubelet 不得高于 API Server 版本的版本偏差策略同时包含控制器与 worker 的 Plan 会先更新所有控制器全部成功后才向 worker 发送更新指令。Plan 不可变Plan 应用后Autopilot 评估应包含的所有控制器与 worker 并记录在状态中此后除状态外不再识别对 Plan 的任何修改。这尤其适配大量动态 worker 的场景——按selector匹配的节点在真正调度时可能已不存在。控制器仲裁安全调度控制器更新前Autopilot 会查询所有控制器的 API Server确保其/ready成功只有全部就绪才会向当前控制器发送更新信令。若之前发现的控制器目标无法再解析Plan 转入IncompleteTargets并终止执行瞬时就绪失败则会重新入队。控制器顺序更新尽管配置允许设置并发同一时刻仍只更新一个控制器。更新负载校验每个 update 对象可提供可选的sha256哈希下载完成后会与实际内容比对。十一、常见问题FAQQ如何应用Plan和ControlNode的 CRDA这些 CRD 定义已内嵌在k0s二进制中启动时自动应用无需额外操作。CRD 静态清单亦可查看 static/_crds/autopilot 目录。QControlNode实例如何被移除AControlNode实例由 Autopilot 控制器启动时创建。控制器消失时不会移除其关联的ControlNode实例其维护责任由运维人员/管理员承担。Q我升级了 worker但 Kubelet 不再上报了A很可能是你先把 worker 升级到了高于 API Server 支持的版本。请务必先将控制器升级到目标版本再升级 worker。结语从 Plan 到多命令编排的完整链路回顾整篇文章Multi-Command Plans 让一次kubectl apply即可编排airgapupdate与k0supdate等多条命令以顺序执行、状态驱动、错误即停的模型串起整条升级链路。其底层由 pkg/autopilot/controller/plans/core 的状态处理器统一调度由各命令提供方airgapupdate、k0supdate实现具体的发现、信令与状态回读逻辑。配合UpdateConfig的周期自动更新以及控制器优先、单点更新、SHA256 校验等安全护栏Autopilot 可以在不破坏集群可用性的前提下完成从控制器到 worker 的滚动升级。想进一步实践可参考仓库中的相关文档Autopilot 总览、离线安装指南、升级指南以及集成测试用例目录 inttest/autopilot 与 inttest/ap-multicommand如多控制器多 worker 场景、平台选择、更新器等它们演示了多命令 Plan 在真实集群中的端到端行为。赞分享云原生容器编排边缘计算【免费下载链接】k0sk0s - The Zero Friction Kubernetes项目地址https://gitcode.com/gh_mirrors/k0/k0s点击查看免费下载相关推荐PX4-Autopilot 命令行工具完全指南Modules Reference: Command 深度解析PX4 Autopilot 命令行工具完全指南Modules Reference: Command 深度解析 PX4 飞控系统在控制台NSH Shell中嵌入式物联网机器人自动驾驶智能硬件Hyperf 命令组件hyperf/command实战指南自定义命令、参数配置与协程化执行Hyperf 命令组件hyperf/command实战指南自定义命令、参数配置与协程化执行 Hyperf 的命令行能力由 hyperf/command 组后端Web框架微服务RPC框架异步编程ruflo-autopilot 状态监控实战深入解析 /autopilot-status 命令与 MCP 工具链ruflo autopilot 状态监控实战深入解析 /autopilot status 命令与 MCP 工具链 /autopilot status 是 ru人工智能AI Agent多智能体Agent 编排Agent 记忆工具调用代码智能体MCP 服务AI 评测上一篇Sunshine游戏串流优化实战指南从问题诊断到场景适配下一篇终极Zotero文献管理神器用Ethereal Style插件提升300%阅读效率创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
阅读完成 · 觉得有帮助?