Skip to content

Commit

Permalink
refactored TestComputeDesiredFleetSize and TestApplyBufferPolicy
Browse files Browse the repository at this point in the history
  • Loading branch information
alexey-kremsa-globant committed May 11, 2020
1 parent 465adf4 commit f2cb6bd
Show file tree
Hide file tree
Showing 2 changed files with 226 additions and 93 deletions.
5 changes: 2 additions & 3 deletions pkg/fleetautoscalers/fleetautoscalers.go
Original file line number Diff line number Diff line change
Expand Up @@ -42,15 +42,14 @@ var client = http.Client{

// computeDesiredFleetSize computes the new desired size of the given fleet
func computeDesiredFleetSize(fas *autoscalingv1.FleetAutoscaler, f *agonesv1.Fleet) (int32, bool, error) {

switch fas.Spec.Policy.Type {
case autoscalingv1.BufferPolicyType:
return applyBufferPolicy(fas.Spec.Policy.Buffer, f)
case autoscalingv1.WebhookPolicyType:
return applyWebhookPolicy(fas.Spec.Policy.Webhook, f)
}

return f.Status.Replicas, false, errors.New("wrong policy type, should be one of: Buffer, Webhook")
return 0, false, errors.New("wrong policy type, should be one of: Buffer, Webhook")
}

func applyWebhookPolicy(w *autoscalingv1.WebhookPolicy, f *agonesv1.Fleet) (int32, bool, error) {
Expand Down Expand Up @@ -183,7 +182,7 @@ func applyBufferPolicy(b *autoscalingv1.BufferPolicy, f *agonesv1.Fleet) (int32,
// it means that allocated must be 70% and adjust the fleet size to make that true.
bufferPercent, err := intstr.GetValueFromIntOrPercent(&b.BufferSize, 100, true)
if err != nil {
return f.Status.Replicas, false, err
return 0, false, err
}
// use Math.Ceil to round the result up
replicas = int32(math.Ceil(float64(f.Status.AllocatedReplicas*100) / float64(100-bufferPercent)))
Expand Down
314 changes: 224 additions & 90 deletions pkg/fleetautoscalers/fleetautoscalers_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,96 +35,6 @@ const (
scaleFactor = 2
)

func TestComputeDesiredFleetSize(t *testing.T) {
t.Parallel()

fas, f := defaultFixtures()

fas.Spec.Policy.Buffer.BufferSize = intstr.FromInt(20)
fas.Spec.Policy.Buffer.MaxReplicas = 100
f.Spec.Replicas = 50
f.Status.Replicas = f.Spec.Replicas
f.Status.AllocatedReplicas = 40
f.Status.ReadyReplicas = 10

replicas, limited, err := computeDesiredFleetSize(fas, f)
assert.Nil(t, err)
assert.Equal(t, replicas, int32(60))
assert.Equal(t, limited, false)

// test empty Policy Type
f.Status.Replicas = 61
fas.Spec.Policy.Type = ""
replicas, limited, err = computeDesiredFleetSize(fas, f)
assert.NotNil(t, err)
assert.Equal(t, replicas, int32(61))
assert.Equal(t, limited, false)
}

func TestApplyBufferPolicy(t *testing.T) {
t.Parallel()

fas, f := defaultFixtures()
b := fas.Spec.Policy.Buffer

b.BufferSize = intstr.FromInt(20)
b.MaxReplicas = 100
f.Spec.Replicas = 50
f.Status.Replicas = f.Spec.Replicas
f.Status.AllocatedReplicas = 40
f.Status.ReadyReplicas = 10

replicas, limited, err := applyBufferPolicy(b, f)
assert.Nil(t, err)
assert.Equal(t, replicas, int32(60))
assert.Equal(t, limited, false)

b.MinReplicas = 65
f.Spec.Replicas = 50
f.Status.Replicas = f.Spec.Replicas
f.Status.AllocatedReplicas = 40
f.Status.ReadyReplicas = 10
replicas, limited, err = applyBufferPolicy(b, f)
assert.Nil(t, err)
assert.Equal(t, replicas, int32(65))
assert.Equal(t, limited, true)

b.MinReplicas = 0
b.MaxReplicas = 55
f.Spec.Replicas = 50
f.Status.Replicas = f.Spec.Replicas
f.Status.AllocatedReplicas = 40
f.Status.ReadyReplicas = 10
replicas, limited, err = applyBufferPolicy(b, f)
assert.Nil(t, err)
assert.Equal(t, replicas, int32(55))
assert.Equal(t, limited, true)

b.BufferSize = intstr.FromString("20%")
b.MinReplicas = 0
b.MaxReplicas = 100
f.Spec.Replicas = 50
f.Status.Replicas = f.Spec.Replicas
f.Status.AllocatedReplicas = 50
f.Status.ReadyReplicas = 0
replicas, limited, err = applyBufferPolicy(b, f)
assert.Nil(t, err)
assert.Equal(t, replicas, int32(63))
assert.Equal(t, limited, false)

b.BufferSize = intstr.FromString("10%")
b.MinReplicas = 0
b.MaxReplicas = 10
f.Spec.Replicas = 1
f.Status.Replicas = f.Spec.Replicas
f.Status.AllocatedReplicas = 1
f.Status.ReadyReplicas = 0
replicas, limited, err = applyBufferPolicy(b, f)
assert.Nil(t, err)
assert.Equal(t, replicas, int32(2))
assert.Equal(t, limited, false)
}

type testServer struct{}

func (t testServer) ServeHTTP(w http.ResponseWriter, r *http.Request) {
Expand Down Expand Up @@ -186,6 +96,230 @@ func (t testServer) ServeHTTP(w http.ResponseWriter, r *http.Request) {
}
}

func TestComputeDesiredFleetSize(t *testing.T) {
t.Parallel()

fas, f := defaultFixtures()

type expected struct {
replicas int32
limited bool
err string
}

var testCases = []struct {
description string
specReplicas int32
statusReplicas int32
statusAllocatedReplicas int32
statusReadyReplicas int32
policy autoscalingv1.FleetAutoscalerPolicy
expected expected
}{
{
description: "Increase replicas",
specReplicas: 50,
statusReplicas: 50,
statusAllocatedReplicas: 40,
statusReadyReplicas: 10,
policy: autoscalingv1.FleetAutoscalerPolicy{
Type: autoscalingv1.BufferPolicyType,
Buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromInt(20),
MaxReplicas: 100,
},
},
expected: expected{
replicas: 60,
limited: false,
err: "",
},
},
{
description: "Wrong policy",
specReplicas: 50,
statusReplicas: 60,
statusAllocatedReplicas: 40,
statusReadyReplicas: 10,
policy: autoscalingv1.FleetAutoscalerPolicy{
Type: "",
Buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromInt(20),
MaxReplicas: 100,
},
},
expected: expected{
replicas: 0,
limited: false,
err: "wrong policy type, should be one of: Buffer, Webhook",
},
},
}

for _, tc := range testCases {
t.Run(tc.description, func(t *testing.T) {
fas.Spec.Policy = tc.policy
f.Spec.Replicas = tc.specReplicas
f.Status.Replicas = tc.statusReplicas
f.Status.AllocatedReplicas = tc.statusAllocatedReplicas
f.Status.ReadyReplicas = tc.statusReadyReplicas

replicas, limited, err := computeDesiredFleetSize(fas, f)

if tc.expected.err != "" && assert.NotNil(t, err) {
assert.Equal(t, tc.expected.err, err.Error())
} else {
assert.Nil(t, err)
assert.Equal(t, tc.expected.replicas, replicas)
assert.Equal(t, tc.expected.limited, limited)
}
})
}
}

func TestApplyBufferPolicy(t *testing.T) {
t.Parallel()

_, f := defaultFixtures()

type expected struct {
replicas int32
limited bool
err string
}

var testCases = []struct {
description string
specReplicas int32
statusReplicas int32
statusAllocatedReplicas int32
statusReadyReplicas int32
buffer *autoscalingv1.BufferPolicy
expected expected
}{
{
description: "Increase replicas",
specReplicas: 50,
statusReplicas: 50,
statusAllocatedReplicas: 40,
statusReadyReplicas: 10,
buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromInt(20),
MaxReplicas: 100,
},
expected: expected{
replicas: 60,
limited: false,
err: "",
},
},
{
description: "Min replicas set, limited == true",
specReplicas: 50,
statusReplicas: 50,
statusAllocatedReplicas: 40,
statusReadyReplicas: 10,
buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromInt(20),
MinReplicas: 65,
MaxReplicas: 100,
},
expected: expected{
replicas: 65,
limited: true,
err: "",
},
},
{
description: "Replicas == max",
specReplicas: 50,
statusReplicas: 50,
statusAllocatedReplicas: 40,
statusReadyReplicas: 10,
buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromInt(20),
MinReplicas: 0,
MaxReplicas: 55,
},
expected: expected{
replicas: 55,
limited: true,
err: "",
},
},
{
description: "FromString buffer size, scale up",
specReplicas: 50,
statusReplicas: 50,
statusAllocatedReplicas: 50,
statusReadyReplicas: 0,
buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromString("20%"),
MinReplicas: 0,
MaxReplicas: 100,
},
expected: expected{
replicas: 63,
limited: false,
err: "",
},
},
{
description: "FromString buffer size, scale up twice",
specReplicas: 1,
statusReplicas: 1,
statusAllocatedReplicas: 1,
statusReadyReplicas: 0,
buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromString("10%"),
MinReplicas: 0,
MaxReplicas: 10,
},
expected: expected{
replicas: 2,
limited: false,
err: "",
},
},
{
description: "FromString buffer size is invalid, err received",
specReplicas: 1,
statusReplicas: 1,
statusAllocatedReplicas: 1,
statusReadyReplicas: 0,
buffer: &autoscalingv1.BufferPolicy{
BufferSize: intstr.FromString("asd"),
MinReplicas: 0,
MaxReplicas: 10,
},
expected: expected{
replicas: 0,
limited: false,
err: "invalid value for IntOrString: invalid value \"asd\": strconv.Atoi: parsing \"asd\": invalid syntax",
},
},
}

for _, tc := range testCases {
t.Run(tc.description, func(t *testing.T) {
f.Spec.Replicas = tc.specReplicas
f.Status.Replicas = tc.statusReplicas
f.Status.AllocatedReplicas = tc.statusAllocatedReplicas
f.Status.ReadyReplicas = tc.statusReadyReplicas

replicas, limited, err := applyBufferPolicy(tc.buffer, f)

if tc.expected.err != "" && assert.NotNil(t, err) {
assert.Equal(t, tc.expected.err, err.Error())
} else {
assert.Nil(t, err)
assert.Equal(t, tc.expected.replicas, replicas)
assert.Equal(t, tc.expected.limited, limited)
}
})
}
}

func TestApplyWebhookPolicy(t *testing.T) {
t.Parallel()
ts := testServer{}
Expand Down

0 comments on commit f2cb6bd

Please sign in to comment.