mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-08-09 12:07:47 +00:00
Merge pull request #118228 from carlory/move-non-graceful-node-shutdown-to-GA
move non-graceful node shutdown to GA
This commit is contained in:
commit
be2cfc9697
@ -127,9 +127,7 @@ func (gcc *PodGCController) gc(ctx context.Context) {
|
|||||||
if gcc.terminatedPodThreshold > 0 {
|
if gcc.terminatedPodThreshold > 0 {
|
||||||
gcc.gcTerminated(ctx, pods)
|
gcc.gcTerminated(ctx, pods)
|
||||||
}
|
}
|
||||||
if utilfeature.DefaultFeatureGate.Enabled(features.NodeOutOfServiceVolumeDetach) {
|
gcc.gcTerminating(ctx, pods)
|
||||||
gcc.gcTerminating(ctx, pods)
|
|
||||||
}
|
|
||||||
gcc.gcOrphaned(ctx, pods, nodes)
|
gcc.gcOrphaned(ctx, pods, nodes)
|
||||||
gcc.gcUnscheduledTerminating(ctx, pods)
|
gcc.gcUnscheduledTerminating(ctx, pods)
|
||||||
}
|
}
|
||||||
|
@ -503,7 +503,6 @@ func TestGCUnscheduledTerminating(t *testing.T) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func TestGCTerminating(t *testing.T) {
|
func TestGCTerminating(t *testing.T) {
|
||||||
defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NodeOutOfServiceVolumeDetach, true)()
|
|
||||||
type node struct {
|
type node struct {
|
||||||
name string
|
name string
|
||||||
readyCondition v1.ConditionStatus
|
readyCondition v1.ConditionStatus
|
||||||
|
@ -28,14 +28,12 @@ import (
|
|||||||
v1 "k8s.io/api/core/v1"
|
v1 "k8s.io/api/core/v1"
|
||||||
"k8s.io/apimachinery/pkg/types"
|
"k8s.io/apimachinery/pkg/types"
|
||||||
"k8s.io/apimachinery/pkg/util/wait"
|
"k8s.io/apimachinery/pkg/util/wait"
|
||||||
utilfeature "k8s.io/apiserver/pkg/util/feature"
|
|
||||||
corelisters "k8s.io/client-go/listers/core/v1"
|
corelisters "k8s.io/client-go/listers/core/v1"
|
||||||
"k8s.io/client-go/tools/record"
|
"k8s.io/client-go/tools/record"
|
||||||
"k8s.io/klog/v2"
|
"k8s.io/klog/v2"
|
||||||
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/cache"
|
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/cache"
|
||||||
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/metrics"
|
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/metrics"
|
||||||
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/statusupdater"
|
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/statusupdater"
|
||||||
"k8s.io/kubernetes/pkg/features"
|
|
||||||
kevents "k8s.io/kubernetes/pkg/kubelet/events"
|
kevents "k8s.io/kubernetes/pkg/kubelet/events"
|
||||||
"k8s.io/kubernetes/pkg/util/goroutinemap/exponentialbackoff"
|
"k8s.io/kubernetes/pkg/util/goroutinemap/exponentialbackoff"
|
||||||
nodeutil "k8s.io/kubernetes/pkg/util/node"
|
nodeutil "k8s.io/kubernetes/pkg/util/node"
|
||||||
@ -143,17 +141,13 @@ func (rc *reconciler) syncStates() {
|
|||||||
rc.attacherDetacher.VerifyVolumesAreAttached(volumesPerNode, rc.actualStateOfWorld)
|
rc.attacherDetacher.VerifyVolumesAreAttached(volumesPerNode, rc.actualStateOfWorld)
|
||||||
}
|
}
|
||||||
|
|
||||||
// hasOutOfServiceTaint returns true if the node has out-of-service taint present
|
// hasOutOfServiceTaint returns true if the node has out-of-service taint present.
|
||||||
// and `NodeOutOfServiceVolumeDetach` feature gate is enabled.
|
|
||||||
func (rc *reconciler) hasOutOfServiceTaint(nodeName types.NodeName) (bool, error) {
|
func (rc *reconciler) hasOutOfServiceTaint(nodeName types.NodeName) (bool, error) {
|
||||||
if utilfeature.DefaultFeatureGate.Enabled(features.NodeOutOfServiceVolumeDetach) {
|
node, err := rc.nodeLister.Get(string(nodeName))
|
||||||
node, err := rc.nodeLister.Get(string(nodeName))
|
if err != nil {
|
||||||
if err != nil {
|
return false, err
|
||||||
return false, err
|
|
||||||
}
|
|
||||||
return taints.TaintKeyExists(node.Spec.Taints, v1.TaintNodeOutOfService), nil
|
|
||||||
}
|
}
|
||||||
return false, nil
|
return taints.TaintKeyExists(node.Spec.Taints, v1.TaintNodeOutOfService), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// nodeIsHealthy returns true if the node looks healthy.
|
// nodeIsHealthy returns true if the node looks healthy.
|
||||||
|
@ -27,10 +27,8 @@ import (
|
|||||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
k8stypes "k8s.io/apimachinery/pkg/types"
|
k8stypes "k8s.io/apimachinery/pkg/types"
|
||||||
"k8s.io/apimachinery/pkg/util/wait"
|
"k8s.io/apimachinery/pkg/util/wait"
|
||||||
utilfeature "k8s.io/apiserver/pkg/util/feature"
|
|
||||||
"k8s.io/client-go/informers"
|
"k8s.io/client-go/informers"
|
||||||
"k8s.io/client-go/tools/record"
|
"k8s.io/client-go/tools/record"
|
||||||
featuregatetesting "k8s.io/component-base/featuregate/testing"
|
|
||||||
"k8s.io/component-base/metrics/legacyregistry"
|
"k8s.io/component-base/metrics/legacyregistry"
|
||||||
metricstestutil "k8s.io/component-base/metrics/testutil"
|
metricstestutil "k8s.io/component-base/metrics/testutil"
|
||||||
"k8s.io/klog/v2"
|
"k8s.io/klog/v2"
|
||||||
@ -40,7 +38,6 @@ import (
|
|||||||
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/metrics"
|
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/metrics"
|
||||||
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/statusupdater"
|
"k8s.io/kubernetes/pkg/controller/volume/attachdetach/statusupdater"
|
||||||
controllervolumetesting "k8s.io/kubernetes/pkg/controller/volume/attachdetach/testing"
|
controllervolumetesting "k8s.io/kubernetes/pkg/controller/volume/attachdetach/testing"
|
||||||
"k8s.io/kubernetes/pkg/features"
|
|
||||||
volumetesting "k8s.io/kubernetes/pkg/volume/testing"
|
volumetesting "k8s.io/kubernetes/pkg/volume/testing"
|
||||||
"k8s.io/kubernetes/pkg/volume/util/operationexecutor"
|
"k8s.io/kubernetes/pkg/volume/util/operationexecutor"
|
||||||
"k8s.io/kubernetes/pkg/volume/util/types"
|
"k8s.io/kubernetes/pkg/volume/util/types"
|
||||||
@ -863,7 +860,6 @@ func Test_Run_OneVolumeAttachAndDetachTimeoutNodesWithReadWriteOnce(t *testing.T
|
|||||||
// Deletes the pod from desiredStateOfWorld cache without first marking the node/volume as unmounted.
|
// Deletes the pod from desiredStateOfWorld cache without first marking the node/volume as unmounted.
|
||||||
// Verifies there is one detach call and no (new) attach calls.
|
// Verifies there is one detach call and no (new) attach calls.
|
||||||
func Test_Run_OneVolumeDetachOnOutOfServiceTaintedNode(t *testing.T) {
|
func Test_Run_OneVolumeDetachOnOutOfServiceTaintedNode(t *testing.T) {
|
||||||
defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NodeOutOfServiceVolumeDetach, true)()
|
|
||||||
registerMetrics.Do(func() {
|
registerMetrics.Do(func() {
|
||||||
legacyregistry.MustRegister(metrics.ForceDetachMetricCounter)
|
legacyregistry.MustRegister(metrics.ForceDetachMetricCounter)
|
||||||
})
|
})
|
||||||
@ -951,7 +947,6 @@ func Test_Run_OneVolumeDetachOnOutOfServiceTaintedNode(t *testing.T) {
|
|||||||
// Deletes the pod from desiredStateOfWorld cache without first marking the node/volume as unmounted.
|
// Deletes the pod from desiredStateOfWorld cache without first marking the node/volume as unmounted.
|
||||||
// Verifies there is no detach call and no (new) attach calls.
|
// Verifies there is no detach call and no (new) attach calls.
|
||||||
func Test_Run_OneVolumeDetachOnNoOutOfServiceTaintedNode(t *testing.T) {
|
func Test_Run_OneVolumeDetachOnNoOutOfServiceTaintedNode(t *testing.T) {
|
||||||
defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NodeOutOfServiceVolumeDetach, true)()
|
|
||||||
// Arrange
|
// Arrange
|
||||||
volumePluginMgr, fakePlugin := volumetesting.GetTestVolumePluginMgr(t)
|
volumePluginMgr, fakePlugin := volumetesting.GetTestVolumePluginMgr(t)
|
||||||
dsw := cache.NewDesiredStateOfWorld(volumePluginMgr)
|
dsw := cache.NewDesiredStateOfWorld(volumePluginMgr)
|
||||||
|
@ -561,6 +561,7 @@ const (
|
|||||||
// kep: https://kep.k8s.io/2268
|
// kep: https://kep.k8s.io/2268
|
||||||
// alpha: v1.24
|
// alpha: v1.24
|
||||||
// beta: v1.26
|
// beta: v1.26
|
||||||
|
// GA: v1.28
|
||||||
//
|
//
|
||||||
// Allow pods to failover to a different node in case of non graceful node shutdown
|
// Allow pods to failover to a different node in case of non graceful node shutdown
|
||||||
NodeOutOfServiceVolumeDetach featuregate.Feature = "NodeOutOfServiceVolumeDetach"
|
NodeOutOfServiceVolumeDetach featuregate.Feature = "NodeOutOfServiceVolumeDetach"
|
||||||
@ -1007,7 +1008,7 @@ var defaultKubernetesFeatureGates = map[featuregate.Feature]featuregate.FeatureS
|
|||||||
|
|
||||||
NodeLogQuery: {Default: false, PreRelease: featuregate.Alpha},
|
NodeLogQuery: {Default: false, PreRelease: featuregate.Alpha},
|
||||||
|
|
||||||
NodeOutOfServiceVolumeDetach: {Default: true, PreRelease: featuregate.Beta},
|
NodeOutOfServiceVolumeDetach: {Default: true, PreRelease: featuregate.GA, LockToDefault: true}, // remove in 1.31
|
||||||
|
|
||||||
NodeSwap: {Default: false, PreRelease: featuregate.Alpha},
|
NodeSwap: {Default: false, PreRelease: featuregate.Alpha},
|
||||||
|
|
||||||
|
@ -177,7 +177,6 @@ func TestTerminatingOnOutOfServiceNode(t *testing.T) {
|
|||||||
for name, test := range tests {
|
for name, test := range tests {
|
||||||
t.Run(name, func(t *testing.T) {
|
t.Run(name, func(t *testing.T) {
|
||||||
defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.PodDisruptionConditions, test.enablePodDisruptionConditions)()
|
defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.PodDisruptionConditions, test.enablePodDisruptionConditions)()
|
||||||
defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NodeOutOfServiceVolumeDetach, true)()
|
|
||||||
testCtx := setup(t, "podgc-out-of-service")
|
testCtx := setup(t, "podgc-out-of-service")
|
||||||
cs := testCtx.ClientSet
|
cs := testCtx.ClientSet
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user