From e72dbf3dfc8f4ecbb4f0ddd629a1625fd7cbba82 Mon Sep 17 00:00:00 2001
From: Mike Williams <7595658+gaima8@users.noreply.github.com>
Date: Wed, 5 Aug 2020 09:52:40 +0100
Subject: [PATCH] Option for MetalLB to talk BGP (#6383)

* Option for MetalLB to talk BGP

* Check for BGP peers when metallb_protocol is bgp

* README clarification

* Commented values as documentation only in the sample inventory

* layer 2 or BGP, not both
---
 inventory/sample/group_vars/k8s-cluster/addons.yml     |  8 ++++++++
 roles/kubernetes-apps/metallb/README.md                | 10 ++++++----
 roles/kubernetes-apps/metallb/tasks/main.yml           |  6 ++++++
 .../metallb/templates/metallb-config.yml.j2            |  8 ++++++++
 4 files changed, 28 insertions(+), 4 deletions(-)

diff --git a/inventory/sample/group_vars/k8s-cluster/addons.yml b/inventory/sample/group_vars/k8s-cluster/addons.yml
index 26cdbad37..e085ac897 100644
--- a/inventory/sample/group_vars/k8s-cluster/addons.yml
+++ b/inventory/sample/group_vars/k8s-cluster/addons.yml
@@ -135,3 +135,11 @@ metallb_enabled: false
 #       - "10.5.1.50-10.5.1.99"
 #     protocol: "layer2"
 #     auto_assign: false
+# metallb_protocol: "bgp"
+# metallb_peers:
+#   - peer_address: 192.0.2.1
+#     peer_asn: 64512
+#     my_asn: 4200000000
+#   - peer_address: 192.0.2.2
+#     peer_asn: 64513
+#     my_asn: 4200000000
diff --git a/roles/kubernetes-apps/metallb/README.md b/roles/kubernetes-apps/metallb/README.md
index d8d980f30..71f1b5bd9 100644
--- a/roles/kubernetes-apps/metallb/README.md
+++ b/roles/kubernetes-apps/metallb/README.md
@@ -3,13 +3,15 @@
 MetalLB hooks into your Kubernetes cluster, and provides a network load-balancer implementation.
 In short, it allows you to create Kubernetes services of type "LoadBalancer" in clusters that
 don't run on a cloud provider, and thus cannot simply hook into paid products to provide load-balancers.
-This addon aims to automate [this](https://metallb.universe.tf/concepts/layer2/).
-It deploys MetalLB into Kubernetes and sets up a layer 2 load-balancer.
+This addon aims to automate [MetalLB in layer 2 mode](https://metallb.universe.tf/concepts/layer2/)
+or [MetalLB in BGP mode][https://metallb.universe.tf/concepts/bgp/].
+It deploys MetalLB into Kubernetes and sets up a layer 2 or BGP load-balancer.
 
 ## Install
 
 In the default, MetalLB is not deployed into your Kubernetes cluster.
-You can override the defaults by copying the contents of this file to somewhere in inventory/mycluster/group_vars
-such as inventory/mycluster/groups_vars/k8s-cluster/addons.yml and updating metallb_enabled option to `true`.
+You can override the defaults by copying the contents of roles/kubernetes-apps/metallb/defaults/main.yml
+to somewhere in inventory/mycluster/group_vars such as inventory/mycluster/groups_vars/k8s-cluster/addons.yml
+and updating metallb_enabled option to `true`.
 In addition you need to update metallb_ip_range option on the addons.yml at least for suiting your network
 environment, because MetalLB allocates external IP addresses from this metallb_ip_range option.
diff --git a/roles/kubernetes-apps/metallb/tasks/main.yml b/roles/kubernetes-apps/metallb/tasks/main.yml
index c7bbc1fc5..5d3c58d6e 100644
--- a/roles/kubernetes-apps/metallb/tasks/main.yml
+++ b/roles/kubernetes-apps/metallb/tasks/main.yml
@@ -11,6 +11,12 @@
   when:
     - metallb_ip_range is not defined or not metallb_ip_range
 
+- name: Kubernetes Apps | Check BGP peers for MetalLB
+  fail:
+    msg: "metallb_peers is mandatory when metallb_protocol is bgp"
+  when:
+    - metallb_protocol == 'bgp' and metallb_peers is not defined
+
 - name: Kubernetes Apps | Check AppArmor status
   command: which apparmor_parser
   register: apparmor_status
diff --git a/roles/kubernetes-apps/metallb/templates/metallb-config.yml.j2 b/roles/kubernetes-apps/metallb/templates/metallb-config.yml.j2
index 73b29d72d..1a4d20a73 100644
--- a/roles/kubernetes-apps/metallb/templates/metallb-config.yml.j2
+++ b/roles/kubernetes-apps/metallb/templates/metallb-config.yml.j2
@@ -6,6 +6,14 @@ metadata:
   name: config
 data:
   config: |
+{% if metallb_protocol == 'bgp' %}
+    peers:
+{% for peer in metallb_peers %}
+    - peer-address: {{ peer.peer_address }}
+      peer-asn: {{ peer.peer_asn }}
+      my-asn: {{ peer.my_asn }}
+{% endfor %}
+{% endif %}
     address-pools:
     - name: loadbalanced
       protocol: {{ metallb_protocol }}
-- 
GitLab