Labels and annotations in Kubernetes
Tags: kubernetes, devops
Published: 2023-04-24 13:20:42

In Kubernetes, you can use labels to assign key-value pairs to any resources.

Labels are ubiquitous and necessary to everyday operations such as creating services.

_However, how should you name and use those labels?_

Any resource in Kubernetes can have labels.

**Some labels are vital (e.g. service's selector, operators, etc.), and others are useful to tag resources (e.g. labelling a deployment).**

![Examples of useful and useless labels in Kubernetes](https://res.cloudinary.com/learnk8s/image/upload/v1682338596/threads/labels-annotations-2_q2c1df.png)

Kubectl offers a `--show-labels` flag to help you list resources and their labels.

If you list pods, deployments and services in an empty cluster, you might notice that Kubernetes uses the `component=<name>` label to tag pods.

![Retrieving labels from resources](https://res.cloudinary.com/learnk8s/image/upload/v1682338596/threads/labels-annotations-3_uqi77a.png)

**Kubernetes recommends six labels for your resources:**

1. Name
2. Instance
3. Version
4. Component
5. Part of
6. Managed By

![Recommended labels for resources](https://res.cloudinary.com/learnk8s/image/upload/v1682338597/threads/labels-annotations-4_lemowe.png)

Let's look at an excellent example of using those labels: [the Prometheus Helm chart.](https://github.com/prometheus-community/helm-charts)

The charts install five pods (i.e. server, alter manager, node exporter, push gateway and kube state metrics).

_Notice how not all labels are applied to all pods._

![Prometheus Helm chart labels](https://res.cloudinary.com/learnk8s/image/upload/v1682338597/threads/labels-annotations-5_c2wsei.png)

Labelling resources properly helps you make sense of what's deployed.

For example, you can filter results with kubectl:

```bash
kubectl get pods -l "environment in (staging, dev)"
```

The command above only lists pod in staging and dev.

![Selecting resources that are tagged with labels](https://res.cloudinary.com/learnk8s/image/upload/v1682338596/threads/labels-annotations-6_ifwhuu.png)

If those labels are not what you are after, you can always create your own.

A `<prefix>/<name>` key is recommended — e.g. `company.com/database`.

![Custom label with prefixes](https://res.cloudinary.com/learnk8s/image/upload/v1682338597/threads/labels-annotations-7_bxomwj.png)

The following labels could be used in a multitenant cluster:

- Business unit
- Development team
- Application
- Client
- Shared services
- Environment
- Compliance
- Asset classification

![Labels for multitenant cluster](https://res.cloudinary.com/learnk8s/image/upload/v1682338597/threads/labels-annotations-8_fbwiwr.png)

Alongside labels, you have annotations.

**Whereas labels are used to select resources, annotations decorate resources with metadata.**

You cannot select resources with annotations.

![Annotations in Kubernetes](https://res.cloudinary.com/learnk8s/image/upload/v1682338847/threads/labels-annotations-9_ltswyf.png)

Administrators can assign annotations to any workload.

However, more often, **Kubernetes and operators decorate resources with extra annotations.**

A good example is the annotation `kubernetes.io/ingress-bandwidth` to assign bandwidth to pods.

![Annotating resources with ingress and egress bandwidth constraints](https://res.cloudinary.com/learnk8s/image/upload/v1682338847/threads/labels-annotations-10_bjzwqe.png)

[The official documentation has a list of well-known labels and annotations.](https://kubernetes.io/docs/reference/labels-annotations-taints/)

Here are some examples:

- `kubectl.kubernetesׄ.io/default-container`
- `topology.kubernetes.io/region`
- `node.kubernetes.io/instance-type`
- `kubernetes.io/egress-bandwidth`

**Annotations are used extensively in operators.**

Look at [all the annotations you can use with the ingress-nginx controller.](https://github.com/kubernetes/ingress-nginx/blob/main/docs/user-guide/nginx-configuration/annotations.md)

![There are several annotations available for the ingress-nginx controller](https://res.cloudinary.com/learnk8s/image/upload/v1682338847/threads/labels-annotations-11_yi1pdu.png)

Unfortunately, using operators/cloud providers/etc. annotations is not always a good idea if you wish to stay vendor-neutral.

However, sometimes it's also the only option [(e.g. having an AWS ALB deployed in the correct subnet when using a service of type LoadBalancer).](https://docs.aws.amazon.com/eks/latest/userguide/network-load-balancing.html)

![Annotations available on AWS and EKS](https://res.cloudinary.com/learnk8s/image/upload/v1682338847/threads/labels-annotations-12_plna0c.png)

Here are a few links if you want to learn more:

- [The Guide to Kubernetes Labels](https://blog.kubecost.com/blog/kubernetes-labels/)
- [Well-Known Labels, Annotations and Taints](https://kubernetes.io/docs/reference/labels-annotations-taints/)
- [Recommended Labels](https://kubernetes.io/docs/concepts/overview/working-with-objects/common-labels/)
- [Label standard and best practices for Kubernetes security](https://www.tigera.io/blog/label-standard-and-best-practices-for-kubernetes-security/)

And finally, if you've enjoyed this thread, you might also like:

- [The Kubernetes workshops that we run at Learnk8s.](https://learnk8s.io/training)
- [This collection of past threads.](https://twitter.com/danielepolencic/status/1298543151901155330)
- [The Kubernetes newsletter I publish every week.](https://learnk8s.io/learn-kubernetes-weekly)