An Introduction to Working with Network Policies in Kubernetes

josephcardillo

Joseph Cardillo

Posted on September 16, 2024

An Introduction to Working with Network Policies in Kubernetes

As I've started to study for my CKAD certification, I thought it would be helpful to start writing again, as a way to help solidify my understanding of certain concepts. In this article I'll start with Network Policies.

To illustrate this, we'll set up an nginx webserver, apply a network policy to restrict all traffic, modify that policy, and see how each affects traffic to the nginx application.

Note: This article assumes a working kubernetes instance or cluster, a basic understanding of Kubernetes concepts, and the use of kubectl for managing your cluster.

What are Network Policies?

I like to think of Network Policies as a sophisticated mail sorting system in a large office. They determine which departments (pods) can send and receive mail (network traffic), through which mailboxes (ports), and with whom they can correspond (other pods or external services).

Similarly, Network Policies control the flow of network traffic between pods.

By default, all pods in a Kubernetes cluster can communicate with each other freely. Network Policies allow you to restrict this communication, enhancing your cluster's security.

Setting Up Our Example

Let's start by creating a simple nginx webserver deployment:

kubectl create deploy nginx-webserver --image=nginx
Enter fullscreen mode Exit fullscreen mode

To view the objects we've created, run:

kubectl get pods
kubectl get deployments.apps
Enter fullscreen mode Exit fullscreen mode

Now, let's expose our deployment via a NodePort:

kubectl expose deploy nginx-webserver --type=NodePort --port=80
Enter fullscreen mode Exit fullscreen mode

To get the NodePort's IP and port, run the following command:

kubectl get svc
Enter fullscreen mode Exit fullscreen mode

You should see output similar to this:

NAME                   TYPE           CLUSTER-IP       EXTERNAL-IP   PORT(S)          AGE
nginx-webserver        NodePort       10.96.173.63     <none>        80:30092/TCP     2m23s
Enter fullscreen mode Exit fullscreen mode

Now, let's test our nginx server by curling the cluster IP from your control plane node:

curl http://10.96.173.63:80

<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
[...]
Enter fullscreen mode Exit fullscreen mode

You can also access the page publicly at the control plane IP:30092. For example:

http://172.243.237.107:30092/

Nginx Welcome Page

Creating a Network Policy

Next, let's create a Network Policy to block all traffic to pods in this deployment. We'll call it blockall:

---
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: blockall
spec:
  podSelector:
    matchLabels:
      app: nginx-webserver
  policyTypes:
  - Ingress
  - Egress
Enter fullscreen mode Exit fullscreen mode

Save this as blockall.yaml and apply it:

kubectl apply -f blockall.yaml
Enter fullscreen mode Exit fullscreen mode

Testing the Network Policy

To test if our policy is working, curl the nginx-webserver IP again:

curl http://10.96.173.63:80
Enter fullscreen mode Exit fullscreen mode

If you wait long enough, you should see a timeout:

curl: (28) Failed to connect to 10.96.173.63 port 80 after 129428 ms: Connection timed out
Enter fullscreen mode Exit fullscreen mode

This means our Network Policy is working. It's as if we've instructed the mail room to return all correspondence addressed to our nginx server (mailbox) as 'Address Unknown'. No matter what department tries to send a message, it won't reach its destination.

Allowing Specific Traffic

Now, let's modify our policy to allow incoming traffic on port 80:

---
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: blockall
spec:
  podSelector:
    matchLabels:
      app: nginx-webserver
  policyTypes:
  - Ingress
  - Egress
  ingress:
    - ports:
      - protocol: TCP
        port: 80
Enter fullscreen mode Exit fullscreen mode

Update the policy with this command:

kubectl replace -f blockall.yaml
Enter fullscreen mode Exit fullscreen mode

Now when we curl our nginx server, we should see the nginx welcome page again:

curl http://10.96.173.63:80

<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
[...]
Enter fullscreen mode Exit fullscreen mode

Conclusion

Network Policies in Kubernetes are like building a custom firewall around your applications. They give you fine-grained control over who can talk to whom in your cluster, enhancing your security posture.

Creating effective Network Policies requires a good understanding of your application's communication patterns and needs. It's recommended to start with restrictive policies and gradually open up communication as needed, rather than starting wide open and trying to lock things down.

In taking the time to understand Network Policies, you're adding a powerful tool to your Kubernetes security toolkit.

Image credit: Photo by Pedro Forester Da Silva on Unsplash

💖 💪 🙅 🚩
josephcardillo
Joseph Cardillo

Posted on September 16, 2024

Join Our Newsletter. No Spam, Only the good stuff.

Sign up to receive the latest update from our blog.

Related