KubernetesCXXIII · NetworkPolicy TroubleshootingNetworkPolicy troubleshooting
Cross-namespace policy — the multi-tenant network
What you'll learn
- Reason about cross-namespace NetworkPolicies
- Allow traffic between namespaces using namespaceSelector
- Diagnose cross-namespace policy failures
- Identify the production failure modes of cross-namespace policies
Prerequisites
Verified against Kubernetes 1.34.x · kubeadm 1.34.x · kubectl 1.34.x · etcd 3.6.x · CoreDNS 1.11.x · containerd 1.7.x / 2.x · 2026-08-16
A Pod in one tenant’s namespace can open a connection to a Pod
in another’s, and namespaceSelector is what stops it. It
matches namespace labels rather than namespace names, which is
why most cross-namespace rules select on
kubernetes.io/metadata.name, the label the API server sets
on every namespace automatically. The trap is structural: a
namespaceSelector and a podSelector inside one from
element mean both must match, while the same two written as
separate elements mean either will do.
The namespaceSelector
A NetworkPolicy’s spec.ingress[].from and spec.egress[].to
can include a namespaceSelector to match Pods in selected
namespaces.
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: allow-frontend-to-backend
namespace: prod
spec:
podSelector:
matchLabels:
app: billing
ingress:
- from:
- namespaceSelector:
matchLabels:
kubernetes.io/metadata.name: frontend
podSelector:
matchLabels:
app: web
ports:
- protocol: TCP
port: 8080
The policy allows ingress from Pods labeled app: web in the
frontend namespace to Pods labeled app: billing in the
prod namespace.
The namespace labels
The namespace labels are the source of truth. The
namespaceSelector must match the namespace’s labels.
# Substitute your own values before running:
SOURCE_NS=frontend
# Check the namespace's labels
kubectl get namespace "$SOURCE_NS" --show-labels
# Output:
# NAME STATUS LABELS
# frontend Active kubernetes.io/metadata.name=frontend
The namespace label kubernetes.io/metadata.name is
automatically set by Kubernetes to the namespace’s name.
The diagnostic
The canonical diagnostic:
# Substitute your own values before running:
POLICY=allow-frontend-to-backend
POLICY_NS=prod
SOURCE_NS=frontend
SOURCE_POD=web-5f9c7d8b6c-2xk9p
TARGET_IP=192.0.2.24
TARGET_PORT=8080
# 1. Check the NetworkPolicy's namespaceSelector
kubectl get networkpolicy "$POLICY" -n "$POLICY_NS" -o yaml
# 2. Check the source namespace's labels
kubectl get namespace "$SOURCE_NS" --show-labels
# 3. Check the source Pod's labels
kubectl get pods -n "$SOURCE_NS" --show-labels
# 4. Test the connection from a Pod in the source namespace
kubectl exec -it "$SOURCE_POD" -n "$SOURCE_NS" -- curl -v "$TARGET_IP:$TARGET_PORT"
The diagnostic is the policy’s selectors, the namespace’s labels, and the Pod’s labels.
Common failures
- Namespace mismatch. The policy’s namespaceSelector
requires
kubernetes.io/metadata.name=frontendbut the source namespace isfrontend-prod. - Pod labels mismatch. The policy’s podSelector requires
app: webbut the Pods haveapp: webapp. - Policy in wrong namespace. The policy is in the target namespace but should be in the source namespace.
flowchart TD
A[Cross-namespace failure] --> B{Namespace labels match?}
B -->|No| C[Fix the namespace or the selector]
B -->|Yes| D{Pod labels match?}
D -->|No| C
D---|Yes| E{Policy in correct namespace?}
E -->|No| F[Move the policy]
E -->|Yes| G[Unknown]
The remediation
The remediation depends on the cause:
# Substitute your own values before running:
SOURCE_NS=frontend-prod # namespace whose metadata.name label is wrong
CORRECT_NAME=frontend # value the policy's namespaceSelector expects
POLICY=allow-frontend-to-backend
POLICY_NS=frontend # namespace the policy currently lives in
CORRECT_POLICY_NS=prod # namespace the policy belongs in
# Option 1: Fix the namespace label
kubectl label namespace "$SOURCE_NS" kubernetes.io/metadata.name="$CORRECT_NAME"
# Option 2: Fix the policy's selector
kubectl patch networkpolicy "$POLICY" -n "$POLICY_NS" -p '{"spec":{"ingress":[{"from":[{"namespaceSelector":{"matchLabels":{"kubernetes.io/metadata.name":"frontend"}}}]}]}]'
# Option 3: Move the policy to the correct namespace
kubectl get networkpolicy "$POLICY" -n "$POLICY_NS" -o yaml > policy.yaml
kubectl apply -f policy.yaml -n "$CORRECT_POLICY_NS"
kubectl delete networkpolicy "$POLICY" -n "$POLICY_NS"
The remediation is the cross-namespace policy.
The cluster-wide policy
A cluster-wide policy (e.g., for monitoring) can be applied
using a policy in the kube-system namespace with a
namespaceSelector that matches all namespaces.
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: allow-monitoring
namespace: kube-system
spec:
podSelector:
matchLabels:
app: prometheus
egress:
- to:
- namespaceSelector: {}
The policy allows the Prometheus Pods in kube-system to
scrape metrics from any Pod in any namespace.
Production discipline
Cross-namespace policies are the cluster’s network hypothesis. The discipline is to walk the canonical flow extended with the multi-tenant network, identify the failure mode, apply the remediation. The network is the cluster’s connectivity; the remediation is the cross-namespace policy.
- Verify the namespace labels. The label is the source of truth.
- Verify the pod labels. The labels are the source of truth.
- Verify the policy’s namespace. The policy is in the target namespace.
Quiz
Knowledge check · 4 questions
Q1. What is the namespace label that Kubernetes automatically sets to the namespace's name?
Q2. A cross-namespace policy must have the namespaceSelector matching the source namespace's labels.
Q3. An operator reports that the frontend cannot reach the backend. The cross-namespace policy has `namespaceSelector: kubernetes.io/metadata.name=frontend` but the frontend namespace is `frontend-prod`. What is the diagnostic and remediation?
The cluster is a 1.34.x kubeadm install. The frontend namespace is `frontend-prod`. The backend namespace is `prod`. The NetworkPolicy is `allow-frontend-to-backend` in `prod`. The policy's namespaceSelector requires `kubernetes.io/metadata.name=frontend`.
Q4. Name three common causes of a cross-namespace NetworkPolicy failure and the diagnostic command for each.
Passing score: 75%. Answers are checked in this browser.