LoadBalancer met MetalLB

De cloud-providers geven de mogelijkheid om een service van het type ‘LoadBalancer’ aan te maken die op de achtergrond de provider’s functies gebruikt. In het geval van een zogenaamde ‘bare metal’ installatie (zoals mijn Kubernetes Cluster op RPi) is deze functie niet aanwezig en zal je zelf dit moeten installeren. MetalLB geeft deze mogelijkheid en biedt meer opties dan alleen http of https.

Installatie van de MetalLB kan op verschillende manieren:

Met behulp van een manifest file

$ kubectl apply -f https://raw.githubusercontent.com/metallb/metallb/v0.13.7/config/manifests/metallb-native.yaml

De namespace is ‘metallb-system’ en daarin wordt de controller-deployment gemaakt. Hierin bevinden zich een aantal workloads:

  • controller-pod die de ip adressen aan de services bindt
  • speaker-daemonset die de gewenste protocollen verzorgt
  • de bijbehorende service-accounts en rbac-rollen

Er wordt door de installatie geen configuratie bestand aangemaakt. Dit wordt later gedaan.

Met behulp van Helm

MetalLB kan geïnstalleerd worden met helm:

$ helm repo add metallb https://metallb.github.io/metallb
$ helm install metallb metallb/metallb

Eventueel met aangepaste values :

$ helm install metallb metallb/metallb -f values.yaml

Configuratie

Als eerste worden de IP-adressen (of IP-adres-range) bepaald en in een IPAddressPool manifest yaml-file geplaatst, bijvoorbeeld:

apiVersion: metallb.io/v1beta1 
kind: IPAddressPool 
metadata:
  name: first-pool 
  namespace: metallb-system 
spec: 
  addresses: 
  - 192.168.10.0/24 
  - 192.168.9.1-192.168.9.5 
  - fc00:f853:0ccd:e799::/124

Zoals te zien, kunnen individuele adressen of een range van adressen ingesteld worden, zowel voor IPv4 als IPv6.

Vervolgens wordt een Layer 2 Advertisement manifest gebruikt om de IP Address Pool te koppelen:

apiVersion: metallb.io/v1beta1 
kind: L2Advertisement 
metadata: 
  name: example 
  namespace: metallb-system 
spec: 
  ipAddressPools: 
  - first-pool

Indien er geen ipAddressPools wordt aangegeven in de L2Advertisement, worden alle IPAddressPools gebruikt die ingesteld zijn.

Stel er zijn twee ipAddressPools aanwezig, een /24 range:

apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: big-pool
  namespace: metallb-system
spec:
  addresses:
  - 192.168.10.0/24

en een minder grote pool, een /30-range:

apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: small-pool
  namespace: metallb-system
spec:
  addresses:
  - 172.16.12.64/30

Met een L2Advertisement voor beide pools, zou er willekeurig een adres ‘allocated’ worden aan de service. Om dit te voorkomen kan een optie meegnomen worden in de ipAddressPool om deze niet automatisch mee te laten doen met behulp van autoAssign op false:

apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
name: small-pool
namespace: metallb-system
spec:
addresses:
- 172.16.12.64/30
  autoAssign: false

Specifiek adres uit een pool toewijzen

Via annotations in de service, kan een IP adres uit een specifieke ipPool toegewezen worden aan de LoadBalancer. Bijvoorbeeld voor bovenstaande ‘small-pool’ :

apiVersion: v1 
kind: Service 
metadata: 
  name: my-lb-service 
  annotations: metallb.universe.tf/address-pool: small-pool
spec:
...

Apply’en van de manifests zal de MetalLB-controller actief maken en gereed voor gebruik. Zodra een service aangemaakt wordt als type: LoadBalancer zal MetalLB een (extern) IP adres uit de ipPool toewijzen aan de service.

Overige en meer gedetailleerde configuratie-informatie is te vinden op de site van MetalLB.