From d372734bfd2ec88df000f9cd943137057a823088 Mon Sep 17 00:00:00 2001
From: sarthurdev <965089+sarthurdev@users.noreply.github.com>
Date: Fri, 18 Jun 2021 20:41:39 +0200
Subject: mdns: vrrp: T3635: Add ability to use mDNS repeater with VRRP
---
interface-definitions/service_mdns-repeater.xml.in | 6 ++++
src/conf_mode/service_mdns-repeater.py | 38 ++++++++++++++++++++++
src/system/keepalived-fifo.py | 8 +++++
3 files changed, 52 insertions(+)
diff --git a/interface-definitions/service_mdns-repeater.xml.in b/interface-definitions/service_mdns-repeater.xml.in
index 33ef9a434..d02dac8a6 100644
--- a/interface-definitions/service_mdns-repeater.xml.in
+++ b/interface-definitions/service_mdns-repeater.xml.in
@@ -23,6 +23,12 @@
+
+
+ Disables mDNS repeater on VRRP interfaces not in MASTER state
+
+
+
diff --git a/src/conf_mode/service_mdns-repeater.py b/src/conf_mode/service_mdns-repeater.py
index 729518c96..c920920ed 100755
--- a/src/conf_mode/service_mdns-repeater.py
+++ b/src/conf_mode/service_mdns-repeater.py
@@ -16,10 +16,12 @@
import os
+from json import loads
from sys import exit
from netifaces import ifaddresses, interfaces, AF_INET
from vyos.config import Config
+from vyos.ifconfig.vrrp import VRRP
from vyos.template import render
from vyos.util import call
from vyos import ConfigError
@@ -27,6 +29,7 @@ from vyos import airbag
airbag.enable()
config_file = r'/etc/default/mdns-repeater'
+vrrp_running_file = '/run/mdns_vrrp_active'
def get_config(config=None):
if config:
@@ -35,6 +38,9 @@ def get_config(config=None):
conf = Config()
base = ['service', 'mdns', 'repeater']
mdns = conf.get_config_dict(base, key_mangling=('-', '_'), get_first_key=True)
+
+ if mdns:
+ mdns['vrrp_exists'] = conf.exists('high-availability vrrp')
return mdns
def verify(mdns):
@@ -60,6 +66,18 @@ def verify(mdns):
return None
+# Get VRRP states from interfaces, returns only interfaces where state is MASTER
+def get_vrrp_master(interfaces):
+ json_data = loads(VRRP.collect('json'))
+ for group in json_data:
+ if 'data' in group:
+ if 'ifp_ifname' in group['data']:
+ iface = group['data']['ifp_ifname']
+ state = group['data']['state'] # 2 = Master
+ if iface in interfaces and state != 2:
+ interfaces.remove(iface)
+ return interfaces
+
def generate(mdns):
if not mdns:
return None
@@ -68,6 +86,12 @@ def generate(mdns):
print('Warning: mDNS repeater will be deactivated because it is disabled')
return None
+ if mdns['vrrp_exists'] and 'vrrp_disable' in mdns:
+ mdns['interface'] = get_vrrp_master(mdns['interface'])
+
+ if len(mdns['interface']) < 2:
+ return None
+
render(config_file, 'mdns-repeater/mdns-repeater.tmpl', mdns)
return None
@@ -76,7 +100,21 @@ def apply(mdns):
call('systemctl stop mdns-repeater.service')
if os.path.exists(config_file):
os.unlink(config_file)
+
+ if os.path.exists(vrrp_running_file):
+ os.unlink(vrrp_running_file)
else:
+ if 'vrrp_disable' not in mdns and os.path.exists(vrrp_running_file):
+ os.unlink(vrrp_running_file)
+
+ if mdns['vrrp_exists'] and 'vrrp_disable' in mdns:
+ if not os.path.exists(vrrp_running_file):
+ os.mknod(vrrp_running_file) # vrrp script looks for this file to update mdns repeater
+
+ if len(mdns['interface']) < 2:
+ call('systemctl stop mdns-repeater.service')
+ return None
+
call('systemctl restart mdns-repeater.service')
return None
diff --git a/src/system/keepalived-fifo.py b/src/system/keepalived-fifo.py
index 7e2076820..3b4330e9b 100755
--- a/src/system/keepalived-fifo.py
+++ b/src/system/keepalived-fifo.py
@@ -37,6 +37,8 @@ logs_handler_syslog.setFormatter(logs_format)
logger.addHandler(logs_handler_syslog)
logger.setLevel(logging.DEBUG)
+mdns_running_file = '/run/mdns_vrrp_active'
+mdns_update_command = 'sudo /usr/libexec/vyos/conf_mode/service_mdns-repeater.py'
# class for all operations
class KeepalivedFifo:
@@ -121,6 +123,9 @@ class KeepalivedFifo:
logger.info("{} {} changed state to {}".format(n_type, n_name, n_state))
# check and run commands for VRRP instances
if n_type == 'INSTANCE':
+ if os.path.exists(mdns_running_file):
+ cmd(mdns_update_command)
+
if n_name in self.vrrp_config['vrrp_groups'] and n_state in self.vrrp_config['vrrp_groups'][n_name]:
n_script = self.vrrp_config['vrrp_groups'][n_name].get(n_state)
if n_script:
@@ -128,6 +133,9 @@ class KeepalivedFifo:
# check and run commands for VRRP sync groups
# currently, this is not available in VyOS CLI
if n_type == 'GROUP':
+ if os.path.exists(mdns_running_file):
+ cmd(mdns_update_command)
+
if n_name in self.vrrp_config['sync_groups'] and n_state in self.vrrp_config['sync_groups'][n_name]:
n_script = self.vrrp_config['sync_groups'][n_name].get(n_state)
if n_script:
--
cgit v1.2.3