Merge pull request #495 from aleksandra-malinowska/resource-limiter-bytes

Use bytes instead of MB for memory limits
This commit is contained in:
MaciekPytel 2018-06-08 14:47:22 +02:00 committed by GitHub
commit c41dc43704
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 44 additions and 26 deletions

View File

@ -158,7 +158,7 @@ const (
// ResourceNameCores is string name for cores. It's used by ResourceLimiter.
ResourceNameCores = "cpu"
// ResourceNameMemory is string name for memory. It's used by ResourceLimiter.
// Memory should always be provided in megabytes.
// Memory should always be provided in bytes.
ResourceNameMemory = "memory"
)

View File

@ -45,6 +45,7 @@ import (
"k8s.io/autoscaler/cluster-autoscaler/cloudprovider"
"k8s.io/autoscaler/cluster-autoscaler/config/dynamic"
"k8s.io/autoscaler/cluster-autoscaler/utils/gpu"
"k8s.io/autoscaler/cluster-autoscaler/utils/units"
provider_gce "k8s.io/kubernetes/pkg/cloudprovider/providers/gce"
)
@ -1097,12 +1098,12 @@ func (m *gceManagerImpl) fetchResourceLimiter() error {
maxLimits[limit.Name] = limit.Maximum
}
// GKE API provides memory in GB, but ResourceLimiter expects them in MB
// GKE API provides memory in GB, but ResourceLimiter expects them in bytes
if _, found := minLimits[cloudprovider.ResourceNameMemory]; found {
minLimits[cloudprovider.ResourceNameMemory] = minLimits[cloudprovider.ResourceNameMemory] * 1024
minLimits[cloudprovider.ResourceNameMemory] = minLimits[cloudprovider.ResourceNameMemory] * units.Gigabyte
}
if _, found := maxLimits[cloudprovider.ResourceNameMemory]; found {
maxLimits[cloudprovider.ResourceNameMemory] = maxLimits[cloudprovider.ResourceNameMemory] * 1024
maxLimits[cloudprovider.ResourceNameMemory] = maxLimits[cloudprovider.ResourceNameMemory] * units.Gigabyte
}
resourceLimiter := cloudprovider.NewResourceLimiter(minLimits, maxLimits)

View File

@ -22,6 +22,7 @@ import (
apiv1 "k8s.io/api/core/v1"
"k8s.io/autoscaler/cluster-autoscaler/utils/gpu"
"k8s.io/autoscaler/cluster-autoscaler/utils/units"
kubeletapis "k8s.io/kubernetes/pkg/kubelet/apis"
)
@ -36,7 +37,6 @@ const (
preemptibleDiscount = 0.00698 / 0.033174
gpuPricePerHour = 0.700
gigabyte = 1024.0 * 1024.0 * 1024.0
preemptibleLabel = "cloud.google.com/gke-preemptible"
)
@ -147,7 +147,7 @@ func getBasePrice(resources apiv1.ResourceList, startTime time.Time, endTime tim
cpu := resources[apiv1.ResourceCPU]
mem := resources[apiv1.ResourceMemory]
price += float64(cpu.MilliValue()) / 1000.0 * cpuPricePerHour * hours
price += float64(mem.Value()) / gigabyte * memoryPricePerHourPerGb * hours
price += float64(mem.Value()) / float64(units.Gigabyte) * memoryPricePerHourPerGb * hours
return price
}

View File

