# Smarter Pod Scheduling with MatchLabelKeys in Pod Affinity
> Enhance Kubernetes pod scheduling with dynamic affinity using matchLabelKeys and mismatchLabelKeys for safer rollouts and tenant isolation.

Canonical: https://blog.abhimanyu-saharan.com/posts/smarter-pod-scheduling-with-matchlabelkeys-in-pod-affinity
Published: 2025-06-20
Last updated: 2025-06-19
Authors: Abhimanyu Saharan
Categories: Kubernetes v1.33, Kubernetes

Kubernetes has introduced a powerful scheduling enhancement, `matchLabelKeys` and `mismatchLabelKeys, `to improve how pods honor `PodAffinity` and `PodAntiAffinity`, especially during rolling updates and multi-tenant isolation scenarios.

### The Problem with Traditional Affinity

During rolling updates, pods from different revisions (e.g., older and newer ReplicaSets) may co-exist. Without a way to differentiate them, Kubernetes might incorrectly schedule new pods, either failing due to affinity constraints or underutilizing available nodes.

Similarly, in multi-tenant clusters, there was no clean way to enforce pod placement boundaries unless the full label values were known in advance—an assumption that doesn't hold in dynamic environments.

### What’s New: `matchLabelKeys` and `mismatchLabelKeys`

This enhancement introduces two new optional fields to `PodAffinityTerm`:

```yaml
matchLabelKeys:      # Affinity applies to pods with the same key-value as the incoming pod
mismatchLabelKeys:   # Anti-affinity applies to pods with different key-values
```

Instead of hardcoding specific values in the `labelSelector`, these keys are looked up dynamically from the incoming pod and merged into the selector.

#### How It Works

When a pod is created, the API server evaluates `matchLabelKeys` and `mismatchLabelKeys`, fetches values from the pod's labels, and automatically modifies the `labelSelector`.

For example:

```yaml
affinity:
  podAntiAffinity:
    requiredDuringSchedulingIgnoredDuringExecution:
    - mismatchLabelKeys:
        - tenant
      labelSelector:
        matchExpressions:
        - key: tenant
          operator: Exists
      topologyKey: node-pool
```

This is expanded at runtime to:

```yaml
labelSelector:
  matchExpressions:
    - key: tenant
      operator: Exists
    - key: tenant
      operator: NotIn
      values:
        - tenant-a  # value from the pod’s label
```

### Use Cases

**1. Rolling Updates**  
Enable pods to schedule near only those with the same `pod-template-hash`, avoiding clashes between old and new versions.

**2. Multi-Tenancy**  
Ensure tenant pods are scheduled together, but isolated from pods of other tenants—without needing to hardcode tenant names in manifests.

### Feature Status

- **Alpha**: Feature-gated by `MatchLabelKeysInPodAffinity`
- **Beta (Default ON)**: As of Kubernetes v1.33
- **GA**: Pending confirmation; no breaking changes introduced

### Rollout Considerations

- Opt-in feature: existing manifests remain unaffected.
- On downgrade, the field is ignored for new pods but not removed from existing ones.
- Minimal impact on scheduler latency (~negligible at scale).

### Observability

- Metrics: `schedule_attempts_total{result="unschedulable"}` can help monitor anomalies.
- There are no explicit logs/events tied to this feature; introspect `labelSelector` for verification.

### Final Thoughts

The introduction of `matchLabelKeys` and `mismatchLabelKeys` is a subtle yet powerful enhancement to Kubernetes scheduling. It offers a cleaner, more dynamic way to define pod co-location and separation without relying on hardcoded label values. Whether you're managing rolling updates or enforcing tenant-level isolation, this feature gives you more control and flexibility without altering existing behavior—making it a valuable addition for production-grade workloads.

## FAQ

### What are matchLabelKeys and mismatchLabelKeys in Kubernetes PodAffinity?

These are new optional fields in `PodAffinityTerm` that dynamically inject label values from the incoming Pod into the affinity's `labelSelector`. This allows flexible co-location or separation of Pods based on matching or mismatching keys without hardcoding label values.

### What problem do these fields solve in Pod scheduling?

They address challenges during rolling updates and multi-tenant isolation. Without them, affinity rules couldn’t distinguish between different versions of a deployment or tenants unless label values were known in advance. These new fields eliminate that static requirement.

### How does this feature work at runtime?

When a Pod is created, Kubernetes inspects the labels of that Pod and uses the specified `matchLabelKeys` or `mismatchLabelKeys` to construct a `labelSelector`. This selector is then used by the scheduler to find Pods with matching or differing values on the target nodes.

### What are the main use cases for matchLabelKeys and mismatchLabelKeys?

- **Rolling updates:** Ensure new pods co-locate only with pods from the same ReplicaSet revision (e.g., same `pod-template-hash`).
- **Multi-tenancy:** Dynamically group tenant pods together while keeping them isolated from others, without hardcoding tenant IDs.

### What is the feature status of matchLabelKeys and how do I enable it?

As of Kubernetes v1.33, the feature is **beta and enabled by default**, controlled by the `MatchLabelKeysInPodAffinity` feature gate. It is safe to use in production, and existing manifests remain unaffected unless explicitly configured.
