karmada/pkg/util/label_test.go

608 lines
15 KiB
Go

/*
Copyright 2022 The Karmada 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 util
import (
"reflect"
"testing"
"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
workv1alpha2 "github.com/karmada-io/karmada/pkg/apis/work/v1alpha2"
)
func TestGetLabelValue(t *testing.T) {
tests := []struct {
name string
labels map[string]string
labelKey string
expected string
}{
{
name: "nil labels",
labels: nil,
expected: "",
},
{
name: "empty labelKey",
labels: map[string]string{"foo": "bar"},
expected: "",
},
{
name: "no exist labelKey",
labels: map[string]string{"foo": "bar"},
labelKey: "foo1",
expected: "",
},
{
name: "exist labelKey",
labels: map[string]string{"foo": "bar"},
labelKey: "foo",
expected: "bar",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
res := GetLabelValue(tt.labels, tt.labelKey)
if res != tt.expected {
t.Errorf("GetLabelValue() = %v, want %v", res, tt.expected)
}
})
}
}
func TestMergeLabel(t *testing.T) {
tests := []struct {
name string
obj *unstructured.Unstructured
labelKey string
labelValue string
expected *unstructured.Unstructured
}{
{
name: "nil labels",
obj: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
labelKey: "foo",
labelValue: "bar",
},
{
name: "same labelKey",
obj: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar1"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
labelKey: "foo",
labelValue: "bar1",
},
{
name: "new labelKey",
obj: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar", "foo1": "bar1"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
labelKey: "foo1",
labelValue: "bar1",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
MergeLabel(tt.obj, tt.labelKey, tt.labelValue)
if !reflect.DeepEqual(tt.obj, tt.expected) {
t.Errorf("MergeLabel() = %v, want %v", tt.obj, tt.expected)
}
})
}
}
func TestDedupeAndMergeLabels(t *testing.T) {
tests := []struct {
name string
existLabel map[string]string
newLabel map[string]string
expected map[string]string
}{
{
name: "two labels are nil",
existLabel: nil,
newLabel: nil,
expected: nil,
},
{
name: "nil newLabel",
existLabel: map[string]string{"foo": "bar"},
newLabel: nil,
expected: map[string]string{"foo": "bar"},
},
{
name: "nil existLabel",
existLabel: nil,
newLabel: map[string]string{"foo": "bar"},
expected: map[string]string{"foo": "bar"},
},
{
name: "same labelKey",
existLabel: map[string]string{"foo": "bar"},
newLabel: map[string]string{"foo": "bar"},
expected: map[string]string{"foo": "bar"},
},
{
name: "different labelKeys",
existLabel: map[string]string{"foo": "bar"},
newLabel: map[string]string{"foo1": "bar1"},
expected: map[string]string{"foo": "bar", "foo1": "bar1"},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
res := DedupeAndMergeLabels(tt.existLabel, tt.newLabel)
if !reflect.DeepEqual(res, tt.expected) {
t.Errorf("DedupeAndMergeLabels() = %v, want %v", res, tt.expected)
}
})
}
}
func TestRemoveLabel(t *testing.T) {
type args struct {
obj *unstructured.Unstructured
labelKey string
}
tests := []struct {
name string
args args
expected *unstructured.Unstructured
}{
{
name: "nil object labels",
args: args{
obj: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
},
"spec": map[string]interface{}{
"replicas": 2,
}}},
labelKey: "foo",
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
},
"spec": map[string]interface{}{
"replicas": 2,
}}},
},
{
name: "same labelKey",
args: args{
obj: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
}}},
labelKey: "foo",
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{},
},
"spec": map[string]interface{}{
"replicas": 2,
}}},
},
{
name: "different labelKey",
args: args{
obj: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
}}},
labelKey: "foo1",
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
}}},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
RemoveLabels(tt.args.obj, tt.args.labelKey)
if !reflect.DeepEqual(tt.args.obj, tt.expected) {
t.Errorf("RemoveLabel() = %v, want %v", tt.args.obj, tt.expected)
}
})
}
}
func TestRetainLabels(t *testing.T) {
tests := []struct {
name string
desired *unstructured.Unstructured
observed *unstructured.Unstructured
expected *unstructured.Unstructured
}{
{
name: "observed has nil labels",
desired: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
observed: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
},
{
name: "observed has labels",
desired: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
observed: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
},
{
name: "observed and desired have the same label key",
desired: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "foo"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
observed: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
"labels": map[string]interface{}{"foo": "bar"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"labels": map[string]interface{}{"foo": "foo"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
},
{
name: "do not merge deleted labels",
desired: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"annotations": map[string]interface{}{workv1alpha2.ManagedLabels: "foo"},
"labels": map[string]interface{}{"foo": "foo"},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
observed: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
"annotations": map[string]interface{}{workv1alpha2.ManagedLabels: "foo,deleted"},
"labels": map[string]interface{}{
"foo": "bar",
"deleted": "deleted",
"retain": "retain",
},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment",
"annotations": map[string]interface{}{workv1alpha2.ManagedLabels: "foo"},
"labels": map[string]interface{}{
"foo": "foo",
"retain": "retain",
},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
RetainLabels(tt.desired, tt.observed)
if !reflect.DeepEqual(tt.desired, tt.expected) {
t.Errorf("RetainLabels() = %v, want %v", tt.desired, tt.expected)
}
})
}
}
func TestRecordManagedLabels(t *testing.T) {
tests := []struct {
name string
object *unstructured.Unstructured
expected *unstructured.Unstructured
}{
{
name: "nil label",
object: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
"annotations": map[string]interface{}{
workv1alpha2.ManagedLabels: "",
},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
},
{
name: "object has has labels",
object: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
"labels": map[string]interface{}{
"foo": "foo",
},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
expected: &unstructured.Unstructured{
Object: map[string]interface{}{
"apiVersion": "apps/v1",
"kind": "Deployment",
"metadata": map[string]interface{}{
"name": "demo-deployment-1",
"annotations": map[string]interface{}{
workv1alpha2.ManagedLabels: "foo",
},
"labels": map[string]interface{}{
"foo": "foo",
},
},
"spec": map[string]interface{}{
"replicas": 2,
},
},
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
RecordManagedLabels(tt.object)
if !reflect.DeepEqual(tt.object, tt.expected) {
t.Errorf("RecordManagedLabels() = %v, want %v", tt.object, tt.expected)
}
})
}
}