kubectl: Make scaling smarter

Skip updating resources that already meet the desired replica count.
This change has an impact in both kubectl scale and kubectl delete in
that reapable resources that already have the desired replicas (number
provided via --replicas for scale, or zero for delete) won't be updated
again and a "already scaled" message will be printed (in case of scale).
This commit is contained in:
Michail Kargakis
2015-12-03 19:53:40 +01:00
parent 439d7a721e
commit e894dcc8ff
6 changed files with 548 additions and 298 deletions

View File

@@ -132,6 +132,31 @@ func TestReplicationControllerScaleFailsPreconditions(t *testing.T) {
}
}
func TestReplicationControllerAlreadyScaled(t *testing.T) {
fake := testclient.NewSimpleFake(&api.ReplicationController{
Spec: api.ReplicationControllerSpec{
Replicas: 3,
},
})
scaler := ReplicationControllerScaler{fake}
count := uint(3)
name := "foo"
err := scaler.Scale("default", name, count, nil, nil, nil)
if err == nil {
t.Fatal("expected AlreadyScaled error, got nil")
}
if scaleErr, ok := err.(ScaleError); !ok || scaleErr.FailureType != AlreadyScaled {
t.Fatalf("expected AlreadyScaled error, got %s", scaleErr.FailureType)
}
actions := fake.Actions()
if len(actions) != 1 {
t.Fatalf("unexpected actions: %v, expected 1 action (get)", actions)
}
if action, ok := actions[0].(testclient.GetAction); !ok || action.GetResource() != "replicationcontrollers" || action.GetName() != name {
t.Errorf("unexpected action: %v, expected get-replicationController %s", actions[0], name)
}
}
func TestValidateReplicationController(t *testing.T) {
tests := []struct {
preconditions ScalePrecondition
@@ -362,6 +387,32 @@ func TestJobScaleFailsPreconditions(t *testing.T) {
}
}
func TestJobAlreadyScaled(t *testing.T) {
three := 3
fake := testclient.NewSimpleFake(&extensions.Job{
Spec: extensions.JobSpec{
Parallelism: &three,
},
})
scaler := JobScaler{&testclient.FakeExperimental{fake}}
count := uint(3)
name := "foo"
err := scaler.Scale("default", name, count, nil, nil, nil)
if err == nil {
t.Fatal("expected AlreadyScaled error, got nil")
}
if scaleErr, ok := err.(ScaleError); !ok || scaleErr.FailureType != AlreadyScaled {
t.Fatalf("expected AlreadyScaled error, got %s", scaleErr.FailureType)
}
actions := fake.Actions()
if len(actions) != 1 {
t.Fatalf("unexpected actions: %v, expected 1 action (get)", actions)
}
if action, ok := actions[0].(testclient.GetAction); !ok || action.GetResource() != "jobs" || action.GetName() != name {
t.Errorf("unexpected action: %v, expected get-job %s", actions[0], name)
}
}
func TestValidateJob(t *testing.T) {
zero, ten, twenty := 0, 10, 20
tests := []struct {
@@ -626,6 +677,31 @@ func TestDeploymentScaleFailsPreconditions(t *testing.T) {
}
}
func TestDeploymentAlreadyScaled(t *testing.T) {
fake := testclient.NewSimpleFake(&extensions.Deployment{
Spec: extensions.DeploymentSpec{
Replicas: 3,
},
})
scaler := DeploymentScaler{&testclient.FakeExperimental{fake}}
count := uint(3)
name := "foo"
err := scaler.Scale("default", name, count, nil, nil, nil)
if err == nil {
t.Fatal("expected AlreadyScaled error, got nil")
}
if scaleErr, ok := err.(ScaleError); !ok || scaleErr.FailureType != AlreadyScaled {
t.Fatalf("expected AlreadyScaled error, got %s", scaleErr.FailureType)
}
actions := fake.Actions()
if len(actions) != 1 {
t.Fatalf("unexpected actions: %v, expected 1 action (get)", actions)
}
if action, ok := actions[0].(testclient.GetAction); !ok || action.GetResource() != "deployments" || action.GetName() != name {
t.Errorf("unexpected action: %v, expected get-deployment %s", actions[0], name)
}
}
func TestValidateDeployment(t *testing.T) {
zero, ten, twenty := 0, 10, 20
tests := []struct {