mirror of https://github.com/k3s-io/k3s
Merge pull request #68015 from damemi/hpa-metrics-specificity
Support backwards compatibility for v1beta1 custom metrics clientpull/8/head
commit
99f319567a
|
@ -79039,11 +79039,6 @@
|
|||
},
|
||||
"io.k8s.api.autoscaling.v2beta2.MetricValueStatus": {
|
||||
"description": "MetricValueStatus holds the current value for a metric",
|
||||
"required": [
|
||||
"value",
|
||||
"averageValue",
|
||||
"averageUtilization"
|
||||
],
|
||||
"properties": {
|
||||
"averageUtilization": {
|
||||
"description": "currentAverageUtilization is the current value of the average of the resource metric across all relevant pods, represented as a percentage of the requested value of the resource for the pods.",
|
||||
|
|
|
@ -1840,11 +1840,6 @@
|
|||
"v2beta2.MetricValueStatus": {
|
||||
"id": "v2beta2.MetricValueStatus",
|
||||
"description": "MetricValueStatus holds the current value for a metric",
|
||||
"required": [
|
||||
"value",
|
||||
"averageValue",
|
||||
"averageUtilization"
|
||||
],
|
||||
"properties": {
|
||||
"value": {
|
||||
"type": "string",
|
||||
|
|
|
@ -28,6 +28,7 @@ import (
|
|||
"k8s.io/client-go/scale"
|
||||
"k8s.io/kubernetes/pkg/controller/podautoscaler"
|
||||
"k8s.io/kubernetes/pkg/controller/podautoscaler/metrics"
|
||||
|
||||
resourceclient "k8s.io/metrics/pkg/client/clientset/versioned/typed/metrics/v1beta1"
|
||||
"k8s.io/metrics/pkg/client/custom_metrics"
|
||||
"k8s.io/metrics/pkg/client/external_metrics"
|
||||
|
@ -48,9 +49,19 @@ func startHPAController(ctx ControllerContext) (http.Handler, bool, error) {
|
|||
|
||||
func startHPAControllerWithRESTClient(ctx ControllerContext) (http.Handler, bool, error) {
|
||||
clientConfig := ctx.ClientBuilder.ConfigOrDie("horizontal-pod-autoscaler")
|
||||
hpaClient := ctx.ClientBuilder.ClientOrDie("horizontal-pod-autoscaler")
|
||||
|
||||
apiVersionsGetter := custom_metrics.NewAvailableAPIsGetter(hpaClient.Discovery())
|
||||
// invalidate the discovery information roughly once per resync interval our API
|
||||
// information is *at most* two resync intervals old.
|
||||
go custom_metrics.PeriodicallyInvalidate(
|
||||
apiVersionsGetter,
|
||||
ctx.ComponentConfig.HPAController.HorizontalPodAutoscalerSyncPeriod.Duration,
|
||||
ctx.Stop)
|
||||
|
||||
metricsClient := metrics.NewRESTMetricsClient(
|
||||
resourceclient.NewForConfigOrDie(clientConfig),
|
||||
custom_metrics.NewForConfigOrDie(clientConfig),
|
||||
custom_metrics.NewForConfig(clientConfig, ctx.RESTMapper, apiVersionsGetter),
|
||||
external_metrics.NewForConfigOrDie(clientConfig),
|
||||
)
|
||||
return startHPAControllerWithMetricsClient(ctx, metricsClient)
|
||||
|
|
|
@ -1002,21 +1002,21 @@ span.icon > [class^="icon-"], span.icon > [class*=" icon-"] { cursor: default; }
|
|||
<tr>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">value</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">value is the current value of the metric (as a quantity).</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">true</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">false</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">string</p></td>
|
||||
<td class="tableblock halign-left valign-top"></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">averageValue</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">averageValue is the current value of the average of the metric across all relevant pods (as a quantity)</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">true</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">false</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">string</p></td>
|
||||
<td class="tableblock halign-left valign-top"></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">averageUtilization</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">currentAverageUtilization is the current value of the average of the resource metric across all relevant pods, represented as a percentage of the requested value of the resource for the pods.</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">true</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">false</p></td>
|
||||
<td class="tableblock halign-left valign-top"><p class="tableblock">integer (int32)</p></td>
|
||||
<td class="tableblock halign-left valign-top"></td>
|
||||
</tr>
|
||||
|
|
|
@ -259,31 +259,37 @@ message MetricTarget {
|
|||
optional string type = 1;
|
||||
|
||||
// value is the target value of the metric (as a quantity).
|
||||
// +optional
|
||||
optional k8s.io.apimachinery.pkg.api.resource.Quantity value = 2;
|
||||
|
||||
// averageValue is the target value of the average of the
|
||||
// metric across all relevant pods (as a quantity)
|
||||
// +optional
|
||||
optional k8s.io.apimachinery.pkg.api.resource.Quantity averageValue = 3;
|
||||
|
||||
// averageUtilization is the target value of the average of the
|
||||
// resource metric across all relevant pods, represented as a percentage of
|
||||
// the requested value of the resource for the pods.
|
||||
// Currently only valid for Resource metric source type
|
||||
// +optional
|
||||
optional int32 averageUtilization = 4;
|
||||
}
|
||||
|
||||
// MetricValueStatus holds the current value for a metric
|
||||
message MetricValueStatus {
|
||||
// value is the current value of the metric (as a quantity).
|
||||
// +optional
|
||||
optional k8s.io.apimachinery.pkg.api.resource.Quantity value = 1;
|
||||
|
||||
// averageValue is the current value of the average of the
|
||||
// metric across all relevant pods (as a quantity)
|
||||
// +optional
|
||||
optional k8s.io.apimachinery.pkg.api.resource.Quantity averageValue = 2;
|
||||
|
||||
// currentAverageUtilization is the current value of the average of the
|
||||
// resource metric across all relevant pods, represented as a percentage of
|
||||
// the requested value of the resource for the pods.
|
||||
// +optional
|
||||
optional int32 averageUtilization = 3;
|
||||
}
|
||||
|
||||
|
|
|
@ -200,16 +200,18 @@ type MetricTarget struct {
|
|||
// type represents whether the metric type is Utilization, Value, or AverageValue
|
||||
Type MetricTargetType `json:"type" protobuf:"bytes,1,name=type"`
|
||||
// value is the target value of the metric (as a quantity).
|
||||
Value *resource.Quantity `json:"value,omitempty" protobuf:"bytes,2,name=value"`
|
||||
// +optional
|
||||
Value *resource.Quantity `json:"value,omitempty" protobuf:"bytes,2,opt,name=value"`
|
||||
// averageValue is the target value of the average of the
|
||||
// metric across all relevant pods (as a quantity)
|
||||
AverageValue *resource.Quantity `json:"averageValue,omitempty" protobuf:"bytes,3,name=averageValue"`
|
||||
|
||||
// +optional
|
||||
AverageValue *resource.Quantity `json:"averageValue,omitempty" protobuf:"bytes,3,opt,name=averageValue"`
|
||||
// averageUtilization is the target value of the average of the
|
||||
// resource metric across all relevant pods, represented as a percentage of
|
||||
// the requested value of the resource for the pods.
|
||||
// Currently only valid for Resource metric source type
|
||||
AverageUtilization *int32 `json:"averageUtilization,omitempty" protobuf:"bytes,4,name=averageUtilization"`
|
||||
// +optional
|
||||
AverageUtilization *int32 `json:"averageUtilization,omitempty" protobuf:"bytes,4,opt,name=averageUtilization"`
|
||||
}
|
||||
|
||||
// MetricTargetType specifies the type of metric being targeted, and should be either
|
||||
|
@ -364,14 +366,17 @@ type ExternalMetricStatus struct {
|
|||
// MetricValueStatus holds the current value for a metric
|
||||
type MetricValueStatus struct {
|
||||
// value is the current value of the metric (as a quantity).
|
||||
Value *resource.Quantity `json:"value" protobuf:"bytes,1,name=value"`
|
||||
// +optional
|
||||
Value *resource.Quantity `json:"value,omitempty" protobuf:"bytes,1,opt,name=value"`
|
||||
// averageValue is the current value of the average of the
|
||||
// metric across all relevant pods (as a quantity)
|
||||
AverageValue *resource.Quantity `json:"averageValue" protobuf:"bytes,2,name=averageValue"`
|
||||
// +optional
|
||||
AverageValue *resource.Quantity `json:"averageValue,omitempty" protobuf:"bytes,2,opt,name=averageValue"`
|
||||
// currentAverageUtilization is the current value of the average of the
|
||||
// resource metric across all relevant pods, represented as a percentage of
|
||||
// the requested value of the resource for the pods.
|
||||
AverageUtilization *int32 `json:"averageUtilization" protobuf:"bytes,3,name=averageUtilization"`
|
||||
// +optional
|
||||
AverageUtilization *int32 `json:"averageUtilization,omitempty" protobuf:"bytes,3,opt,name=averageUtilization"`
|
||||
}
|
||||
|
||||
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
|
||||
|
|
|
@ -90,6 +90,18 @@
|
|||
"ImportPath": "github.com/peterbourgon/diskv",
|
||||
"Rev": "5f041e8faa004a95c88a202771f4cc3e991971e6"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/pmezard/go-difflib/difflib",
|
||||
"Rev": "d8ed2627bdf02c080bf22230dbb337003b7aba2d"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/stretchr/testify/assert",
|
||||
"Rev": "c679ae2cc0cb27ec3293fea7e254e47386f05d69"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/stretchr/testify/require",
|
||||
"Rev": "c679ae2cc0cb27ec3293fea7e254e47386f05d69"
|
||||
},
|
||||
{
|
||||
"ImportPath": "golang.org/x/crypto/ssh/terminal",
|
||||
"Rev": "de0752318171da717af4ce24d0a2e8626afaeb11"
|
||||
|
|
|
@ -46,6 +46,7 @@ func addKnownTypes(scheme *runtime.Scheme) error {
|
|||
scheme.AddKnownTypes(SchemeGroupVersion,
|
||||
&MetricValue{},
|
||||
&MetricValueList{},
|
||||
&MetricListOptions{},
|
||||
)
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -71,6 +71,22 @@ type MetricValue struct {
|
|||
// for all objects matching the given label selector
|
||||
const AllObjects = "*"
|
||||
|
||||
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
|
||||
|
||||
// MetricListOptions is used to select metrics by their label selectors
|
||||
type MetricListOptions struct {
|
||||
metav1.TypeMeta `json:",inline"`
|
||||
|
||||
// A selector to restrict the list of returned objects by their labels.
|
||||
// Defaults to everything.
|
||||
// +optional
|
||||
LabelSelector string `json:"labelSelector,omitempty" protobuf:"bytes,1,opt,name=labelSelector"`
|
||||
|
||||
// A selector to restrict the list of returned metrics by their labels
|
||||
// +optional
|
||||
MetricLabelSelector string `json:"metricLabelSelector,omitempty" protobuf:"bytes,2,opt,name=metricLabelSelector"`
|
||||
}
|
||||
|
||||
// NOTE: ObjectReference is copied from k8s.io/kubernetes/pkg/api/types.go. We
|
||||
// cannot depend on k8s.io/kubernetes/pkg/api because that creates cyclic
|
||||
// dependency between k8s.io/metrics and k8s.io/kubernetes. We cannot depend on
|
||||
|
|
|
@ -25,6 +25,7 @@ limitations under the License.
|
|||
k8s.io/kubernetes/vendor/k8s.io/metrics/pkg/apis/custom_metrics/v1beta1/generated.proto
|
||||
|
||||
It has these top-level messages:
|
||||
MetricListOptions
|
||||
MetricValue
|
||||
MetricValueList
|
||||
*/
|
||||
|
@ -52,18 +53,49 @@ var _ = math.Inf
|
|||
// proto package needs to be updated.
|
||||
const _ = proto.GoGoProtoPackageIsVersion2 // please upgrade the proto package
|
||||
|
||||
func (m *MetricListOptions) Reset() { *m = MetricListOptions{} }
|
||||
func (*MetricListOptions) ProtoMessage() {}
|
||||
func (*MetricListOptions) Descriptor() ([]byte, []int) { return fileDescriptorGenerated, []int{0} }
|
||||
|
||||
func (m *MetricValue) Reset() { *m = MetricValue{} }
|
||||
func (*MetricValue) ProtoMessage() {}
|
||||
func (*MetricValue) Descriptor() ([]byte, []int) { return fileDescriptorGenerated, []int{0} }
|
||||
func (*MetricValue) Descriptor() ([]byte, []int) { return fileDescriptorGenerated, []int{1} }
|
||||
|
||||
func (m *MetricValueList) Reset() { *m = MetricValueList{} }
|
||||
func (*MetricValueList) ProtoMessage() {}
|
||||
func (*MetricValueList) Descriptor() ([]byte, []int) { return fileDescriptorGenerated, []int{1} }
|
||||
func (*MetricValueList) Descriptor() ([]byte, []int) { return fileDescriptorGenerated, []int{2} }
|
||||
|
||||
func init() {
|
||||
proto.RegisterType((*MetricListOptions)(nil), "k8s.io.metrics.pkg.apis.custom_metrics.v1beta1.MetricListOptions")
|
||||
proto.RegisterType((*MetricValue)(nil), "k8s.io.metrics.pkg.apis.custom_metrics.v1beta1.MetricValue")
|
||||
proto.RegisterType((*MetricValueList)(nil), "k8s.io.metrics.pkg.apis.custom_metrics.v1beta1.MetricValueList")
|
||||
}
|
||||
func (m *MetricListOptions) Marshal() (dAtA []byte, err error) {
|
||||
size := m.Size()
|
||||
dAtA = make([]byte, size)
|
||||
n, err := m.MarshalTo(dAtA)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return dAtA[:n], nil
|
||||
}
|
||||
|
||||
func (m *MetricListOptions) MarshalTo(dAtA []byte) (int, error) {
|
||||
var i int
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
dAtA[i] = 0xa
|
||||
i++
|
||||
i = encodeVarintGenerated(dAtA, i, uint64(len(m.LabelSelector)))
|
||||
i += copy(dAtA[i:], m.LabelSelector)
|
||||
dAtA[i] = 0x12
|
||||
i++
|
||||
i = encodeVarintGenerated(dAtA, i, uint64(len(m.MetricLabelSelector)))
|
||||
i += copy(dAtA[i:], m.MetricLabelSelector)
|
||||
return i, nil
|
||||
}
|
||||
|
||||
func (m *MetricValue) Marshal() (dAtA []byte, err error) {
|
||||
size := m.Size()
|
||||
dAtA = make([]byte, size)
|
||||
|
@ -190,6 +222,16 @@ func encodeVarintGenerated(dAtA []byte, offset int, v uint64) int {
|
|||
dAtA[offset] = uint8(v)
|
||||
return offset + 1
|
||||
}
|
||||
func (m *MetricListOptions) Size() (n int) {
|
||||
var l int
|
||||
_ = l
|
||||
l = len(m.LabelSelector)
|
||||
n += 1 + l + sovGenerated(uint64(l))
|
||||
l = len(m.MetricLabelSelector)
|
||||
n += 1 + l + sovGenerated(uint64(l))
|
||||
return n
|
||||
}
|
||||
|
||||
func (m *MetricValue) Size() (n int) {
|
||||
var l int
|
||||
_ = l
|
||||
|
@ -238,6 +280,17 @@ func sovGenerated(x uint64) (n int) {
|
|||
func sozGenerated(x uint64) (n int) {
|
||||
return sovGenerated(uint64((x << 1) ^ uint64((int64(x) >> 63))))
|
||||
}
|
||||
func (this *MetricListOptions) String() string {
|
||||
if this == nil {
|
||||
return "nil"
|
||||
}
|
||||
s := strings.Join([]string{`&MetricListOptions{`,
|
||||
`LabelSelector:` + fmt.Sprintf("%v", this.LabelSelector) + `,`,
|
||||
`MetricLabelSelector:` + fmt.Sprintf("%v", this.MetricLabelSelector) + `,`,
|
||||
`}`,
|
||||
}, "")
|
||||
return s
|
||||
}
|
||||
func (this *MetricValue) String() string {
|
||||
if this == nil {
|
||||
return "nil"
|
||||
|
@ -272,6 +325,114 @@ func valueToStringGenerated(v interface{}) string {
|
|||
pv := reflect.Indirect(rv).Interface()
|
||||
return fmt.Sprintf("*%v", pv)
|
||||
}
|
||||
func (m *MetricListOptions) Unmarshal(dAtA []byte) error {
|
||||
l := len(dAtA)
|
||||
iNdEx := 0
|
||||
for iNdEx < l {
|
||||
preIndex := iNdEx
|
||||
var wire uint64
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowGenerated
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
wire |= (uint64(b) & 0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
fieldNum := int32(wire >> 3)
|
||||
wireType := int(wire & 0x7)
|
||||
if wireType == 4 {
|
||||
return fmt.Errorf("proto: MetricListOptions: wiretype end group for non-group")
|
||||
}
|
||||
if fieldNum <= 0 {
|
||||
return fmt.Errorf("proto: MetricListOptions: illegal tag %d (wire type %d)", fieldNum, wire)
|
||||
}
|
||||
switch fieldNum {
|
||||
case 1:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field LabelSelector", wireType)
|
||||
}
|
||||
var stringLen uint64
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowGenerated
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
stringLen |= (uint64(b) & 0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
intStringLen := int(stringLen)
|
||||
if intStringLen < 0 {
|
||||
return ErrInvalidLengthGenerated
|
||||
}
|
||||
postIndex := iNdEx + intStringLen
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.LabelSelector = string(dAtA[iNdEx:postIndex])
|
||||
iNdEx = postIndex
|
||||
case 2:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field MetricLabelSelector", wireType)
|
||||
}
|
||||
var stringLen uint64
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowGenerated
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
stringLen |= (uint64(b) & 0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
intStringLen := int(stringLen)
|
||||
if intStringLen < 0 {
|
||||
return ErrInvalidLengthGenerated
|
||||
}
|
||||
postIndex := iNdEx + intStringLen
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.MetricLabelSelector = string(dAtA[iNdEx:postIndex])
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
iNdEx = preIndex
|
||||
skippy, err := skipGenerated(dAtA[iNdEx:])
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if skippy < 0 {
|
||||
return ErrInvalidLengthGenerated
|
||||
}
|
||||
if (iNdEx + skippy) > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
iNdEx += skippy
|
||||
}
|
||||
}
|
||||
|
||||
if iNdEx > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
return nil
|
||||
}
|
||||
func (m *MetricValue) Unmarshal(dAtA []byte) error {
|
||||
l := len(dAtA)
|
||||
iNdEx := 0
|
||||
|
@ -715,41 +876,44 @@ func init() {
|
|||
}
|
||||
|
||||
var fileDescriptorGenerated = []byte{
|
||||
// 566 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0x93, 0x4f, 0x6f, 0xd3, 0x3e,
|
||||
0x18, 0xc7, 0x9b, 0xf5, 0xd7, 0xfd, 0x3a, 0x8f, 0x69, 0x2c, 0x17, 0xa2, 0x1d, 0xd2, 0x6a, 0x5c,
|
||||
0x0a, 0xd2, 0x6c, 0x6d, 0x20, 0x84, 0xc4, 0x2d, 0xe2, 0x82, 0xb4, 0x81, 0xc8, 0x26, 0x26, 0xf1,
|
||||
0x47, 0xe0, 0x38, 0x4f, 0x53, 0xd3, 0x26, 0x8e, 0x6c, 0xa7, 0xd3, 0x6e, 0xbc, 0x04, 0x5e, 0x56,
|
||||
0x8f, 0xe3, 0xb6, 0x53, 0x45, 0x83, 0x78, 0x1f, 0x28, 0x89, 0xd3, 0x76, 0x1b, 0x7f, 0xb6, 0x5b,
|
||||
0x6c, 0x3f, 0xdf, 0x8f, 0xbf, 0xcf, 0xf7, 0x71, 0xd0, 0xc9, 0xf0, 0xa9, 0xc2, 0x5c, 0x90, 0x61,
|
||||
0x16, 0x80, 0x4c, 0x40, 0x83, 0x22, 0x63, 0x48, 0x42, 0x21, 0x89, 0x39, 0x88, 0x41, 0x4b, 0xce,
|
||||
0x14, 0x49, 0x87, 0x11, 0xa1, 0x29, 0x57, 0x84, 0x65, 0x4a, 0x8b, 0xf8, 0x63, 0xbd, 0x3f, 0xde,
|
||||
0x0b, 0x40, 0xd3, 0x3d, 0x12, 0x41, 0x02, 0x92, 0x6a, 0x08, 0x71, 0x2a, 0x85, 0x16, 0x36, 0xae,
|
||||
0xf4, 0xd8, 0xd4, 0xe1, 0x74, 0x18, 0xe1, 0x42, 0x8f, 0x2f, 0xeb, 0xb1, 0xd1, 0x6f, 0xef, 0x46,
|
||||
0x5c, 0x0f, 0xb2, 0x00, 0x33, 0x11, 0x93, 0x48, 0x44, 0x82, 0x94, 0x98, 0x20, 0xeb, 0x97, 0xab,
|
||||
0x72, 0x51, 0x7e, 0x55, 0xf8, 0xed, 0x1d, 0x63, 0x8f, 0xa6, 0x9c, 0x30, 0x21, 0x81, 0x8c, 0xaf,
|
||||
0x59, 0xd8, 0x7e, 0xbc, 0xa8, 0x89, 0x29, 0x1b, 0xf0, 0x04, 0xe4, 0x59, 0xdd, 0x07, 0x91, 0xa0,
|
||||
0x44, 0x26, 0x19, 0xdc, 0x4a, 0xa5, 0x8a, 0x38, 0xe8, 0xef, 0xee, 0x22, 0x7f, 0x52, 0xc9, 0x2c,
|
||||
0xd1, 0x3c, 0xbe, 0x7e, 0xcd, 0x93, 0x7f, 0x09, 0x14, 0x1b, 0x40, 0x4c, 0xaf, 0xea, 0x76, 0x7e,
|
||||
0x36, 0xd1, 0xfa, 0x61, 0x99, 0xdd, 0x1b, 0x3a, 0xca, 0xc0, 0xee, 0xa3, 0xcd, 0x10, 0x14, 0x93,
|
||||
0x3c, 0x80, 0xf0, 0x55, 0xf0, 0x19, 0x98, 0x76, 0xac, 0xae, 0xd5, 0x5b, 0xdf, 0xbf, 0x5f, 0x4f,
|
||||
0x80, 0xa6, 0x1c, 0x17, 0x11, 0xe1, 0xf1, 0x1e, 0xae, 0x2a, 0x7c, 0xe8, 0x83, 0x84, 0x84, 0x81,
|
||||
0x77, 0x6f, 0x32, 0xed, 0x34, 0xf2, 0x69, 0x67, 0xf3, 0xf9, 0x65, 0x86, 0x7f, 0x15, 0x6a, 0xef,
|
||||
0x23, 0x54, 0x8d, 0xec, 0x25, 0x8d, 0xc1, 0x59, 0xe9, 0x5a, 0xbd, 0x35, 0xcf, 0x36, 0x6a, 0x74,
|
||||
0x38, 0x3f, 0xf1, 0x97, 0xaa, 0xec, 0x77, 0x68, 0xad, 0x68, 0x45, 0x69, 0x1a, 0xa7, 0x4e, 0xb3,
|
||||
0x74, 0xf5, 0x70, 0xc9, 0xd5, 0xbc, 0xef, 0xc5, 0xe3, 0x28, 0xe2, 0x2d, 0x7c, 0x1e, 0xf3, 0x18,
|
||||
0xbc, 0x2d, 0x83, 0x5f, 0x3b, 0xae, 0x21, 0xfe, 0x82, 0x67, 0x3f, 0x40, 0xab, 0xa7, 0x3c, 0x09,
|
||||
0xc5, 0xa9, 0xf3, 0x5f, 0xd7, 0xea, 0x35, 0xbd, 0xad, 0x7c, 0xda, 0xd9, 0x38, 0x29, 0x77, 0x8e,
|
||||
0x80, 0x89, 0x24, 0x54, 0xbe, 0x29, 0xb0, 0x8f, 0x50, 0x6b, 0x5c, 0x84, 0xe5, 0xb4, 0x4a, 0x0f,
|
||||
0xf8, 0x6f, 0x1e, 0x70, 0xfd, 0x30, 0xf0, 0xeb, 0x8c, 0x26, 0x9a, 0xeb, 0x33, 0x6f, 0xc3, 0xf8,
|
||||
0x68, 0x95, 0x89, 0xfb, 0x15, 0xcb, 0xfe, 0x80, 0xda, 0x0a, 0x46, 0xc0, 0xb4, 0x90, 0xce, 0x6a,
|
||||
0xc9, 0x7d, 0x74, 0xb3, 0xde, 0x0e, 0x68, 0x00, 0xa3, 0x23, 0x23, 0xf5, 0xee, 0xe4, 0xd3, 0x4e,
|
||||
0xbb, 0x5e, 0xf9, 0x73, 0xe4, 0xce, 0x37, 0x0b, 0x6d, 0x2e, 0xcd, 0xf9, 0x80, 0x2b, 0x6d, 0xbf,
|
||||
0x47, 0xed, 0x02, 0x12, 0x52, 0x4d, 0xcd, 0x90, 0xf1, 0x0d, 0xaf, 0xe4, 0x4a, 0x1f, 0x82, 0xa6,
|
||||
0xde, 0x5d, 0xd3, 0x4a, 0xbb, 0xde, 0xf1, 0xe7, 0x44, 0xfb, 0x13, 0x6a, 0x71, 0x0d, 0xb1, 0x72,
|
||||
0x56, 0xba, 0xcd, 0xde, 0xfa, 0xfe, 0xb3, 0x5b, 0xfe, 0xc1, 0x78, 0xc9, 0xed, 0x22, 0xb2, 0x17,
|
||||
0x05, 0xd1, 0xaf, 0xc0, 0xde, 0xee, 0x64, 0xe6, 0x36, 0xce, 0x67, 0x6e, 0xe3, 0x62, 0xe6, 0x36,
|
||||
0xbe, 0xe4, 0xae, 0x35, 0xc9, 0x5d, 0xeb, 0x3c, 0x77, 0xad, 0x8b, 0xdc, 0xb5, 0xbe, 0xe7, 0xae,
|
||||
0xf5, 0xf5, 0x87, 0xdb, 0x78, 0xfb, 0xbf, 0x01, 0xfe, 0x0a, 0x00, 0x00, 0xff, 0xff, 0xdb, 0xed,
|
||||
0x64, 0xfc, 0x9c, 0x04, 0x00, 0x00,
|
||||
// 616 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0x94, 0x4f, 0x4f, 0x14, 0x3f,
|
||||
0x1c, 0xc6, 0x77, 0xd8, 0xdf, 0xf2, 0x5b, 0x8a, 0x04, 0x19, 0x62, 0xdc, 0x60, 0x32, 0x90, 0xf5,
|
||||
0x82, 0x26, 0xb4, 0x01, 0x8d, 0x31, 0xe1, 0x36, 0xf1, 0x62, 0xc2, 0x4a, 0x1c, 0x88, 0x24, 0xfe,
|
||||
0x89, 0x76, 0x3a, 0x5f, 0x96, 0xba, 0x3b, 0xd3, 0x49, 0xdb, 0x59, 0xc2, 0xcd, 0x97, 0xe0, 0x3b,
|
||||
0xf0, 0xed, 0x70, 0xc4, 0x1b, 0x27, 0x22, 0x63, 0x7c, 0x1f, 0x66, 0x3a, 0x9d, 0xfd, 0xc3, 0xa2,
|
||||
0xc2, 0x6d, 0xa7, 0x7d, 0x9e, 0x4f, 0x9f, 0x7e, 0x9f, 0x66, 0xd1, 0x41, 0xef, 0xb9, 0xc2, 0x5c,
|
||||
0x90, 0x5e, 0x16, 0x82, 0x4c, 0x40, 0x83, 0x22, 0x03, 0x48, 0x22, 0x21, 0x89, 0xdd, 0x88, 0x41,
|
||||
0x4b, 0xce, 0x14, 0x49, 0x7b, 0x5d, 0x42, 0x53, 0xae, 0x08, 0xcb, 0x94, 0x16, 0xf1, 0xc7, 0x6a,
|
||||
0x7d, 0xb0, 0x19, 0x82, 0xa6, 0x9b, 0xa4, 0x0b, 0x09, 0x48, 0xaa, 0x21, 0xc2, 0xa9, 0x14, 0x5a,
|
||||
0xb8, 0xb8, 0xf4, 0x63, 0xab, 0xc3, 0x69, 0xaf, 0x8b, 0x0b, 0x3f, 0x9e, 0xf4, 0x63, 0xeb, 0x5f,
|
||||
0xd9, 0xe8, 0x72, 0x7d, 0x94, 0x85, 0x98, 0x89, 0x98, 0x74, 0x45, 0x57, 0x10, 0x83, 0x09, 0xb3,
|
||||
0x43, 0xf3, 0x65, 0x3e, 0xcc, 0xaf, 0x12, 0xbf, 0xd2, 0xb6, 0xf1, 0x68, 0xca, 0x09, 0x13, 0x12,
|
||||
0xc8, 0x60, 0x2a, 0xc2, 0xca, 0xd3, 0x91, 0x26, 0xa6, 0xec, 0x88, 0x27, 0x20, 0x4f, 0xaa, 0x7b,
|
||||
0x10, 0x09, 0x4a, 0x64, 0x92, 0xc1, 0xad, 0x5c, 0xaa, 0x18, 0x07, 0xbd, 0xee, 0x2c, 0xf2, 0x27,
|
||||
0x97, 0xcc, 0x12, 0xcd, 0xe3, 0xe9, 0x63, 0x9e, 0xfd, 0xcb, 0xa0, 0xd8, 0x11, 0xc4, 0xf4, 0xaa,
|
||||
0xaf, 0xfd, 0xcd, 0x41, 0x4b, 0x1d, 0x33, 0xbb, 0x1d, 0xae, 0xf4, 0x6e, 0xaa, 0xb9, 0x48, 0x94,
|
||||
0xbb, 0x8d, 0x16, 0xfa, 0x34, 0x84, 0xfe, 0x1e, 0xf4, 0x81, 0x69, 0x21, 0x5b, 0xce, 0x9a, 0xb3,
|
||||
0x3e, 0xe7, 0xdf, 0x3b, 0xbd, 0x58, 0xad, 0xe5, 0x17, 0xab, 0x0b, 0x3b, 0xe3, 0x9b, 0xc1, 0xa4,
|
||||
0xd6, 0xed, 0xa0, 0xe5, 0xb2, 0x8d, 0x09, 0x55, 0x6b, 0xc6, 0x20, 0x1e, 0x58, 0xc4, 0x72, 0x67,
|
||||
0x5a, 0x12, 0x5c, 0xe7, 0x6b, 0xff, 0xaa, 0xa3, 0xf9, 0x52, 0xfc, 0x86, 0xf6, 0x33, 0x70, 0x0f,
|
||||
0xd1, 0x62, 0x04, 0x8a, 0x49, 0x1e, 0x42, 0xb4, 0x1b, 0x7e, 0x06, 0xa6, 0x4d, 0xba, 0xf9, 0xad,
|
||||
0x87, 0xd5, 0x1b, 0xa1, 0x29, 0xc7, 0x45, 0x89, 0x78, 0xb0, 0x89, 0x4b, 0x45, 0x00, 0x87, 0x20,
|
||||
0x21, 0x61, 0xe0, 0xdf, 0xb7, 0xe7, 0x2f, 0xbe, 0x98, 0x64, 0x04, 0x57, 0xa1, 0xee, 0x16, 0x42,
|
||||
0x65, 0x9c, 0x57, 0x34, 0x06, 0x9b, 0xde, 0xb5, 0x6e, 0xd4, 0x19, 0xee, 0x04, 0x63, 0x2a, 0xf7,
|
||||
0x1d, 0x9a, 0x2b, 0x86, 0xad, 0x34, 0x8d, 0xd3, 0x56, 0xdd, 0xa4, 0x7a, 0x3c, 0x96, 0x6a, 0xd8,
|
||||
0xcc, 0xe8, 0xf9, 0x16, 0x0f, 0xa0, 0xc8, 0xb9, 0xcf, 0x63, 0xf0, 0x97, 0x2c, 0x7e, 0x6e, 0xbf,
|
||||
0x82, 0x04, 0x23, 0x9e, 0xfb, 0x08, 0xcd, 0x1e, 0xf3, 0x24, 0x12, 0xc7, 0xad, 0xff, 0xd6, 0x9c,
|
||||
0xf5, 0xba, 0xbf, 0x54, 0x34, 0x71, 0x60, 0x56, 0xf6, 0x80, 0x89, 0x24, 0x52, 0x81, 0x15, 0xb8,
|
||||
0x7b, 0xa8, 0x31, 0x28, 0x86, 0xd5, 0x6a, 0x98, 0x0c, 0xf8, 0x6f, 0x19, 0x70, 0xf5, 0x74, 0xf1,
|
||||
0xeb, 0x8c, 0x26, 0x9a, 0xeb, 0x13, 0x7f, 0xc1, 0xe6, 0x68, 0x98, 0x89, 0x07, 0x25, 0xcb, 0xfd,
|
||||
0x80, 0x9a, 0xaa, 0x2a, 0x73, 0xd6, 0x70, 0x9f, 0xdc, 0xec, 0x6e, 0x13, 0x7d, 0xfa, 0x77, 0xf2,
|
||||
0x8b, 0xd5, 0xe6, 0xb0, 0xf2, 0x21, 0xb2, 0xfd, 0xdd, 0x41, 0x8b, 0x63, 0x3d, 0x17, 0xcf, 0xd1,
|
||||
0x7d, 0x8f, 0x9a, 0x05, 0x24, 0xa2, 0x9a, 0xda, 0x92, 0xf1, 0x0d, 0x8f, 0xe4, 0x4a, 0x77, 0x40,
|
||||
0x53, 0xff, 0xae, 0xbd, 0x4a, 0xb3, 0x5a, 0x09, 0x86, 0x44, 0xf7, 0x13, 0x6a, 0x70, 0x0d, 0xb1,
|
||||
0x6a, 0xcd, 0xac, 0xd5, 0xd7, 0xe7, 0xb7, 0xb6, 0x6f, 0xf9, 0x1f, 0x83, 0xc7, 0xd2, 0x8e, 0x46,
|
||||
0xf6, 0xb2, 0x20, 0x06, 0x25, 0xd8, 0xdf, 0x38, 0xbd, 0xf4, 0x6a, 0x67, 0x97, 0x5e, 0xed, 0xfc,
|
||||
0xd2, 0xab, 0x7d, 0xc9, 0x3d, 0xe7, 0x34, 0xf7, 0x9c, 0xb3, 0xdc, 0x73, 0xce, 0x73, 0xcf, 0xf9,
|
||||
0x91, 0x7b, 0xce, 0xd7, 0x9f, 0x5e, 0xed, 0xed, 0xff, 0x16, 0xf8, 0x3b, 0x00, 0x00, 0xff, 0xff,
|
||||
0xf5, 0x23, 0xb5, 0xdc, 0x3e, 0x05, 0x00, 0x00,
|
||||
}
|
||||
|
|
|
@ -30,6 +30,18 @@ import "k8s.io/apimachinery/pkg/runtime/schema/generated.proto";
|
|||
// Package-wide variables from generator "generated".
|
||||
option go_package = "v1beta1";
|
||||
|
||||
// MetricListOptions is used to select metrics by their label selectors
|
||||
message MetricListOptions {
|
||||
// A selector to restrict the list of returned objects by their labels.
|
||||
// Defaults to everything.
|
||||
// +optional
|
||||
optional string labelSelector = 1;
|
||||
|
||||
// A selector to restrict the list of returned metrics by their labels
|
||||
// +optional
|
||||
optional string metricLabelSelector = 2;
|
||||
}
|
||||
|
||||
// a metric value for some object
|
||||
message MetricValue {
|
||||
// a reference to the described object
|
||||
|
|
|
@ -43,6 +43,7 @@ func addKnownTypes(scheme *runtime.Scheme) error {
|
|||
scheme.AddKnownTypes(SchemeGroupVersion,
|
||||
&MetricValue{},
|
||||
&MetricValueList{},
|
||||
&MetricListOptions{},
|
||||
)
|
||||
metav1.AddToGroupVersion(scheme, SchemeGroupVersion)
|
||||
return nil
|
||||
|
|
|
@ -65,6 +65,22 @@ type MetricValue struct {
|
|||
Selector *metav1.LabelSelector `json:"selector" protobuf:"bytes,6,opt,name=selector"`
|
||||
}
|
||||
|
||||
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
|
||||
|
||||
// MetricListOptions is used to select metrics by their label selectors
|
||||
type MetricListOptions struct {
|
||||
metav1.TypeMeta `json:",inline"`
|
||||
|
||||
// A selector to restrict the list of returned objects by their labels.
|
||||
// Defaults to everything.
|
||||
// +optional
|
||||
LabelSelector string `json:"labelSelector,omitempty" protobuf:"bytes,1,opt,name=labelSelector"`
|
||||
|
||||
// A selector to restrict the list of returned metrics by their labels
|
||||
// +optional
|
||||
MetricLabelSelector string `json:"metricLabelSelector,omitempty" protobuf:"bytes,2,opt,name=metricLabelSelector"`
|
||||
}
|
||||
|
||||
// allObjects is a wildcard used to select metrics
|
||||
// for all objects matching the given label selector
|
||||
const AllObjects = "*"
|
||||
|
|
|
@ -35,6 +35,16 @@ func init() {
|
|||
// RegisterConversions adds conversion functions to the given scheme.
|
||||
// Public to allow building arbitrary schemes.
|
||||
func RegisterConversions(s *runtime.Scheme) error {
|
||||
if err := s.AddGeneratedConversionFunc((*MetricListOptions)(nil), (*custommetrics.MetricListOptions)(nil), func(a, b interface{}, scope conversion.Scope) error {
|
||||
return Convert_v1beta1_MetricListOptions_To_custom_metrics_MetricListOptions(a.(*MetricListOptions), b.(*custommetrics.MetricListOptions), scope)
|
||||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := s.AddGeneratedConversionFunc((*custommetrics.MetricListOptions)(nil), (*MetricListOptions)(nil), func(a, b interface{}, scope conversion.Scope) error {
|
||||
return Convert_custom_metrics_MetricListOptions_To_v1beta1_MetricListOptions(a.(*custommetrics.MetricListOptions), b.(*MetricListOptions), scope)
|
||||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := s.AddGeneratedConversionFunc((*MetricValue)(nil), (*custommetrics.MetricValue)(nil), func(a, b interface{}, scope conversion.Scope) error {
|
||||
return Convert_v1beta1_MetricValue_To_custom_metrics_MetricValue(a.(*MetricValue), b.(*custommetrics.MetricValue), scope)
|
||||
}); err != nil {
|
||||
|
@ -68,6 +78,28 @@ func RegisterConversions(s *runtime.Scheme) error {
|
|||
return nil
|
||||
}
|
||||
|
||||
func autoConvert_v1beta1_MetricListOptions_To_custom_metrics_MetricListOptions(in *MetricListOptions, out *custommetrics.MetricListOptions, s conversion.Scope) error {
|
||||
out.LabelSelector = in.LabelSelector
|
||||
out.MetricLabelSelector = in.MetricLabelSelector
|
||||
return nil
|
||||
}
|
||||
|
||||
// Convert_v1beta1_MetricListOptions_To_custom_metrics_MetricListOptions is an autogenerated conversion function.
|
||||
func Convert_v1beta1_MetricListOptions_To_custom_metrics_MetricListOptions(in *MetricListOptions, out *custommetrics.MetricListOptions, s conversion.Scope) error {
|
||||
return autoConvert_v1beta1_MetricListOptions_To_custom_metrics_MetricListOptions(in, out, s)
|
||||
}
|
||||
|
||||
func autoConvert_custom_metrics_MetricListOptions_To_v1beta1_MetricListOptions(in *custommetrics.MetricListOptions, out *MetricListOptions, s conversion.Scope) error {
|
||||
out.LabelSelector = in.LabelSelector
|
||||
out.MetricLabelSelector = in.MetricLabelSelector
|
||||
return nil
|
||||
}
|
||||
|
||||
// Convert_custom_metrics_MetricListOptions_To_v1beta1_MetricListOptions is an autogenerated conversion function.
|
||||
func Convert_custom_metrics_MetricListOptions_To_v1beta1_MetricListOptions(in *custommetrics.MetricListOptions, out *MetricListOptions, s conversion.Scope) error {
|
||||
return autoConvert_custom_metrics_MetricListOptions_To_v1beta1_MetricListOptions(in, out, s)
|
||||
}
|
||||
|
||||
func autoConvert_v1beta1_MetricValue_To_custom_metrics_MetricValue(in *MetricValue, out *custommetrics.MetricValue, s conversion.Scope) error {
|
||||
// TODO: Inefficient conversion - can we improve it?
|
||||
if err := s.Convert(&in.DescribedObject, &out.DescribedObject, 0); err != nil {
|
||||
|
|
|
@ -25,6 +25,31 @@ import (
|
|||
runtime "k8s.io/apimachinery/pkg/runtime"
|
||||
)
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *MetricListOptions) DeepCopyInto(out *MetricListOptions) {
|
||||
*out = *in
|
||||
out.TypeMeta = in.TypeMeta
|
||||
return
|
||||
}
|
||||
|
||||
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new MetricListOptions.
|
||||
func (in *MetricListOptions) DeepCopy() *MetricListOptions {
|
||||
if in == nil {
|
||||
return nil
|
||||
}
|
||||
out := new(MetricListOptions)
|
||||
in.DeepCopyInto(out)
|
||||
return out
|
||||
}
|
||||
|
||||
// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
|
||||
func (in *MetricListOptions) DeepCopyObject() runtime.Object {
|
||||
if c := in.DeepCopy(); c != nil {
|
||||
return c
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *MetricValue) DeepCopyInto(out *MetricValue) {
|
||||
*out = *in
|
||||
|
|
|
@ -46,6 +46,16 @@ func RegisterConversions(s *runtime.Scheme) error {
|
|||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := s.AddGeneratedConversionFunc((*MetricListOptions)(nil), (*custommetrics.MetricListOptions)(nil), func(a, b interface{}, scope conversion.Scope) error {
|
||||
return Convert_v1beta2_MetricListOptions_To_custom_metrics_MetricListOptions(a.(*MetricListOptions), b.(*custommetrics.MetricListOptions), scope)
|
||||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := s.AddGeneratedConversionFunc((*custommetrics.MetricListOptions)(nil), (*MetricListOptions)(nil), func(a, b interface{}, scope conversion.Scope) error {
|
||||
return Convert_custom_metrics_MetricListOptions_To_v1beta2_MetricListOptions(a.(*custommetrics.MetricListOptions), b.(*MetricListOptions), scope)
|
||||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := s.AddGeneratedConversionFunc((*MetricValue)(nil), (*custommetrics.MetricValue)(nil), func(a, b interface{}, scope conversion.Scope) error {
|
||||
return Convert_v1beta2_MetricValue_To_custom_metrics_MetricValue(a.(*MetricValue), b.(*custommetrics.MetricValue), scope)
|
||||
}); err != nil {
|
||||
|
@ -91,6 +101,28 @@ func Convert_custom_metrics_MetricIdentifier_To_v1beta2_MetricIdentifier(in *cus
|
|||
return autoConvert_custom_metrics_MetricIdentifier_To_v1beta2_MetricIdentifier(in, out, s)
|
||||
}
|
||||
|
||||
func autoConvert_v1beta2_MetricListOptions_To_custom_metrics_MetricListOptions(in *MetricListOptions, out *custommetrics.MetricListOptions, s conversion.Scope) error {
|
||||
out.LabelSelector = in.LabelSelector
|
||||
out.MetricLabelSelector = in.MetricLabelSelector
|
||||
return nil
|
||||
}
|
||||
|
||||
// Convert_v1beta2_MetricListOptions_To_custom_metrics_MetricListOptions is an autogenerated conversion function.
|
||||
func Convert_v1beta2_MetricListOptions_To_custom_metrics_MetricListOptions(in *MetricListOptions, out *custommetrics.MetricListOptions, s conversion.Scope) error {
|
||||
return autoConvert_v1beta2_MetricListOptions_To_custom_metrics_MetricListOptions(in, out, s)
|
||||
}
|
||||
|
||||
func autoConvert_custom_metrics_MetricListOptions_To_v1beta2_MetricListOptions(in *custommetrics.MetricListOptions, out *MetricListOptions, s conversion.Scope) error {
|
||||
out.LabelSelector = in.LabelSelector
|
||||
out.MetricLabelSelector = in.MetricLabelSelector
|
||||
return nil
|
||||
}
|
||||
|
||||
// Convert_custom_metrics_MetricListOptions_To_v1beta2_MetricListOptions is an autogenerated conversion function.
|
||||
func Convert_custom_metrics_MetricListOptions_To_v1beta2_MetricListOptions(in *custommetrics.MetricListOptions, out *MetricListOptions, s conversion.Scope) error {
|
||||
return autoConvert_custom_metrics_MetricListOptions_To_v1beta2_MetricListOptions(in, out, s)
|
||||
}
|
||||
|
||||
func autoConvert_v1beta2_MetricValue_To_custom_metrics_MetricValue(in *MetricValue, out *custommetrics.MetricValue, s conversion.Scope) error {
|
||||
// TODO: Inefficient conversion - can we improve it?
|
||||
if err := s.Convert(&in.DescribedObject, &out.DescribedObject, 0); err != nil {
|
||||
|
|
|
@ -46,6 +46,31 @@ func (in *MetricIdentifier) DeepCopy() *MetricIdentifier {
|
|||
return out
|
||||
}
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *MetricListOptions) DeepCopyInto(out *MetricListOptions) {
|
||||
*out = *in
|
||||
out.TypeMeta = in.TypeMeta
|
||||
return
|
||||
}
|
||||
|
||||
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new MetricListOptions.
|
||||
func (in *MetricListOptions) DeepCopy() *MetricListOptions {
|
||||
if in == nil {
|
||||
return nil
|
||||
}
|
||||
out := new(MetricListOptions)
|
||||
in.DeepCopyInto(out)
|
||||
return out
|
||||
}
|
||||
|
||||
// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
|
||||
func (in *MetricListOptions) DeepCopyObject() runtime.Object {
|
||||
if c := in.DeepCopy(); c != nil {
|
||||
return c
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *MetricValue) DeepCopyInto(out *MetricValue) {
|
||||
*out = *in
|
||||
|
|
|
@ -1,21 +1,29 @@
|
|||
load("@io_bazel_rules_go//go:def.bzl", "go_library")
|
||||
load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
|
||||
|
||||
go_library(
|
||||
name = "go_default_library",
|
||||
srcs = [
|
||||
"client.go",
|
||||
"converter.go",
|
||||
"discovery.go",
|
||||
"interfaces.go",
|
||||
"multi_client.go",
|
||||
"versioned_client.go",
|
||||
],
|
||||
importmap = "k8s.io/kubernetes/vendor/k8s.io/metrics/pkg/client/custom_metrics",
|
||||
importpath = "k8s.io/metrics/pkg/client/custom_metrics",
|
||||
visibility = ["//visibility:public"],
|
||||
deps = [
|
||||
"//staging/src/k8s.io/apimachinery/pkg/api/meta:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/apis/meta/v1:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/labels:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/runtime:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/runtime/schema:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/runtime/serializer:go_default_library",
|
||||
"//staging/src/k8s.io/client-go/discovery:go_default_library",
|
||||
"//staging/src/k8s.io/client-go/rest:go_default_library",
|
||||
"//staging/src/k8s.io/client-go/util/flowcontrol:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics/v1beta1:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics/v1beta2:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/client/custom_metrics/scheme:go_default_library",
|
||||
],
|
||||
|
@ -38,3 +46,18 @@ filegroup(
|
|||
tags = ["automanaged"],
|
||||
visibility = ["//visibility:public"],
|
||||
)
|
||||
|
||||
go_test(
|
||||
name = "go_default_test",
|
||||
srcs = ["util_test.go"],
|
||||
embed = [":go_default_library"],
|
||||
deps = [
|
||||
"//staging/src/k8s.io/apimachinery/pkg/apis/meta/v1:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/runtime:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/runtime/schema:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics/v1beta1:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics/v1beta2:go_default_library",
|
||||
"//vendor/github.com/stretchr/testify/require:go_default_library",
|
||||
],
|
||||
)
|
||||
|
|
|
@ -0,0 +1,122 @@
|
|||
/*
|
||||
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 custom_metrics
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"k8s.io/apimachinery/pkg/runtime"
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
"k8s.io/apimachinery/pkg/runtime/serializer"
|
||||
"k8s.io/client-go/rest"
|
||||
|
||||
cmint "k8s.io/metrics/pkg/apis/custom_metrics"
|
||||
cmv1beta1 "k8s.io/metrics/pkg/apis/custom_metrics/v1beta1"
|
||||
cmv1beta2 "k8s.io/metrics/pkg/apis/custom_metrics/v1beta2"
|
||||
"k8s.io/metrics/pkg/client/custom_metrics/scheme"
|
||||
)
|
||||
|
||||
var (
|
||||
// MetricVersions is the set of metric versions accepted by the converter.
|
||||
MetricVersions = []schema.GroupVersion{
|
||||
cmv1beta2.SchemeGroupVersion,
|
||||
cmv1beta1.SchemeGroupVersion,
|
||||
cmint.SchemeGroupVersion,
|
||||
}
|
||||
)
|
||||
|
||||
// MetricConverter knows how to convert between external MetricValue versions.
|
||||
type MetricConverter struct {
|
||||
scheme *runtime.Scheme
|
||||
codecs serializer.CodecFactory
|
||||
internalVersioner runtime.GroupVersioner
|
||||
}
|
||||
|
||||
// NewMetricConverter creates a MetricConverter which knows how to convert objects
|
||||
// between different versions of the custom metrics api.
|
||||
func NewMetricConverter() *MetricConverter {
|
||||
return &MetricConverter{
|
||||
scheme: scheme.Scheme,
|
||||
codecs: serializer.NewCodecFactory(scheme.Scheme),
|
||||
internalVersioner: runtime.NewMultiGroupVersioner(
|
||||
scheme.SchemeGroupVersion,
|
||||
schema.GroupKind{Group: cmint.GroupName, Kind: ""},
|
||||
schema.GroupKind{Group: cmv1beta1.GroupName, Kind: ""},
|
||||
schema.GroupKind{Group: cmv1beta2.GroupName, Kind: ""},
|
||||
),
|
||||
}
|
||||
}
|
||||
|
||||
// Scheme returns the scheme used by this metric converter.
|
||||
func (c *MetricConverter) Scheme() *runtime.Scheme {
|
||||
return c.scheme
|
||||
}
|
||||
|
||||
// Codecs returns the codecs used by this metric converter
|
||||
func (c *MetricConverter) Codecs() serializer.CodecFactory {
|
||||
return c.codecs
|
||||
}
|
||||
|
||||
// ConvertListOptionsToVersion converts converts a set of MetricListOptions
|
||||
// to the provided GroupVersion.
|
||||
func (c *MetricConverter) ConvertListOptionsToVersion(opts *cmint.MetricListOptions, version schema.GroupVersion) (runtime.Object, error) {
|
||||
paramObj, err := c.UnsafeConvertToVersionVia(opts, version)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return paramObj, nil
|
||||
}
|
||||
|
||||
// ConvertResultToVersion converts a Result to the provided GroupVersion
|
||||
func (c *MetricConverter) ConvertResultToVersion(res rest.Result, gv schema.GroupVersion) (runtime.Object, error) {
|
||||
if err := res.Error(); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
metricBytes, err := res.Raw()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
decoder := c.codecs.UniversalDecoder(MetricVersions...)
|
||||
rawMetricObj, err := runtime.Decode(decoder, metricBytes)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
metricObj, err := c.UnsafeConvertToVersionVia(rawMetricObj, gv)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return metricObj, nil
|
||||
}
|
||||
|
||||
// unsafeConvertToVersionVia is like Scheme.UnsafeConvertToVersion, but it does so via an internal version first.
|
||||
// We use it here to work with the v1beta2 client internally, while preserving backwards compatibility for existing custom metrics adapters
|
||||
func (c *MetricConverter) UnsafeConvertToVersionVia(obj runtime.Object, externalVersion schema.GroupVersion) (runtime.Object, error) {
|
||||
objInt, err := c.scheme.UnsafeConvertToVersion(obj, schema.GroupVersion{Group: externalVersion.Group, Version: runtime.APIVersionInternal})
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to convert the given object to the internal version: %v", err)
|
||||
}
|
||||
|
||||
objExt, err := c.scheme.UnsafeConvertToVersion(objInt, externalVersion)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to convert the given object back to the external version: %v", err)
|
||||
}
|
||||
|
||||
return objExt, err
|
||||
}
|
|
@ -0,0 +1,145 @@
|
|||
/*
|
||||
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 custom_metrics
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"sync"
|
||||
|
||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
"k8s.io/client-go/discovery"
|
||||
|
||||
cmint "k8s.io/metrics/pkg/apis/custom_metrics"
|
||||
)
|
||||
|
||||
var (
|
||||
// metricVersionsToGV is the map of string group-versions
|
||||
// accepted by the converter to group-version objects (so
|
||||
// we don't have to re-parse)
|
||||
metricVersionsToGV map[string]schema.GroupVersion
|
||||
)
|
||||
|
||||
func init() {
|
||||
metricVersionsToGV = make(map[string]schema.GroupVersion)
|
||||
for _, ver := range MetricVersions {
|
||||
metricVersionsToGV[ver.String()] = ver
|
||||
}
|
||||
}
|
||||
|
||||
// NewAvailableAPIsGetter creates an AvailableAPIsGetter that checks discovery
|
||||
// to find the available versions of the custom metrics api.
|
||||
func NewAvailableAPIsGetter(client discovery.DiscoveryInterface) AvailableAPIsGetter {
|
||||
return &apiVersionsFromDiscovery{
|
||||
client: client,
|
||||
}
|
||||
}
|
||||
|
||||
// apiVersionsFromDiscovery caches a preferred version of the custom metrics api.
|
||||
type apiVersionsFromDiscovery struct {
|
||||
client discovery.DiscoveryInterface
|
||||
|
||||
// just cache the group directly since the discovery interface doesn't yet allow
|
||||
// asking for a single API group's versions.
|
||||
prefVersion *schema.GroupVersion
|
||||
mu sync.RWMutex
|
||||
}
|
||||
|
||||
// fetchVersions fetches the versions, but doesn't try to invalidate on cache misses.
|
||||
func (d *apiVersionsFromDiscovery) fetchVersions() (*metav1.APIGroup, error) {
|
||||
// TODO(directxman12): amend the discovery interface to ask for a particular group (/apis/foo)
|
||||
groups, err := d.client.ServerGroups()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Determine the preferred version on the server by first finding the custom metrics group
|
||||
var apiGroup *metav1.APIGroup
|
||||
for _, group := range groups.Groups {
|
||||
if group.Name == cmint.GroupName {
|
||||
apiGroup = &group
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
if apiGroup == nil {
|
||||
return nil, fmt.Errorf("no custom metrics API (%s) registered", cmint.GroupName)
|
||||
}
|
||||
|
||||
return apiGroup, nil
|
||||
}
|
||||
|
||||
// chooseVersion sets a preferred version of the custom metrics api based on available versions.
|
||||
func (d *apiVersionsFromDiscovery) chooseVersion(apiGroup *metav1.APIGroup) (schema.GroupVersion, error) {
|
||||
var preferredVersion *schema.GroupVersion
|
||||
if gv, present := metricVersionsToGV[apiGroup.PreferredVersion.GroupVersion]; present && len(apiGroup.PreferredVersion.GroupVersion) != 0 {
|
||||
preferredVersion = &gv
|
||||
} else {
|
||||
for _, version := range apiGroup.Versions {
|
||||
if gv, present := metricVersionsToGV[version.GroupVersion]; present {
|
||||
preferredVersion = &gv
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if preferredVersion == nil {
|
||||
return schema.GroupVersion{}, fmt.Errorf("no known available metric versions found")
|
||||
}
|
||||
return *preferredVersion, nil
|
||||
}
|
||||
|
||||
// PreferredVersion returns the current preferred version of the custom metrics api.
|
||||
// If none is specified, it will use the first known one.
|
||||
func (d *apiVersionsFromDiscovery) PreferredVersion() (schema.GroupVersion, error) {
|
||||
d.mu.RLock()
|
||||
if d.prefVersion != nil {
|
||||
// if we've already got one, proceed with that
|
||||
defer d.mu.RUnlock()
|
||||
return *d.prefVersion, nil
|
||||
}
|
||||
d.mu.RUnlock()
|
||||
|
||||
d.mu.Lock()
|
||||
defer d.mu.Unlock()
|
||||
|
||||
// double check, someone might have beaten us to it
|
||||
if d.prefVersion != nil {
|
||||
return *d.prefVersion, nil
|
||||
}
|
||||
|
||||
// populate our cache
|
||||
groupInfo, err := d.fetchVersions()
|
||||
if err != nil {
|
||||
return schema.GroupVersion{}, err
|
||||
}
|
||||
prefVersion, err := d.chooseVersion(groupInfo)
|
||||
if err != nil {
|
||||
return schema.GroupVersion{}, err
|
||||
}
|
||||
|
||||
d.prefVersion = &prefVersion
|
||||
return *d.prefVersion, nil
|
||||
}
|
||||
|
||||
// Invalidate refreshes the preferred version information.
|
||||
func (d *apiVersionsFromDiscovery) Invalidate() {
|
||||
d.mu.Lock()
|
||||
defer d.mu.Unlock()
|
||||
|
||||
d.prefVersion = nil
|
||||
}
|
|
@ -0,0 +1,138 @@
|
|||
/*
|
||||
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 custom_metrics
|
||||
|
||||
import (
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"k8s.io/apimachinery/pkg/api/meta"
|
||||
"k8s.io/apimachinery/pkg/labels"
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
"k8s.io/client-go/rest"
|
||||
|
||||
"k8s.io/metrics/pkg/apis/custom_metrics/v1beta2"
|
||||
)
|
||||
|
||||
// AvailableAPIsGetter knows how to fetch and cache the preferred custom metrics API version,
|
||||
// and invalidate that cache when asked.
|
||||
type AvailableAPIsGetter interface {
|
||||
PreferredVersion() (schema.GroupVersion, error)
|
||||
Invalidate()
|
||||
}
|
||||
|
||||
// PeriodicallyInvalidate periodically invalidates the preferred version cache until
|
||||
// told to stop.
|
||||
func PeriodicallyInvalidate(cache AvailableAPIsGetter, interval time.Duration, stopCh <-chan struct{}) {
|
||||
ticker := time.NewTicker(interval)
|
||||
defer ticker.Stop()
|
||||
|
||||
for {
|
||||
select {
|
||||
case <-ticker.C:
|
||||
cache.Invalidate()
|
||||
case <-stopCh:
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// NewForConfig creates a new custom metrics client which delegates to a client which
|
||||
// uses the preferred api version.
|
||||
func NewForConfig(baseConfig *rest.Config, mapper meta.RESTMapper, availableAPIs AvailableAPIsGetter) CustomMetricsClient {
|
||||
return &multiClient{
|
||||
clients: make(map[schema.GroupVersion]CustomMetricsClient),
|
||||
availableAPIs: availableAPIs,
|
||||
|
||||
newClient: func(ver schema.GroupVersion) (CustomMetricsClient, error) {
|
||||
return NewForVersionForConfig(rest.CopyConfig(baseConfig), mapper, ver)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
// multiClient is a CustomMetricsClient that can work with *any* metrics API version.
|
||||
type multiClient struct {
|
||||
newClient func(schema.GroupVersion) (CustomMetricsClient, error)
|
||||
clients map[schema.GroupVersion]CustomMetricsClient
|
||||
availableAPIs AvailableAPIsGetter
|
||||
mu sync.RWMutex
|
||||
}
|
||||
|
||||
// getPreferredClient returns a custom metrics client of the preferred api version.
|
||||
func (c *multiClient) getPreferredClient() (CustomMetricsClient, error) {
|
||||
pref, err := c.availableAPIs.PreferredVersion()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
c.mu.RLock()
|
||||
client, present := c.clients[pref]
|
||||
c.mu.RUnlock()
|
||||
if present {
|
||||
return client, nil
|
||||
}
|
||||
|
||||
c.mu.Lock()
|
||||
defer c.mu.Unlock()
|
||||
client, err = c.newClient(pref)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
c.clients[pref] = client
|
||||
|
||||
return client, nil
|
||||
}
|
||||
|
||||
func (c *multiClient) RootScopedMetrics() MetricsInterface {
|
||||
return &multiClientInterface{clients: c}
|
||||
}
|
||||
|
||||
func (c *multiClient) NamespacedMetrics(namespace string) MetricsInterface {
|
||||
return &multiClientInterface{
|
||||
clients: c,
|
||||
namespace: &namespace,
|
||||
}
|
||||
}
|
||||
|
||||
type multiClientInterface struct {
|
||||
clients *multiClient
|
||||
namespace *string
|
||||
}
|
||||
|
||||
func (m *multiClientInterface) GetForObject(groupKind schema.GroupKind, name string, metricName string, metricSelector labels.Selector) (*v1beta2.MetricValue, error) {
|
||||
client, err := m.clients.getPreferredClient()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if m.namespace == nil {
|
||||
return client.RootScopedMetrics().GetForObject(groupKind, name, metricName, metricSelector)
|
||||
} else {
|
||||
return client.NamespacedMetrics(*m.namespace).GetForObject(groupKind, name, metricName, metricSelector)
|
||||
}
|
||||
}
|
||||
|
||||
func (m *multiClientInterface) GetForObjects(groupKind schema.GroupKind, selector labels.Selector, metricName string, metricSelector labels.Selector) (*v1beta2.MetricValueList, error) {
|
||||
client, err := m.clients.getPreferredClient()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if m.namespace == nil {
|
||||
return client.RootScopedMetrics().GetForObjects(groupKind, selector, metricName, metricSelector)
|
||||
} else {
|
||||
return client.NamespacedMetrics(*m.namespace).GetForObjects(groupKind, selector, metricName, metricSelector)
|
||||
}
|
||||
}
|
|
@ -11,6 +11,7 @@ go_library(
|
|||
"//staging/src/k8s.io/apimachinery/pkg/runtime:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/runtime/schema:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/runtime/serializer:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics/v1beta1:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics/v1beta2:go_default_library",
|
||||
],
|
||||
|
|
|
@ -21,10 +21,15 @@ import (
|
|||
runtime "k8s.io/apimachinery/pkg/runtime"
|
||||
schema "k8s.io/apimachinery/pkg/runtime/schema"
|
||||
serializer "k8s.io/apimachinery/pkg/runtime/serializer"
|
||||
cmint "k8s.io/metrics/pkg/apis/custom_metrics"
|
||||
cmv1beta1 "k8s.io/metrics/pkg/apis/custom_metrics/v1beta1"
|
||||
cmv1beta2 "k8s.io/metrics/pkg/apis/custom_metrics/v1beta2"
|
||||
)
|
||||
|
||||
const GroupName = cmv1beta1.GroupName
|
||||
|
||||
var SchemeGroupVersion = schema.GroupVersion{Group: GroupName, Version: runtime.APIVersionInternal}
|
||||
|
||||
var Scheme = runtime.NewScheme()
|
||||
var Codecs = serializer.NewCodecFactory(Scheme)
|
||||
var ParameterCodec = runtime.NewParameterCodec(Scheme)
|
||||
|
@ -49,6 +54,7 @@ func init() {
|
|||
// After this, RawExtensions in Kubernetes types will serialize kube-aggregator types
|
||||
// correctly.
|
||||
func AddToScheme(scheme *runtime.Scheme) {
|
||||
cmint.AddToScheme(scheme)
|
||||
cmv1beta1.AddToScheme(scheme)
|
||||
cmv1beta2.AddToScheme(scheme)
|
||||
}
|
||||
|
|
|
@ -0,0 +1,65 @@
|
|||
/*
|
||||
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 custom_metrics
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||
"k8s.io/apimachinery/pkg/runtime"
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
|
||||
cmint "k8s.io/metrics/pkg/apis/custom_metrics"
|
||||
cmv1beta1 "k8s.io/metrics/pkg/apis/custom_metrics/v1beta1"
|
||||
cmv1beta2 "k8s.io/metrics/pkg/apis/custom_metrics/v1beta2"
|
||||
)
|
||||
|
||||
func TestMetricConverter(t *testing.T) {
|
||||
testCases := []struct {
|
||||
name string
|
||||
group schema.GroupVersion
|
||||
expected runtime.Object
|
||||
}{
|
||||
{
|
||||
name: "Use custom metrics v1beta2",
|
||||
group: cmv1beta2.SchemeGroupVersion,
|
||||
expected: &cmv1beta2.MetricListOptions{
|
||||
TypeMeta: metav1.TypeMeta{Kind: "MetricListOptions", APIVersion: cmv1beta2.SchemeGroupVersion.String()},
|
||||
MetricLabelSelector: "foo",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "Use custom metrics v1beta1",
|
||||
group: cmv1beta1.SchemeGroupVersion,
|
||||
expected: &cmv1beta1.MetricListOptions{
|
||||
TypeMeta: metav1.TypeMeta{Kind: "MetricListOptions", APIVersion: cmv1beta1.SchemeGroupVersion.String()},
|
||||
MetricLabelSelector: "foo",
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for _, test := range testCases {
|
||||
t.Run(test.name, func(t *testing.T) {
|
||||
metricConverter := NewMetricConverter()
|
||||
opts := &cmint.MetricListOptions{MetricLabelSelector: "foo"}
|
||||
res, err := metricConverter.ConvertListOptionsToVersion(opts, test.group)
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, test.expected, res)
|
||||
})
|
||||
}
|
||||
}
|
|
@ -25,22 +25,35 @@ import (
|
|||
serializer "k8s.io/apimachinery/pkg/runtime/serializer"
|
||||
"k8s.io/client-go/rest"
|
||||
"k8s.io/client-go/util/flowcontrol"
|
||||
|
||||
cmint "k8s.io/metrics/pkg/apis/custom_metrics"
|
||||
"k8s.io/metrics/pkg/apis/custom_metrics/v1beta1"
|
||||
"k8s.io/metrics/pkg/apis/custom_metrics/v1beta2"
|
||||
"k8s.io/metrics/pkg/client/custom_metrics/scheme"
|
||||
)
|
||||
|
||||
var (
|
||||
codecs = serializer.NewCodecFactory(scheme.Scheme)
|
||||
versionConverter = NewMetricConverter()
|
||||
)
|
||||
|
||||
type customMetricsClient struct {
|
||||
client rest.Interface
|
||||
mapper meta.RESTMapper
|
||||
client rest.Interface
|
||||
version schema.GroupVersion
|
||||
mapper meta.RESTMapper
|
||||
}
|
||||
|
||||
func New(client rest.Interface) CustomMetricsClient {
|
||||
// NewForVersion returns a new CustomMetricsClient for a particular api version.
|
||||
func NewForVersion(client rest.Interface, mapper meta.RESTMapper, version schema.GroupVersion) CustomMetricsClient {
|
||||
return &customMetricsClient{
|
||||
client: client,
|
||||
client: client,
|
||||
version: version,
|
||||
mapper: mapper,
|
||||
}
|
||||
}
|
||||
|
||||
func NewForConfig(c *rest.Config) (CustomMetricsClient, error) {
|
||||
// NewForVersionForConfig returns a new CustomMetricsClient for a particular api version and base configuration.
|
||||
func NewForVersionForConfig(c *rest.Config, mapper meta.RESTMapper, version schema.GroupVersion) (CustomMetricsClient, error) {
|
||||
configShallowCopy := *c
|
||||
if configShallowCopy.RateLimiter == nil && configShallowCopy.QPS > 0 {
|
||||
configShallowCopy.RateLimiter = flowcontrol.NewTokenBucketRateLimiter(configShallowCopy.QPS, configShallowCopy.Burst)
|
||||
|
@ -49,7 +62,7 @@ func NewForConfig(c *rest.Config) (CustomMetricsClient, error) {
|
|||
if configShallowCopy.UserAgent == "" {
|
||||
configShallowCopy.UserAgent = rest.DefaultKubernetesUserAgent()
|
||||
}
|
||||
configShallowCopy.GroupVersion = &v1beta2.SchemeGroupVersion
|
||||
configShallowCopy.GroupVersion = &version
|
||||
configShallowCopy.NegotiatedSerializer = serializer.DirectCodecFactory{CodecFactory: scheme.Codecs}
|
||||
|
||||
client, err := rest.RESTClientFor(&configShallowCopy)
|
||||
|
@ -57,24 +70,7 @@ func NewForConfig(c *rest.Config) (CustomMetricsClient, error) {
|
|||
return nil, err
|
||||
}
|
||||
|
||||
return New(client), nil
|
||||
}
|
||||
|
||||
func NewForConfigOrDie(c *rest.Config) CustomMetricsClient {
|
||||
client, err := NewForConfig(c)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return client
|
||||
}
|
||||
|
||||
// NewForMapper constructs the client with a RESTMapper, which allows more
|
||||
// accurate translation from GroupVersionKind to GroupVersionResource.
|
||||
func NewForMapper(client rest.Interface, mapper meta.RESTMapper) CustomMetricsClient {
|
||||
return &customMetricsClient{
|
||||
client: client,
|
||||
mapper: mapper,
|
||||
}
|
||||
return NewForVersion(client, mapper, version), nil
|
||||
}
|
||||
|
||||
func (c *customMetricsClient) RootScopedMetrics() MetricsInterface {
|
||||
|
@ -88,16 +84,8 @@ func (c *customMetricsClient) NamespacedMetrics(namespace string) MetricsInterfa
|
|||
}
|
||||
}
|
||||
|
||||
// qualResourceForKind returns the string format of a qualified group resource for the specified GroupKind
|
||||
func (c *customMetricsClient) qualResourceForKind(groupKind schema.GroupKind) (string, error) {
|
||||
if c.mapper == nil {
|
||||
// the version doesn't matter
|
||||
gvk := groupKind.WithVersion("")
|
||||
gvr, _ := meta.UnsafeGuessKindToResource(gvk)
|
||||
gr := gvr.GroupResource()
|
||||
return gr.String(), nil
|
||||
}
|
||||
|
||||
// use the mapper if it's available
|
||||
mapping, err := c.mapper.RESTMapping(groupKind)
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("unable to map kind %s to resource: %v", groupKind.String(), err)
|
||||
|
@ -112,21 +100,26 @@ type rootScopedMetrics struct {
|
|||
}
|
||||
|
||||
func (m *rootScopedMetrics) getForNamespace(namespace string, metricName string, metricSelector labels.Selector) (*v1beta2.MetricValue, error) {
|
||||
res := &v1beta2.MetricValueList{}
|
||||
err := m.client.client.Get().
|
||||
Resource("metrics").
|
||||
Namespace(namespace).
|
||||
Name(metricName).
|
||||
VersionedParams(&v1beta2.MetricListOptions{
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, scheme.ParameterCodec).
|
||||
Do().
|
||||
Into(res)
|
||||
|
||||
params, err := versionConverter.ConvertListOptionsToVersion(&cmint.MetricListOptions{
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, m.client.version)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
result := m.client.client.Get().
|
||||
Resource("metrics").
|
||||
Namespace(namespace).
|
||||
Name(metricName).
|
||||
VersionedParams(params, scheme.ParameterCodec).
|
||||
Do()
|
||||
|
||||
metricObj, err := versionConverter.ConvertResultToVersion(result, v1beta2.SchemeGroupVersion)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
res := metricObj.(*v1beta2.MetricValueList)
|
||||
if len(res.Items) != 1 {
|
||||
return nil, fmt.Errorf("the custom metrics API server returned %v results when we asked for exactly one", len(res.Items))
|
||||
}
|
||||
|
@ -145,21 +138,26 @@ func (m *rootScopedMetrics) GetForObject(groupKind schema.GroupKind, name string
|
|||
return nil, err
|
||||
}
|
||||
|
||||
res := &v1beta2.MetricValueList{}
|
||||
err = m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Name(name).
|
||||
SubResource(metricName).
|
||||
VersionedParams(&v1beta2.MetricListOptions{
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, scheme.ParameterCodec).
|
||||
Do().
|
||||
Into(res)
|
||||
|
||||
params, err := versionConverter.ConvertListOptionsToVersion(&cmint.MetricListOptions{
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, m.client.version)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
result := m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Name(name).
|
||||
SubResource(metricName).
|
||||
VersionedParams(params, scheme.ParameterCodec).
|
||||
Do()
|
||||
|
||||
metricObj, err := versionConverter.ConvertResultToVersion(result, v1beta2.SchemeGroupVersion)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
res := metricObj.(*v1beta2.MetricValueList)
|
||||
if len(res.Items) != 1 {
|
||||
return nil, fmt.Errorf("the custom metrics API server returned %v results when we asked for exactly one", len(res.Items))
|
||||
}
|
||||
|
@ -178,22 +176,27 @@ func (m *rootScopedMetrics) GetForObjects(groupKind schema.GroupKind, selector l
|
|||
return nil, err
|
||||
}
|
||||
|
||||
res := &v1beta2.MetricValueList{}
|
||||
err = m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Name(v1beta2.AllObjects).
|
||||
SubResource(metricName).
|
||||
VersionedParams(&v1beta2.MetricListOptions{
|
||||
LabelSelector: selector.String(),
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, scheme.ParameterCodec).
|
||||
Do().
|
||||
Into(res)
|
||||
|
||||
params, err := versionConverter.ConvertListOptionsToVersion(&cmint.MetricListOptions{
|
||||
LabelSelector: selector.String(),
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, m.client.version)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
result := m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Name(v1beta1.AllObjects).
|
||||
SubResource(metricName).
|
||||
VersionedParams(params, scheme.ParameterCodec).
|
||||
Do()
|
||||
|
||||
metricObj, err := versionConverter.ConvertResultToVersion(result, v1beta2.SchemeGroupVersion)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
res := metricObj.(*v1beta2.MetricValueList)
|
||||
return res, nil
|
||||
}
|
||||
|
||||
|
@ -208,22 +211,27 @@ func (m *namespacedMetrics) GetForObject(groupKind schema.GroupKind, name string
|
|||
return nil, err
|
||||
}
|
||||
|
||||
res := &v1beta2.MetricValueList{}
|
||||
err = m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Namespace(m.namespace).
|
||||
Name(name).
|
||||
SubResource(metricName).
|
||||
VersionedParams(&v1beta2.MetricListOptions{
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, scheme.ParameterCodec).
|
||||
Do().
|
||||
Into(res)
|
||||
|
||||
params, err := versionConverter.ConvertListOptionsToVersion(&cmint.MetricListOptions{
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, m.client.version)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
result := m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Namespace(m.namespace).
|
||||
Name(name).
|
||||
SubResource(metricName).
|
||||
VersionedParams(params, scheme.ParameterCodec).
|
||||
Do()
|
||||
|
||||
metricObj, err := versionConverter.ConvertResultToVersion(result, v1beta2.SchemeGroupVersion)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
res := metricObj.(*v1beta2.MetricValueList)
|
||||
if len(res.Items) != 1 {
|
||||
return nil, fmt.Errorf("the custom metrics API server returned %v results when we asked for exactly one", len(res.Items))
|
||||
}
|
||||
|
@ -237,22 +245,27 @@ func (m *namespacedMetrics) GetForObjects(groupKind schema.GroupKind, selector l
|
|||
return nil, err
|
||||
}
|
||||
|
||||
res := &v1beta2.MetricValueList{}
|
||||
err = m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Namespace(m.namespace).
|
||||
Name(v1beta2.AllObjects).
|
||||
SubResource(metricName).
|
||||
VersionedParams(&v1beta2.MetricListOptions{
|
||||
LabelSelector: selector.String(),
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, scheme.ParameterCodec).
|
||||
Do().
|
||||
Into(res)
|
||||
|
||||
params, err := versionConverter.ConvertListOptionsToVersion(&cmint.MetricListOptions{
|
||||
LabelSelector: selector.String(),
|
||||
MetricLabelSelector: metricSelector.String(),
|
||||
}, m.client.version)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
result := m.client.client.Get().
|
||||
Resource(resourceName).
|
||||
Namespace(m.namespace).
|
||||
Name(v1beta1.AllObjects).
|
||||
SubResource(metricName).
|
||||
VersionedParams(params, scheme.ParameterCodec).
|
||||
Do()
|
||||
|
||||
metricObj, err := versionConverter.ConvertResultToVersion(result, v1beta2.SchemeGroupVersion)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
res := metricObj.(*v1beta2.MetricValueList)
|
||||
return res, nil
|
||||
}
|
|
@ -22,6 +22,7 @@ go_library(
|
|||
"//staging/src/k8s.io/api/core/v1:go_default_library",
|
||||
"//staging/src/k8s.io/api/extensions/v1beta1:go_default_library",
|
||||
"//staging/src/k8s.io/api/rbac/v1:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/api/meta:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/api/resource:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/apis/meta/v1:go_default_library",
|
||||
"//staging/src/k8s.io/apimachinery/pkg/labels:go_default_library",
|
||||
|
@ -30,6 +31,7 @@ go_library(
|
|||
"//staging/src/k8s.io/apimachinery/pkg/util/wait:go_default_library",
|
||||
"//staging/src/k8s.io/client-go/discovery:go_default_library",
|
||||
"//staging/src/k8s.io/client-go/kubernetes:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/apis/custom_metrics/v1beta1:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/client/custom_metrics:go_default_library",
|
||||
"//staging/src/k8s.io/metrics/pkg/client/external_metrics:go_default_library",
|
||||
"//test/e2e/common:go_default_library",
|
||||
|
|
|
@ -29,11 +29,13 @@ import (
|
|||
|
||||
gcm "google.golang.org/api/monitoring/v3"
|
||||
"k8s.io/api/core/v1"
|
||||
"k8s.io/apimachinery/pkg/api/meta"
|
||||
"k8s.io/apimachinery/pkg/labels"
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
"k8s.io/apimachinery/pkg/selection"
|
||||
"k8s.io/client-go/discovery"
|
||||
"k8s.io/kubernetes/test/e2e/framework"
|
||||
cmv1beta1 "k8s.io/metrics/pkg/apis/custom_metrics/v1beta1"
|
||||
customclient "k8s.io/metrics/pkg/client/custom_metrics"
|
||||
externalclient "k8s.io/metrics/pkg/client/external_metrics"
|
||||
)
|
||||
|
@ -57,8 +59,10 @@ var _ = instrumentation.SIGDescribe("Stackdriver Monitoring", func() {
|
|||
if err != nil {
|
||||
framework.Failf("Failed to load config: %s", err)
|
||||
}
|
||||
customMetricsClient := customclient.NewForConfigOrDie(config)
|
||||
discoveryClient := discovery.NewDiscoveryClientForConfigOrDie(config)
|
||||
apiVersionsGetter := customclient.NewAvailableAPIsGetter(discoveryClient)
|
||||
restMapper := meta.NewDefaultRESTMapper([]schema.GroupVersion{cmv1beta1.SchemeGroupVersion})
|
||||
customMetricsClient := customclient.NewForConfig(config, restMapper, apiVersionsGetter)
|
||||
testCustomMetrics(f, kubeClient, customMetricsClient, discoveryClient, AdapterForOldResourceModel)
|
||||
})
|
||||
|
||||
|
@ -68,8 +72,10 @@ var _ = instrumentation.SIGDescribe("Stackdriver Monitoring", func() {
|
|||
if err != nil {
|
||||
framework.Failf("Failed to load config: %s", err)
|
||||
}
|
||||
customMetricsClient := customclient.NewForConfigOrDie(config)
|
||||
discoveryClient := discovery.NewDiscoveryClientForConfigOrDie(config)
|
||||
apiVersionsGetter := customclient.NewAvailableAPIsGetter(discoveryClient)
|
||||
restMapper := meta.NewDefaultRESTMapper([]schema.GroupVersion{cmv1beta1.SchemeGroupVersion})
|
||||
customMetricsClient := customclient.NewForConfig(config, restMapper, apiVersionsGetter)
|
||||
testCustomMetrics(f, kubeClient, customMetricsClient, discoveryClient, AdapterForNewResourceModel)
|
||||
})
|
||||
|
||||
|
|
Loading…
Reference in New Issue