@ -69,9 +69,9 @@ type AutoscalingOptions struct {
MaxCoresTotal int64
// MinCoresTotal sets the minimum number of cores in the whole cluster
MinCoresTotal int64
// MaxMemoryTotal sets the maximum memory (in megabytes) in the whole cluster
// MaxMemoryTotal sets the maximum memory (in bytes) in the whole cluster
MaxMemoryTotal int64
// MinMemoryTotal sets the maximum memory (in megabytes) in the whole cluster
// MinMemoryTotal sets the maximum memory (in bytes) in the whole cluster
MinMemoryTotal int64
// NodeGroupAutoDiscovery represents one or more definition(s) of node group auto-discovery
NodeGroupAutoDiscovery []string

View File

@ -38,6 +38,7 @@ import (
kube_util "k8s.io/autoscaler/cluster-autoscaler/utils/kubernetes"
scheduler_util "k8s.io/autoscaler/cluster-autoscaler/utils/scheduler"
. "k8s.io/autoscaler/cluster-autoscaler/utils/test"
"k8s.io/autoscaler/cluster-autoscaler/utils/units"
"k8s.io/client-go/kubernetes/fake"
core "k8s.io/client-go/testing"
@ -865,7 +866,7 @@ var defaultScaleDownOptions = context.AutoscalingOptions{
MinCoresTotal: 0,
MinMemoryTotal: 0,
MaxCoresTotal: config.DefaultMaxClusterCores,
MaxMemoryTotal: config.DefaultMaxClusterMemory,
MaxMemoryTotal: config.DefaultMaxClusterMemory * units.Gigabyte,
}
func TestScaleDownEmptyMultipleNodeGroups(t *testing.T) {
@ -910,7 +911,7 @@ func TestScaleDownEmptyMinCoresLimitHit(t *testing.T) {
func TestScaleDownEmptyMinMemoryLimitHit(t *testing.T) {
options := defaultScaleDownOptions
options.MinMemoryTotal = 4000
options.MinMemoryTotal = 4000 * MB
config := &scaleTestConfig{
nodes: []nodeConfig{
{"n1", 2000, 1000 * MB, 0, true, "ng1"},
@ -1310,7 +1311,7 @@ func TestCalculateCoresAndMemoryTotal(t *testing.T) {
coresTotal, memoryTotal := calculateCoresAndMemoryTotal(nodes, time.Now())
assert.Equal(t, int64(42), coresTotal)
assert.Equal(t, int64(44000), memoryTotal)
assert.Equal(t, int64(44000*MB), memoryTotal)
}
func TestFilterOutMasters(t *testing.T) {

View File

@ -36,6 +36,7 @@ import (
"k8s.io/autoscaler/cluster-autoscaler/simulator"
kube_util "k8s.io/autoscaler/cluster-autoscaler/utils/kubernetes"
. "k8s.io/autoscaler/cluster-autoscaler/utils/test"
"k8s.io/autoscaler/cluster-autoscaler/utils/units"
apiv1 "k8s.io/api/core/v1"
extensionsv1 "k8s.io/api/extensions/v1beta1"
@ -52,7 +53,7 @@ import (
var defaultOptions = context.AutoscalingOptions{
EstimatorName: estimator.BinpackingEstimatorName,
MaxCoresTotal: config.DefaultMaxClusterCores,
MaxMemoryTotal: config.DefaultMaxClusterMemory,
MaxMemoryTotal: config.DefaultMaxClusterMemory * units.Gigabyte,
MinCoresTotal: 0,
MinMemoryTotal: 0,
}
@ -106,7 +107,7 @@ const MB = 1024 * 1024
func TestScaleUpMaxMemoryLimitHit(t *testing.T) {
options := defaultOptions
options.MaxMemoryTotal = 1300 // set in mb
options.MaxMemoryTotal = 1300 * MB
config := &scaleTestConfig{
nodes: []nodeConfig{
{"n1", 2000, 100 * MB, 0, true, "ng1"},

View File

@ -18,7 +18,6 @@ package core
import (
"fmt"
"math"
"math/rand"
"reflect"
"time"
@ -488,12 +487,6 @@ func ConfigurePredicateCheckerForLoop(unschedulablePods []*apiv1.Pod, schedulabl
}
}
// Getting node cores/memory
const (
// Megabyte is 2^20 bytes.
Megabyte float64 = 1024 * 1024
)
func getNodeCoresAndMemory(node *apiv1.Node) (int64, int64, error) {
cores, err := getNodeResource(node, apiv1.ResourceCPU)
if err != nil {
@ -509,8 +502,7 @@ func getNodeCoresAndMemory(node *apiv1.Node) (int64, int64, error) {
return 0, 0, fmt.Errorf("Invalid node CPU/memory values - cpu %v, memory %v", cores, memory)
}
memoryMb := math.Ceil(float64(memory) / Megabyte)
return cores, int64(memoryMb), nil
return cores, memory, nil
}
func getNodeResource(node *apiv1.Node, resource apiv1.ResourceName) (int64, error) {

View File

@ -599,7 +599,7 @@ func TestGetNodeCoresAndMemory(t *testing.T) {
cores, memory, err := getNodeCoresAndMemory(node)
assert.NoError(t, err)
assert.Equal(t, int64(2), cores)
assert.Equal(t, int64(2048), memory)
assert.Equal(t, int64(2048*MB), memory)
node.Status.Capacity = apiv1.ResourceList{}

View File

@ -40,6 +40,7 @@ import (
"k8s.io/autoscaler/cluster-autoscaler/simulator"
"k8s.io/autoscaler/cluster-autoscaler/utils/errors"
kube_util "k8s.io/autoscaler/cluster-autoscaler/utils/kubernetes"
"k8s.io/autoscaler/cluster-autoscaler/utils/units"
kube_client "k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
"k8s.io/client-go/tools/clientcmd"
@ -143,9 +144,9 @@ func createAutoscalingOptions() context.AutoscalingOptions {
if err != nil {
glog.Fatalf("Failed to parse flags: %v", err)
}
// Convert memory limits to megabytes.
minMemoryTotal = minMemoryTotal * 1024
maxMemoryTotal = maxMemoryTotal * 1024
// Convert memory limits to bytes.
minMemoryTotal = minMemoryTotal * units.Gigabyte
maxMemoryTotal = maxMemoryTotal * units.Gigabyte
return context.AutoscalingOptions{
CloudConfig: *cloudConfig,

View File

@ -0,0 +1,22 @@
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package units
const (
// Gigabyte is 2^30 bytes.
Gigabyte = 1024 * 1024 * 1024
)