| /* |
| Copyright 2015 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 qos |
| |
| import ( |
| "k8s.io/api/core/v1" |
| "k8s.io/apimachinery/pkg/api/resource" |
| "k8s.io/apimachinery/pkg/util/sets" |
| "k8s.io/kubernetes/pkg/apis/core" |
| ) |
| |
| var supportedQoSComputeResources = sets.NewString(string(core.ResourceCPU), string(core.ResourceMemory)) |
| |
| // QOSList is a set of (resource name, QoS class) pairs. |
| type QOSList map[v1.ResourceName]v1.PodQOSClass |
| |
| func isSupportedQoSComputeResource(name v1.ResourceName) bool { |
| return supportedQoSComputeResources.Has(string(name)) |
| } |
| |
| // GetPodQOS returns the QoS class of a pod. |
| // A pod is besteffort if none of its containers have specified any requests or limits. |
| // A pod is guaranteed only when requests and limits are specified for all the containers and they are equal. |
| // A pod is burstable if limits and requests do not match across all containers. |
| func GetPodQOS(pod *v1.Pod) v1.PodQOSClass { |
| requests := v1.ResourceList{} |
| limits := v1.ResourceList{} |
| zeroQuantity := resource.MustParse("0") |
| isGuaranteed := true |
| for _, container := range pod.Spec.Containers { |
| // process requests |
| for name, quantity := range container.Resources.Requests { |
| if !isSupportedQoSComputeResource(name) { |
| continue |
| } |
| if quantity.Cmp(zeroQuantity) == 1 { |
| delta := quantity.Copy() |
| if _, exists := requests[name]; !exists { |
| requests[name] = *delta |
| } else { |
| delta.Add(requests[name]) |
| requests[name] = *delta |
| } |
| } |
| } |
| // process limits |
| qosLimitsFound := sets.NewString() |
| for name, quantity := range container.Resources.Limits { |
| if !isSupportedQoSComputeResource(name) { |
| continue |
| } |
| if quantity.Cmp(zeroQuantity) == 1 { |
| qosLimitsFound.Insert(string(name)) |
| delta := quantity.Copy() |
| if _, exists := limits[name]; !exists { |
| limits[name] = *delta |
| } else { |
| delta.Add(limits[name]) |
| limits[name] = *delta |
| } |
| } |
| } |
| |
| if !qosLimitsFound.HasAll(string(v1.ResourceMemory), string(v1.ResourceCPU)) { |
| isGuaranteed = false |
| } |
| } |
| if len(requests) == 0 && len(limits) == 0 { |
| return v1.PodQOSBestEffort |
| } |
| // Check is requests match limits for all resources. |
| if isGuaranteed { |
| for name, req := range requests { |
| if lim, exists := limits[name]; !exists || lim.Cmp(req) != 0 { |
| isGuaranteed = false |
| break |
| } |
| } |
| } |
| if isGuaranteed && |
| len(requests) == len(limits) { |
| return v1.PodQOSGuaranteed |
| } |
| return v1.PodQOSBurstable |
| } |