Network Security Policies
Para essa sessão podemos rever o material do CKA. Somente irei colocar a diferença de conteúdo.
- São as regras de firewall no Kubernetes.
- Implementados pelo CNI, nem todos os Network Plugins suportam.
- Nível de namespace.
- Restringe o ingress e o egress para um grupo de pods baseado em certas condições.
- Network Policies.
Nesse primeiro cenário estamos aplicando uma regra de saída estamos negando tudo, ao menos que passe em uma regra. Como não temos regras, tudo é negado.

Aqui já temos regras de saída.

Podemos criar várias network policies para os mesmo pods. Praticamente um merge.
- Se um pod possui mais de uma NP
- Então teremos a união de todas as NP aplicadas a ele.
- A ordem não importa, o resultado é sempre o mesmo.
Sabendo disso podemos criar um NP para negar tudo em cada namespace e somente ir permitindo aquilo que é necessário.
Vamos rodar dois pods no namespace default e vamos conferir se conseguem se enxergar.
root@cks-master:~# kubectl get pods
No resources found in default namespace.
root@cks-master:~# k run frontend --image=nginx
pod/frontend created
root@cks-master:~# k run backend --image=nginx
pod/backend created
root@cks-master:~# k expose pod frontend --port 80
service/frontend exposed
root@cks-master:~# k expose pod backend --port 80
service/backend exposed
root@cks-master:~# k get pod,svc
NAME READY STATUS RESTARTS AGE
pod/backend 1/1 Running 0 46s
pod/frontend 1/1 Running 0 59s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/backend ClusterIP 10.111.182.74 <none> 80/TCP 20s
service/frontend ClusterIP 10.104.14.250 <none> 80/TCP 27s
service/kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 44h
# executando um curl dentro do frontend para o backend
root@cks-master:~# k exec frontend -- curl backend
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 615 100 615 0 0 73652 0 <!DOCTYPE html>-- --:--:-- 0
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>
<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>
<p><em>Thank you for using nginx.</em></p>
</body>
</html>
--:--:-- --:--:-- --:--:-- 76875
root@cks-master:~# k exec backend -- curl frontend
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 615 100 615 0 0 221k 0 --:--:-- --:--:-- --:--:-- 300k
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>
<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>
<p><em>Thank you for using nginx.</em></p>
</body>
</html>
Podemos observar que existe a comunicação. Vamos criar uma NP default e somente permitir o que é necessário.
Crie um arquivo e aplique no cluster.
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: default-deny
namespace: default
spec:
podSelector: {}
policyTypes:
- Ingress
- Egress
root@cks-master:~# mkdir default
root@cks-master:~# cd default/
root@cks-master:~/default# vi np-default-deny.yaml
root@cks-master:~/default# kubectl apply -f np-default-deny.yaml
networkpolicy.networking.k8s.io/default-deny created
root@cks-master:~/default# k get networkpolicies
NAME POD-SELECTOR AGE
default-deny <none> 48s
root@cks-master:~/default# k describe networkpolicies default-deny
Name: default-deny
Namespace: default
Created on: 2024-08-17 17:33:21 +0000 UTC
Labels: <none>
Annotations: <none>
Spec:
PodSelector: <none> (Allowing the specific traffic to all pods in this namespace)
Allowing ingress traffic:
<none> (Selected pods are isolated for ingress connectivity)
Allowing egress traffic:
<none> (Selected pods are isolated for egress connectivity)
Policy Types: Ingress, Egress
# Se tentar a comunicação novamente vemos que não conseguimos mais a página do nginx.
root@cks-master:~/default# k exec frontend -- curl backend
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- 0:00:14 --:--:--
root@cks-master:~/default#
Vamos permitir o pod frontend saír para o backend.
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: frontend
namespace: default
spec:
podSelector:
matchLabels:
run: frontend # Quando rodando o comando run temos essa label padronizada
policyTypes:
- Egress
egress:
- to:
- podSelector:
matchLabels:
run: backend
Vamos criar e aplicar essa policy.
root@cks-master:~/default# vim np-frontend.yaml
root@cks-master:~/default# kubectl apply -f np-frontend.yaml
networkpolicy.networking.k8s.io/frontend created
root@cks-master:~/default# k exec frontend -- curl backend
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- 0:00:01 --:--:-- 0
Não conseguimos ainda a conexão pois o pod backend está negando tudo, vamos então liberar a entrada dele.
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: backend
namespace: default
spec:
podSelector:
matchLabels:
run: backend # Quando rodando o comando run temos essa label padronizada
policyTypes:
- Ingress
ingress:
- from:
- podSelector:
matchLabels:
run: frontend
Vamos liberar a entrada para os pods do frontend no backend e testar.
root@cks-master:~/default# vim np-backend.yaml
root@cks-master:~/default# kubectl apply -f np-backend.yaml
networkpolicy.networking.k8s.io/backend created
# Ainda não conseguimos
root@cks-master:~/default# k exec frontend -- curl backend
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- 0:00:02 --:--:--
root@cks-master:~/default# k get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
backend 1/1 Running 0 26m 192.168.1.3 cks-worker <none> <none>
frontend 1/1 Running 0 26m 192.168.1.2 cks-worker <none> <none>
# Tentando direto pelo IP conseguimos
root@cks-master:~/default# k exec frontend -- curl 192.168.1.3
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>
<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>
<p><em>Thank you for using nginx.</em></p>
</body>
</html>
100 615 100 615 0 0 399k 0 --:--:-- --:--:-- --:--:-- 600k
O que esta acontecendo é que não conseguimos resolver os nomes pois não tem acesso ao core-dns. Precisamos liberar isso em todos os pods do namespace. Para que isso seja fácil podemos aplicar esta regra em todos os pods de uma única vez. Podemos alterar o nosso default-deny ou criar outro NP. Vamos extender o default-deny e permitir somente o egress para a porta 53.
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: default-deny
namespace: default
spec:
podSelector: {}
policyTypes:
- Ingress
- Egress
egress:
- to:
ports:
- port: 53
protocol: TCP
- port : 53
protocol: UDP
root@cks-master:~/default# vim np-default-deny.yaml
root@cks-master:~/default# k apply -f np-default-deny.yaml
networkpolicy.networking.k8s.io/default-deny configured
# Funcionando
root@cks-master:~/default# k exec frontend -- curl backend
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 615 100 615 0 0 268k 0 --:--:-- --:--:-- --:--:-- 300k
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>
<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>
<p><em>Thank you for using nginx.</em></p>
</body>
</html>
# E só para constar, não permitimos que o backend se comunique com o frontend
# Também não permitimos entrdadas no frontend. Só permitimos uma direção frontend > backend.
root@cks-master:~/default# k exec backend -- curl frontend
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- 0:00:02 --:--:-- 0^C
root@cks-master:~/default# k exec backend -- curl 192.168.1.2
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- 0:00:01 --:--:-- 0^C
root@cks-master:~/default#