github.com/Racer159/jackal@v0.32.7-0.20240401174413-0bd2339e4f2e/src/pkg/k8s/dynamic.go (about) 1 // SPDX-License-Identifier: Apache-2.0 2 // SPDX-FileCopyrightText: 2021-Present The Jackal Authors 3 4 // Package k8s provides a client for interacting with a Kubernetes cluster. 5 package k8s 6 7 import ( 8 "context" 9 10 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 11 "k8s.io/apimachinery/pkg/runtime/schema" 12 "k8s.io/client-go/discovery" 13 "k8s.io/client-go/dynamic" 14 "k8s.io/client-go/restmapper" 15 ) 16 17 // AddLabelsAndAnnotations adds the provided labels and annotations to the specified K8s resource 18 func (k *K8s) AddLabelsAndAnnotations(resourceNamespace string, resourceName string, groupKind schema.GroupKind, labels map[string]string, annotations map[string]string) error { 19 return k.updateLabelsAndAnnotations(resourceNamespace, resourceName, groupKind, labels, annotations, false) 20 } 21 22 // RemoveLabelsAndAnnotations removes the provided labels and annotations to the specified K8s resource 23 func (k *K8s) RemoveLabelsAndAnnotations(resourceNamespace string, resourceName string, groupKind schema.GroupKind, labels map[string]string, annotations map[string]string) error { 24 return k.updateLabelsAndAnnotations(resourceNamespace, resourceName, groupKind, labels, annotations, true) 25 } 26 27 // updateLabelsAndAnnotations updates the provided labels and annotations to the specified K8s resource 28 func (k *K8s) updateLabelsAndAnnotations(resourceNamespace string, resourceName string, groupKind schema.GroupKind, labels map[string]string, annotations map[string]string, isRemove bool) error { 29 dynamicClient := dynamic.NewForConfigOrDie(k.RestConfig) 30 31 discoveryClient := discovery.NewDiscoveryClientForConfigOrDie(k.RestConfig) 32 33 groupResources, err := restmapper.GetAPIGroupResources(discoveryClient) 34 if err != nil { 35 return err 36 } 37 mapper := restmapper.NewDiscoveryRESTMapper(groupResources) 38 39 mapping, err := mapper.RESTMapping(groupKind) 40 if err != nil { 41 return err 42 } 43 44 deployedResource, err := dynamicClient.Resource(mapping.Resource).Namespace(resourceNamespace).Get(context.TODO(), resourceName, metav1.GetOptions{}) 45 if err != nil { 46 return err 47 } 48 49 // Pull the existing labels from the rendered resource 50 deployedLabels := deployedResource.GetLabels() 51 if deployedLabels == nil { 52 // Ensure label map exists to avoid nil panic 53 deployedLabels = make(map[string]string) 54 } 55 for key, value := range labels { 56 if isRemove { 57 delete(deployedLabels, key) 58 } else { 59 deployedLabels[key] = value 60 } 61 } 62 63 deployedResource.SetLabels(deployedLabels) 64 65 // Pull the existing annotations from the rendered resource 66 deployedAnnotations := deployedResource.GetAnnotations() 67 if deployedAnnotations == nil { 68 // Ensure label map exists to avoid nil panic 69 deployedAnnotations = make(map[string]string) 70 } 71 for key, value := range annotations { 72 if isRemove { 73 delete(deployedAnnotations, key) 74 } else { 75 deployedAnnotations[key] = value 76 } 77 } 78 79 deployedResource.SetAnnotations(deployedAnnotations) 80 81 _, err = dynamicClient.Resource(mapping.Resource).Namespace(resourceNamespace).Update(context.TODO(), deployedResource, metav1.UpdateOptions{}) 82 return err 83 }