Como restringir acesso a um LoadBalancer de serviço pelo IP de origem
Para restringir o acesso a aplicações expostas por Load Balancers de serviço em um cluster Kubernetes de workload, com base no IP de origem da requisição, foram realizados testes utilizando um echoserver (disponível no DockerHub da Cilium), um Service do tipo LoadBalancer configurado para testes, e uma especificação do OpenStack Cloud Controller Manager para a implementação da restrição.
A funcionalidade loadBalancerSourceRanges
permite especificar uma lista de CIDRs autorizados, limitando quais IPs podem acessar o Service do tipo Load Balancer.
Com essa funcionalidade conseguimos definir quais os CIDRs (ranges de IPs) que poderão enviar requisições para o IP deste Load Balancer. Se um IP, que não se encaixa em nenhum CIDR da lista, tentar enviar uma requisição ao IP do LoadBalancer, receberá timeout, pois seu acesso a esse recurso não está permitido.
Recursos necessários
- Namespace e Deployment:
apiVersion: v1
kind: Namespace
metadata:
name: echoserver
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: echoserver
namespace: echoserver
labels:
app: echoserver
spec:
replicas: 1
selector:
matchLabels:
app: echoserver
template:
metadata:
labels:
app: echoserver
spec:
containers:
- name: echoserver
image: cilium/echoserver
ports:
- containerPort: 80
- Service - Tipo LoadBalancer:
apiVersion: v1
kind: Service
metadata:
labels:
app: echoserver
name: echoserver
namespace: echoserver
spec:
ports:
- port: 80
protocol: TCP
targetPort: 80
selector:
app: echoserver
type: LoadBalancer
loadBalancerSourceRanges:
- IP
Passo a passo:
-
Crie um cluster pelo portal da Magalu Cloud ou CLI
-
Faça download do kubeconfig do cluster e se conecte via kubectl
-
Faça deploy do Namespace e do Deployment
-
Identifique seu IP público através do seguinte comando (Windows ou Linux):
curl ip.me
-
Na declaração do Service do tipo LoadBalancer, em spec → loadBalancerSourceRanges é onde são definidos os CIDRs (ranges de IPs) que serão permitidos a acessar. Para cada range deve colocar o caracter “-” antes, para definir como mais um item de uma lista segundo a declaração do Yaml. A especificação “loadBalancerSourceRanges“ é uma funcionalidade nativa da api do Kubernetes, ou seja, está inclusa por padrão na ferramenta, porém é opcional do Cloud Provider se fará uso dela ou não. No caso o OpenStack Cloud Controler Manager, que é o Cloud Provider, faz uso. Nesse exemplo usaremos o IP que obtemos com o passo acima (passo 4). Exemplo de como ficaria:
apiVersion: v1
kind: Service
metadata:
labels:
app: echoserver
name: echoserver
namespace: echoserver
spec:
ports:
- port: 80
protocol: TCP
targetPort: 80
selector:
app: echoserver
type: LoadBalancer
loadBalancerSourceRanges:
- 163.116.224.120/32 -
Fazer deploy do Service do tipo LoadBalancer
-
Obter o IP externo do LoadBalancer, através do comando
kubectl get service echoserver -n echoserver
onde o Ip externo será exibido no campo EXTERNAL-IP -
Acessar o IP externo gerado pelo LoadBalancer por um IP que está incluso em um CIDR permitido na lista, através do comando
curl <enderecoIpExterno>
O retorno do comando será semelhante a este:
Hostname: echoserver-54f69dcbb4-9v455
Pod Information:
-no pod information available-
Server values:
server_version-nginx: 1.13.3 - lua: 10008
Request Information:
client_address=::ffff:192.168.1.127
method=GET
real path=/
query=
request_version=1.1
request_scheme=http
request_uri=http://213.163.247.41:80/
Request Headers:
accept=*/*
host=213.163.247.41
user-agent-curl/7.81.0
x-forwarded-for-177.130.233.12
Request Body:
-no body in request-
Conclusão
Fazendo uso da funcionalidade nativa do Kubernetes chamada “loadBalancerSourceRanges”, é possível restringir o acesso ao LoadBalancer de serviço se baseando no IP de origem da requisição.
- Referências
Documentação do OpenStack Cloud Controller Manager sobre a opção loadBalancerSourceRanges: https://github.com/kubernetes/cloud-provider-openstack/blob/master/docs/openstack-cloud-controller-manager/expose-applications-using-loadbalancer-type-service.md