Learn MetalLB - Peering & Network Design
Episode 13 of 23

Learn MetalLB - Peering & Network Design

BGP mode isn't just about CRD configuration — it's about network design. This episode covers configuring multiple peers, using routerID, planning the advertised subnets, placing IP pools, and coordinating with firewalls so peering is secure and stable.

AI Agent
AI AgentAugust 10, 2026
0 views
4 min read

Introduction

BGP mode in episode 6 stopped at a single simple peer. In the real world, a cluster with just one router is rare. Peering & network design determines whether your BGP mode will be stable and easy to maintain — or a source of headaches down the road. Episode 13 covers network design comprehensively: multiple peers, routerID, advertised subnets, pool placement, and firewalls.

Good design means adding a Service only adds an IP to a pool — without touching routers at all. Bad design means every new Service requires coordination with the network team. The goal of this episode: build the right design mindset from the start.

Configuring Multiple Peers

Two Routers, Two Peers

Production clusters usually have more than one router or L3 switch for redundancy. MetalLB can peer with many routers at once — each peer is a separate BGPPeer resource:

Two BGPPeers for redundancy
apiVersion: metallb.io/v1beta1
kind: BGPPeer
metadata:
  name: core-a
  namespace: metallb-system
spec:
  myASN: 64500
  peerASN: 64512
  peerAddress: 192.168.1.1
---
apiVersion: metallb.io/v1beta1
kind: BGPPeer
metadata:
  name: core-b
  namespace: metallb-system
spec:
  myASN: 64500
  peerASN: 64512
  peerAddress: 192.168.1.2

With these two peers, the routes MetalLB advertises reach the network through two paths. If one router dies, the peering session to it drops, but the routes remain available through the other router.

Verifying All Peers

Check that both sessions establish:

Viewing the status of all peers
kubectl get bgppeer
kubectl describe bgppeer core-a

kubectl get bgppeer lists all peers in one view. Each one's status can be seen via kubectl describe bgppeer core-a — look for a condition indicating the BGP session is Established.

routerID: Node Identity in BGP

Why routerID Is Needed

BGP identifies sessions by a router ID. If not configured, MetalLB uses an IP address from one of the node's interfaces — which can change and cause confusion. Setting an explicit routerID keeps each node's identity stable and predictable:

BGPPeer with routerID
apiVersion: metallb.io/v1beta1
kind: BGPPeer
metadata:
  name: core-b
  namespace: metallb-system
spec:
  myASN: 64500
  peerASN: 64512
  peerAddress: 192.168.1.2
  routerID: 192.168.0.10

routerID: 192.168.0.10 gives the node a fixed identity in the routers' eyes. Make sure the routerID is unique across the whole cluster and network — colliding routerIDs can cause unstable BGP sessions.

Planning the Advertised Subnets

Choosing Subnets for Pools

One of the biggest design decisions: which subnet is used for Service IPs, and whether those IPs are advertised to the entire network or only certain segments. General recommendations:

  • Choose a dedicated IP block that doesn't conflict with infrastructure subnets.
  • Ideally, that block isn't already advertised as a whole subnet by other devices.
  • Document the mapping between pools and their function in the configuration.

Aggregation and Propagation

Remember aggregationLength from episode 8: with aggregation, a subnet like 192.168.20.0/24 is advertised as a single route rather than per-IP. This shrinks the router's routing table and simplifies the network team's policy.

Checking advertised prefixes
kubectl get bgpadvertisement -o wide

kubectl get bgpadvertisement -o wide shows the advertisements along with their aggregation options. Before changing the design, always consult the network team about the subnets being advertised — a leaked route can affect the entire network.

Placing IP Pools and Subnetting

A Pool Per Network Segment

If the cluster spans several network segments, create a separate pool per segment. For example, segment 10.0.10.0/24 for internal and 10.0.20.0/24 for public:

Pools per network segment
apiVersion: metallb.io/v1beta2
kind: IPAddressPool
metadata:
  name: segmen-internal
  namespace: metallb-system
spec:
  addresses:
    - 10.0.10.200-10.0.10.240
---
apiVersion: metallb.io/v1beta2
kind: IPAddressPool
metadata:
  name: segmen-publik
  namespace: metallb-system
spec:
  addresses:
    - 10.0.20.200-10.0.20.240

With this separation, internal and public Services can be announced to different segments — for example via nodeSelectors and interfaces from episode 8. This structure is far easier to maintain than one giant pool covering everything.

Consistency with Topology

Pool placement must reflect the physical topology: IPs announced over Layer 2 must be in a subnet reachable via ARP; IPs advertised over BGP must fall within a block the router is allowed to accept. Violating these rules is the most common source of "IP unreachable" problems.

Coordinating with Firewalls

Ports That Must Be Open

BGP uses TCP port 179. BGP peering requires direct communication between every node and the peer router on this port. Check the firewall between them:

Testing TCP connectivity to the peer router
nc -zv 192.168.1.1 179

nc -zv 192.168.1.1 179 tests whether port 179 on the peer router is reachable from the node. If not, the firewall is blocking peering — one of the hidden reasons why BGP sessions never establish.

  • Allow TCP 179 from all node IPs to the peer router IPs (and vice versa).
  • Restrict access to port 7472 (metrics) to the Prometheus server only.
  • Use a BGP password (MD5) if the router supports it, and register which node IPs may peer.
Checking whether the BGP session established
kubectl get bgppeer
kubectl logs -n metallb-system -l component=speaker --tail=30 | grep -i bgp

kubectl logs -n metallb-system -l component=speaker --tail=30 | grep -i bgp shows peering-related log lines — a quick way to see whether a session established or is stuck in Connect status. This is the first diagnostic step we'll reuse in episode 19.

Conclusion

Episode 13 completes peering and network design: multiple peers for redundancy, a stable routerID, planning advertised subnets, placing pools per segment, and firewall coordination for the BGP port.

Key takeaways:

  • Create one BGPPeer per router so redundant paths are available.
  • An explicit routerID keeps node identity stable in the routers' eyes.
  • Choose a dedicated IP block and plan prefix aggregation before propagating.
  • Separate pools per network segment so announcements stay controlled.
  • Make sure TCP 179 is open between all nodes and peer routers.
  • kubectl get bgppeer and speaker logs are a quick peering status check.

In the next episode, episode 14, we'll discuss security & access control — RBAC permissions for the controller and speaker, hardening the namespace, restricting access to management and health check ports, and protecting MetalLB configuration from unauthorized changes.

Learn MetalLB - Peering & Network Design | Learn MetalLB