<p>I want to create a controller and listen to the pod events when new pod is created (by a deployment) then add all labels belong to deployment to the created pod, is this possible at scale with <code>client-go</code>?</p>

hani
<p>In order to observe pod events, you need to use informers. Informers have built-in optimizations to avoid overloading API servers.</p>
<p>There is a patch method available in the PodInterface that allows you to add a label to a pod.</p>
<p>Here is a sample code for your reference. In the main function, the informer code is added, and the LabelPod function implements the label logic.</p>
<pre><code>package main

import (
    &quot;context&quot;
    &quot;encoding/json&quot;
    &quot;fmt&quot;
    &quot;time&quot;

    v1 &quot;k8s.io/api/core/v1&quot;
    metav1 &quot;k8s.io/apimachinery/pkg/apis/meta/v1&quot;
    &quot;k8s.io/apimachinery/pkg/labels&quot;
    &quot;k8s.io/apimachinery/pkg/types&quot;
    &quot;k8s.io/apimachinery/pkg/util/wait&quot;
    &quot;k8s.io/client-go/informers&quot;
    &quot;k8s.io/client-go/kubernetes&quot;
    &quot;k8s.io/client-go/rest&quot;
    &quot;k8s.io/client-go/tools/cache&quot;
)

type patchStringValue struct {
    Op    string `json:&quot;op&quot;`
    Path  string `json:&quot;path&quot;`
    Value string `json:&quot;value&quot;`
}

func main() {
    clientSet := GetK8sClient()

    labelOptions := informers.WithTweakListOptions(func(opts *metav1.ListOptions) {
        opts.LabelSelector = GetLabelSelectorForDeployment(&quot;deployment-name&quot;, &quot;namespace-name&quot;)
    })
    informers := informers.NewSharedInformerFactoryWithOptions(clientSet, 10*time.Second, informers.WithNamespace(&quot;namespace-name&quot;), labelOptions)

    podInformer := informers.Core().V1().Pods()

    podInformer.Informer().AddEventHandler(
        cache.ResourceEventHandlerFuncs{
            AddFunc: handleAdd,
        },
    )

    informers.Start(wait.NeverStop)
    informers.WaitForCacheSync(wait.NeverStop)

}

func GetLabelSelectorForDeployment(Name string, Namespace string) string {
    clientSet := GetK8sClient()

    k8sClient := clientSet.AppsV1()

    deployment, _ := k8sClient.Deployments(Namespace).Get(context.Background(), Name, metav1.GetOptions{})

    labelSet := labels.Set(deployment.Spec.Selector.MatchLabels)

    return string(labelSet.AsSelector().String())
}

func handleAdd(obj interface{}) {
    k8sClient := GetK8sClient().CoreV1()
    pod := obj.(*v1.Pod)
    fmt.Println(&quot;Pod&quot;, pod.GetName(), pod.Spec.NodeName, pod.Spec.Containers)
    payload := []patchStringValue{{
        Op:    &quot;replace&quot;,
        Path:  &quot;/metadata/labels/testLabel&quot;,
        Value: &quot;testValue&quot;,
    }}
    payloadBytes, _ := json.Marshal(payload)

    _, updateErr := k8sClient.Pods(pod.GetNamespace()).Patch(context.Background(), pod.GetName(), types.JSONPatchType, payloadBytes, metav1.PatchOptions{})
    if updateErr == nil {
        fmt.Println(fmt.Sprintf(&quot;Pod %s labelled successfully.&quot;, pod.GetName()))
    } else {
        fmt.Println(updateErr)
    }

}

func GetK8sClient() *kubernetes.Clientset {
    config, err := rest.InClusterConfig()
    if err != nil {
        panic(err.Error())
    }
    // creates the clientset
    clientset, err := kubernetes.NewForConfig(config)
    if err != nil {
        panic(err.Error())
    }

    return clientset
}

</code></pre>
