Kubernetes: Prevent Cross-Tier Traffic with NetworkPolicy while Preserving DNS Access

Kubernetes NetworkPolicy: Cross-Tier Traffic Control with DNS

Kubernetes NetworkPolicy: Preventing Cross-Tier Traffic with DNS Access

This tutorial demonstrates how to use Kubernetes NetworkPolicies to restrict communication between different tiers of your application while ensuring that services within each tier can still resolve DNS names. We’ll cover common pitfalls and demonstrate corrective actions through practical examples.

Understanding the Problem

Without NetworkPolicies, all pods in a Kubernetes cluster can communicate with each other. This can create security risks, especially in multi-tier applications. We’ll focus on preventing traffic from the Web Tier (frontend) to the Backend Tier (API and Database) and ensuring that the API tier can still resolve DNS names for its services. DNS access is critical for the API tier to function correctly.

Example 1: Initial State – Open Communication

Initially, all tiers can communicate. This is a risky state. We’ll start with a simple setup and then introduce the issues.


apiVersion: v1
kind: Pod
metadata:
  name: web-frontend
  labels:
    app: web-frontend
spec:
  containers:
  - name: frontend
    image: nginx
    ports:
    - containerPort: 80
---
apiVersion: v1
kind: Pod
metadata:
  name: api-backend
  labels:
    app: api-backend
spec:
  containers:
  - name: backend
    image: busybox:latest
    command: ["sleep", "3600"]
    ports:
    - containerPort: 8080
---
apiVersion: v1
kind: Pod
metadata:
  name: db-backend
  labels:
    app: db-backend
spec:
  containers:
  - name: db
    image: busybox:latest
    command: ["sleep", "3600"]
    ports:
    - containerPort: 5432

Verification:

  • `kubectl get pods -l app=web-frontend`
  • `kubectl get pods -l app=api-backend`
  • `kubectl get pods -l app=db-backend`

You should see all three pods running. Currently, the web frontend can directly connect to the api backend on port 8080 and the db backend on port 5432. This is undesirable.

Example 2: Introducing NetworkPolicy – Restricting Web Tier Access

Now, let’s restrict the web frontend from connecting to the backend tiers. This is the core of the tutorial.


apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: restrict-web-tier
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: api-backend
  ingress:
  - ports:
    - port: 8080
      protocol: TCP
      namespaceSelector:
        matchLabels:
          app: web-frontend
  policyTypes:
  - Ingress

Explanation: This NetworkPolicy defines a rule to restrict incoming traffic to pods labeled `app: api-backend` on port 8080. The `namespaceSelector` ensures this applies only within the `default` namespace. Critically, the `policyTypes` are explicitly set to `Ingress`. Without this, the network policy may not function as expected. The `matchLabels` are set to the labels of the API Backend pods.

Verification:

  • `kubectl get networkpolicies -l app=api-backend`
  • `kubectl describe networkpolicy restrict-web-tier`
  • Attempt to connect from the web frontend pod to the api backend pod on port 8080. This should fail.

Example 3: Correcting a DNS Access Issue – Incomplete Policy & Correction

We’ve now restricted traffic, but the API tier still needs to resolve DNS names. If our NetworkPolicy is too restrictive, this will break the API. The key is that NetworkPolicies by default allow egress traffic to the Kubernetes DNS service (10.96.0.10). However, we can explicitly allow DNS resolution.


apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-dns-resolution
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: api-backend
  ingress:
  - ports:
    - port: 53
      protocol: UDP
      namespaceSelector:
        matchLabels:
          app: kube-dns
  policyTypes:
  - Ingress

Explanation: This NetworkPolicy allows UDP traffic to port 53 (DNS) from the API backend pods, specifically targeting the Kubernetes DNS service (10.96.0.10). The `policyTypes` are explicitly set to `Ingress`. We have defined `matchLabels` on the Kubernetes DNS service to target the specific DNS server we want to use.

Verification:

  • `kubectl get networkpolicies -l app=api-backend`
  • `kubectl describe networkpolicy allow-dns-resolution`
  • Exec into the api-backend pod and run `nslookup google.com`. It should resolve successfully.

Common Mistake & Correction: If this NetworkPolicy still doesn’t work, ensure you’ve applied it after the API Backend pods are running. NetworkPolicies are applied to existing pods, not created new ones. Also, ensure the labels are correctly applied to the pods and the NetworkPolicy selectors match these labels.

This tutorial demonstrates a basic scenario of restricting cross-tier traffic with NetworkPolicies while maintaining DNS access. Remember to thoroughly test your NetworkPolicies and understand their impact on your application.

Leave a Reply

Your email address will not be published. Required fields are marked *

We use cookies and similar technologies to enhance your experience on wobizdu.com, analyze site traffic, personalize content, and deliver relevant ads. Some cookies are essential for the site to function, while others help us improve performance and user experience. You may accept all cookies, decline optional ones, or customize your settings. Review our Privacy Policy to learn more.