Kubernetes 1.27:SIG-Scheduling的变更内容
以下是从Kubernetes 1.27的CHANGELOG中摘录的关于SIG-Scheduling的部分。以下是我对此的评论。
过去三个发布版本的更改内容:
-
- Kubernetes 1.26: SIG-Scheduling の変更内容
-
- Kubernetes 1.25: SIG-Scheduling の変更内容
- Kubernetes 1.24: SIG-Scheduling の変更内容
感受之处 (Suǒ zhī chù)
这次发布中有很多与SIG-Scheduling相关的更改。其中,以下两个变更尤为重要。
-
- KEP-1287: In-place Update of Pod Resources
- KEP-3063: Dynamic resource allocation
KEP-1287: Pod资源的原地更新
至今为止,无法更改分配给pod的计算资源量,也就是Pod资源的.spec.containers[].resources字段的值。因此,如果想要改变分配的计算资源量,就需要指定一个新值并重新创建pod。
在不重新创建pod的情况下,可以通过In-place Update of Pod Resources来更改分配给该容器的计算资源量。这意味着pod的in-place垂直扩展变得可能。使用这个功能,可以更容易地调整分配给代价高昂的pod(如数据库或运行时间长的批处理作业)的计算资源量,避免重新创建的成本。
这个功能从2018年左右开始提出,由于涉及到CRI的更改等,它是一个非常具有影响力的功能,但在Kubernetes 1.27中已经作为Alpha版本被收录进来了。
现在似乎正致力于将其升级为Beta版本,希望在Kubernetes 1.29中实现这一目标。
在Beta版本中,将会添加一个名为/resize的子资源到Pod资源中,通过这个资源可以请求计算资源量的变更。
动态资源分配
动态资源分配是一种管理分配GPU、FPGA等扩展计算资源的功能。与当前的设备插件相比,它更加灵活,可以处理与节点无关的计算资源。
Kubernetes 1.26中引入了这个功能作为Alpha版,但是在Kubernetes 1.27中也在进行开发。
由于SIG-Node是主要处理此功能的团队,因此详细的说明请参考SIG-Node的文章。
此外,Kubernetes官方文档中也有相关说明:动态资源分配| Kubernetes。
紧急升级注意事项(必须先阅读再进行升级的事项)
关于SIG-Scheduling的内容不存在。
种类别的变化
不再推荐
关于SIG-Scheduling的内容没有。
API改动
-
- Pod のコンディションの DisruptionTarget type について、PreemptionByKubeScheduler という reason が PreemptionByScheduler に変更されました。(#114623, @Huang-Wei)
DisruptionTarget は Kubernetes 1.25 から導入された type です (Disruptions | Kubernetes)。Kubernetes 1.27 からは、このコンディションの reason が PreemptedByScheduler であることで、その pod がプリエンプションされたことを判定するようになりました。
resource.k8s.io/v1alpha1.PodScheduling は resource.k8s.io/v1alpha2.PodSchedulingContext に改名されました。(#116556, @pohly)
Dynaic Resource Allocation の API で、pod のスケジューリングに関わる情報をコントロールプレーンとリソースのドライバとのあいだで調整するために使われます。
InterPodAffinity スケジューラプラグインに、いまスケジュール処理中の pod が preferred inter-pod affinity をもっていない場合、クラスタ上にすでにある pod の inter-pod affinity を無視するオプションを追加しました。このオプションを有効にすると、スケジューリングのスループットを向上させられる可能性があります(代わりに、クラスタ上の pod がもつ inter-pod affinity に対して最適でないスケジューリング結果になる、あるいは違反する可能性があります)。このオプションを有効にするには、InterPodAffinity プラグインのオプションで ignorePreferredTermsOfExistingPods: true と設定します。(#114393, @danielvegamyhre)
Inter-pod affinity は、2 つの pod 群のあいだで双方向に設定されることが多いです。つまり、いまスケジュール処理中の pod が preferred inter-pod affinity をもたない場合、クラスタ上の pod はスケジュール処理中の pod に対する inter-pod affinity をもたない可能性が高いです。このとき、クラスタ上の pod をすべて参照して inter-pod affinity をチェックすることは無駄な処理になります。本オプションを有効にすることで、クラスタ上の pod 数に比例する計算を削減することができます。
Pod の topologySpreadConstraints フィールドにおいて、labelSelector が設定されていないとき、matchLabelKeys の指定を禁止するようになりました。(#116535, @denkensk)
matchLabelKeys による pod の選択は labelSelector による選択と AND で組み合わされ、labelSelector が未指定 (null) のときはどの pod も選択しないので、matchLabelKeys だけを指定することには意味がありません。
resource.k8s.io API の AllocationResult struct に破壊的変更が入りました。この変更により、Dynamic resource allocation をおこなう kubelet プラグインで、複数のリソースのドライバからリソースを割り当てることができるようになります。(#116332, @klueska)
リーダー選出をおこなう Kubernetes のコンポーネントが、 Leases API を使う方法のみをサポートするようになりました。(#114055, @aimuz)
kube-scheduler に加え、kube-controller-manager にもこの変更が入っています。
Pod Scheduling Readiness で gate されている pod について、node selector と node affinity が可変になりました(追加のみが可能で、削除と既存の設定の更新はできません)。(#116161, @danielvegamyhre)
ユースケースの例として、ワークロードをキューイングし、ワークロードを実行するタイミングと場所を動的に制御するコントローラを構築するケースなどが考えられています。
DynamicResourceManagement の kubeletplugin API について、v1alpha1 バージョンのサポートが削除されました。すべてのプラグインは v1alpha2 バージョンを使うよう更新する必要があります。(#116558, @klueska)
/metrics/slis がコントロールプレーンのコンポーネントで使用可能になり、ヘルスチェックのためのメトリクスをスクレイプできるようになりました。(#114997, @Richabanker)
メトリクスの定義など詳細はこちらを参照してください:Kubernetes Component SLI Metrics | Kubernetes
NodeResourceFit と NodeResourcesBalancedAllocation スケジューラプラグインが、PreScore 拡張点を使いより効率よく pod の要求リソース量の計算をおこなうようになりました。(#115655, @tangwz)
Pod に含まれるコンテナの要求リソース量を合計する計算について、pod ごとに一度のみおこなうようになりました。これまでは、同じ計算を Score 拡張点でノード数だけおこなっていました。
PodSchedulingReadiness がベータに昇格しました。(#115815, @Huang-Wei)
Pod Scheduling Readiness についてはこちらを参照してください:Pod Scheduling Readiness | Kubernetes
PodSpec.Container.Resources フィールドが、CPU とメモリについて可変になりました。
PodSpec.Container.ResizePolicy フィールドが追加され、コンテナのリサイズ(割り当てるリソース量の変更)をどうおこなうか制御できるようになりました。
PodStatus.Resize フィールドが追加され、pod のリサイズの状態が記述されるようになりました。
PodStatus.ResourcesAllocated フィールドが追加され、pod に割り当てられているノードのリソースが記述されるようになりました。
リリースノートには PodStatus.ResourcesAllocated とありますが、おそらく PodStatus.ContainerStatuses.AllocatedResources のことだと思われます。
PodStatus.Resources フィールドが追加され、CRI が実行中のコンテナに適用したノードのリソースが記述されるようになりました。
リリースノートには PodStatus.Resources とありますが、おそらく PodStatus.ContainerStatuses.Resources のことだと思われます。
UpdateContainerResources CRI API が Linux と Windows の両方をサポートするようになりました。(#102884, @vinaykul)
以上、前述の In-place Update of Pod Resources に関わる Pod API の変更です。
resource.k8s.io/v1alpha1 が resource.k8s.io/v1alpha2 に置き換えられました。クラスタをアップグレードする前に、すべての resource.k8s.io/v1alpha1 バージョンのリソース (ResourceClaim, ResourceClaimTemplate, ResourceClass, PodScheduling) は削除する必要があります。この変更は内部的なものであるため、apiVersion を更新する以外に、pod や resource claim を作る YAML の変更は必要ありません。(#116299, @pohly)
功能延伸/增加特性
-
- アクセスモードが ReadWriteOncePod な PVC を使う pod のプリエンプションがサポートされました。(#114051, @chrishenzie)
-
- Pod Topology Spread Constraints の matchLabelKeys フィールドがベータに昇格しました。(#116291, @denkensk)
matchLabelKeys フィールドを使うと、pod 群をローリングアップグレードする際も topology spread constraints がうまく機能するようになります。詳しくはこちらを参照してください:KEP-3243: Respect PodTopologySpread after rolling upgrades
defaultbinder スケジューラプラグイン が contextual logging を使うようになりました。(#116571, @mengjiao-liu)
スケジューラに plugin_evaluation_total メトリックが追加されました。このメトリックは、各プラグインがスケジューリング結果に影響を及ぼした回数をカウントします。プラグインがスケジュール処理中の pod に対しておこなう処理が何もなかった場合は加算されません。(#115082, @sanposhiho)
現時点で PreFilter および Filter 拡張点がサポートされているようです。
スケジューラプラグインの PreFilter メソッドが Skip ステータスを返した場合、スケジューラはそのプラグインの Filter メソッドを呼ばないようになりました。つまり、PreFilter / Filter 拡張点を実装するプラグインは、Filter でおこなう処理が何もないとき、PreFilter で Skip ステータスを返すことができます。この機能追加に基づき、NodeAffinity プラグインが Filter でおこなう処理が何もないとき、スケジューラは NodeAffinity プラグインの Filter を呼ばないようになりました。この変更は、NodeAffinity プラグインの Filter に関するメトリクスに影響する可能性があります。(#114125, @sanposhiho)
また、InterPodAffinity プラグインが Filter でおこなう処理が何もないとき、スケジューラは InterPodAffinity プラグインの Filter を呼ばないようになりました。この変更は、InterPodAffinity プラグインの Filter に関するメトリクスに影響する可能性があります。(#114889, @sanposhiho)
今後、他のプラグインについても(適切な場合)PreFilter で Skip ステータスを返すようにしていくようです。
VolumeBinding スケジューラプラグインで、pod がノードローカルな PV への claim をもっているとき、PreFilterResult を使いその PV が利用可能なノードだけをフィルタ結果として返すようにしました。(#109877, @yibozhuang)
スケジューラプラグインが PostFilter メソッドで unschedulableAndUnresolvable を返したとき、スケジューラはその pod のスケジューリング処理を即時終了するようになりました。(#114699, @kerthcet)
Pod の .spec.schedulingGates[*].name フィールドは qualified name(例:example.com/mygate)でなければならなくなりました。.spec.readinessGates[*].name フィールドと同じルールが適用されます。Pod Scheduling Readiness(Kubernetes 1.27 より前ではアルファ)のユーザは、1.27 へのアップグレードをする前に違反している名前を修正または削除する必要があります。(#115821, @lianghao208)
スケジューラプラグインの PreScore メソッドが Skip ステータスを返した場合、スケジューラはそのプラグインの Score メソッドを呼ばないようになりました。つまり、PreScore / Score 拡張点を実装するプラグインは、Score でおこなう処理が何もないとき、PreScore で Skip ステータスを返すことができます。(#115652, @AxeZhan)
JobMutableNodeSchedulingDirectives 機能が GA に昇格しました。(#116116, @ahg-g)
サスペンドされ、まだ開始もしていない job の scheduling directive(pod template のノードアフィニティやノードセレクタなど)を可変にする機能です。詳しくはこちらを参照してください:KEP-2926: Allow updating scheduling directives of jobs
ReadWriteOncePod 機能がベータに昇格しました。(#114494, @chrishenzie)
ReadWriteOncePod は、PV へのアクセスをある一つのノード上のある一つの pod からに限定するアクセスモードです。詳しくはこちらを参照してください:KEP-2485: ReadWriteOncePod PersistentVolume AccessMode
スケジューラの plugin_execution_duration_seconds メトリックが、PreEnqueue 拡張点のプラグインの実行にかかった時間を記録するようになりました。(#116201, @sanposhiho)
PreEnqueue 拡張点は、Kubernetes 1.26 で追加されました。
MinDomainsInPodTopologySpread 機能がベータに昇格し、デフォルトで有効になりました。(#114445, @mengjiao-liu)
MinDomainsInPodTopologySpread は、その名の通り、Pod Topology Spread Constraints で許容する最小のドメイン数を設定できるようにする機能です。詳しくはこちらを参照してください:KEP-3022: min domains in Pod Topology Spread
Pod topology spread constraints において、labelSelector が null のときの計算が最適化されました。(#116607, @alculquicondor)
文件(文档改进)
SIG-Scheduling没有相关信息。
缺陷或回归(Bug修复)
-
- Pod がプリエンプションされたときのイベントのメッセージから、プリエンプター pod のメタデータを除きました。(#114923, @mimowo)
他のネームスペースの存在や、その中の pod 名が漏洩することを防ぐためです。
スケジューラで、ボリュームのバインドが完了したことを誤って意味していたログを修正しました。(#116018, @TommyStarK)
スケジューラが Filter プラグインを常にすべて実行していたバグを修正しました。(#114518, @Huang-Wei)
本来は、ある Filter プラグインが失敗したらそこで処理を止めなければなりません。
スケジューラで、プリエンプション処理と pod の更新処理とのあいだにあった競合状態を修正しました。(#116395, @alculquicondor)
NodeVolumeLimits CSI のロギングにあった nil ポインタの参照を修正しました。(#115179, @sunnylovestiramisu)
メトリックの探索をクリティカルパスで頻繁におこなっていたことによる性能劣化を修正しました。(#116428, @mborsz)
DisruptionTarget type のコンディションのメッセージから、プリエンプター pod のメタデータを除きました。(#114914, @mimowo)
イベントのメッセージと同様の修正です。
プリエンプションのイベントのメッセージから、スケジューラの名前を除きました。(#114980, @mimowo)
プリエンプター pod のスケジュール処理をおこなったスケジューラの名前を除くようになりました。スケジューラの名前も漏洩することを防ぐためのようです。
schedulingGates が空でない場合、nodeName を指定することを禁止するようになりました。(#115569, @Huang-Wei)
この変更は、Pod Scheduling Readiness が有効化されているかどうかによらず適用されます。
其他(清理或削片)
–contention-profiling フラグのドキュメントを修正し、このフラグが block profiling をおこなうことを反映しました。(#114490, @MadhavJivrajani)
文面を “lock contention” から “block profiling” に書き換えた変更です。なお、このフラグは非推奨です。
Pod のリソースの request / limit 量のメトリクスが stable に昇格しました。(#115454, @dgrisonnet)
In-tree の Azure disk ストレージ用のプラグインを削除しました。(#116301, @andyzhangx)
scheduler_e2e_scheduling_duration_seconds メトリックが削除され、scheduler_scheduling_attempt_duration_seconds メトリックで置き換えられました。(#115209, @dgrisonnet)
削除されたのは Kubernetes 1.23.0 から非推奨だったメトリックです。