diff options
Diffstat (limited to 'src')
-rwxr-xr-x | src/conf_mode/firewall.py | 72 | ||||
-rwxr-xr-x | src/conf_mode/interfaces_openvpn.py | 28 | ||||
-rwxr-xr-x | src/conf_mode/service_monitoring_prometheus.py | 63 | ||||
-rwxr-xr-x | src/conf_mode/service_ssh.py | 57 | ||||
-rw-r--r-- | src/etc/skel/.bashrc | 3 | ||||
-rw-r--r-- | src/etc/udev/rules.d/90-vyos-serial.rules | 2 | ||||
-rw-r--r--[-rwxr-xr-x] | src/migration-scripts/firewall/16-to-17 | 0 | ||||
-rwxr-xr-x | src/migration-scripts/firewall/17-to-18 | 41 | ||||
-rw-r--r-- | src/op_mode/tech_support.py | 19 | ||||
-rw-r--r-- | src/op_mode/zone.py | 11 | ||||
-rwxr-xr-x | src/services/vyos-configd | 16 | ||||
-rwxr-xr-x | src/services/vyos-domain-resolver (renamed from src/helpers/vyos-domain-resolver.py) | 14 | ||||
-rw-r--r-- | src/systemd/vyos-domain-resolver.service | 4 |
13 files changed, 267 insertions, 63 deletions
diff --git a/src/conf_mode/firewall.py b/src/conf_mode/firewall.py index ffbd915a2..768bb127d 100755 --- a/src/conf_mode/firewall.py +++ b/src/conf_mode/firewall.py @@ -18,7 +18,6 @@ import os import re from sys import exit - from vyos.base import Warning from vyos.config import Config from vyos.configdict import is_node_changed @@ -34,6 +33,8 @@ from vyos.utils.dict import dict_search_recursive from vyos.utils.process import call from vyos.utils.process import cmd from vyos.utils.process import rc_cmd +from vyos.utils.network import get_vrf_members +from vyos.utils.network import get_interface_vrf from vyos import ConfigError from vyos import airbag from pathlib import Path @@ -43,7 +44,6 @@ airbag.enable() nftables_conf = '/run/nftables.conf' domain_resolver_usage = '/run/use-vyos-domain-resolver-firewall' -domain_resolver_usage_nat = '/run/use-vyos-domain-resolver-nat' sysctl_file = r'/run/sysctl/10-vyos-firewall.conf' @@ -134,6 +134,27 @@ def get_config(config=None): fqdn_config_parse(firewall, 'firewall') + if not os.path.exists(nftables_conf): + firewall['first_install'] = True + + if 'zone' in firewall: + for local_zone, local_zone_conf in firewall['zone'].items(): + if 'local_zone' not in local_zone_conf: + # Get physical interfaces assigned to the zone if vrf is used: + if 'vrf' in local_zone_conf['member']: + local_zone_conf['vrf_interfaces'] = {} + for vrf_name in local_zone_conf['member']['vrf']: + local_zone_conf['vrf_interfaces'][vrf_name] = ','.join(get_vrf_members(vrf_name)) + continue + + local_zone_conf['from_local'] = {} + + for zone, zone_conf in firewall['zone'].items(): + if zone == local_zone or 'from' not in zone_conf: + continue + if local_zone in zone_conf['from']: + local_zone_conf['from_local'][zone] = zone_conf['from'][local_zone] + set_dependents('conntrack', conf) return firewall @@ -442,28 +463,45 @@ def verify(firewall): local_zone = False zone_interfaces = [] + zone_vrf = [] if 'zone' in firewall: for zone, zone_conf in firewall['zone'].items(): - if 'local_zone' not in zone_conf and 'interface' not in zone_conf: + if 'local_zone' not in zone_conf and 'member' not in zone_conf: raise ConfigError(f'Zone "{zone}" has no interfaces and is not the local zone') if 'local_zone' in zone_conf: if local_zone: raise ConfigError('There cannot be multiple local zones') - if 'interface' in zone_conf: + if 'member' in zone_conf: raise ConfigError('Local zone cannot have interfaces assigned') if 'intra_zone_filtering' in zone_conf: raise ConfigError('Local zone cannot use intra-zone-filtering') local_zone = True - if 'interface' in zone_conf: - found_duplicates = [intf for intf in zone_conf['interface'] if intf in zone_interfaces] + if 'member' in zone_conf: + if 'interface' in zone_conf['member']: + for iface in zone_conf['member']['interface']: + + if iface in zone_interfaces: + raise ConfigError(f'Interfaces cannot be assigned to multiple zones') - if found_duplicates: - raise ConfigError(f'Interfaces cannot be assigned to multiple zones') + iface_vrf = get_interface_vrf(iface) + if iface_vrf != 'default': + Warning(f"Interface {iface} assigned to zone {zone} is in VRF {iface_vrf}. This might not work as expected.") + zone_interfaces.append(iface) - zone_interfaces += zone_conf['interface'] + if 'vrf' in zone_conf['member']: + for vrf in zone_conf['member']['vrf']: + if vrf in zone_vrf: + raise ConfigError(f'VRF cannot be assigned to multiple zones') + zone_vrf.append(vrf) + + if 'vrf_interfaces' in zone_conf: + for vrf_name, vrf_interfaces in zone_conf['vrf_interfaces'].items(): + if not vrf_interfaces: + raise ConfigError( + f'VRF "{vrf_name}" cannot be a member of any zone. It does not contain any interfaces.') if 'intra_zone_filtering' in zone_conf: intra_zone = zone_conf['intra_zone_filtering'] @@ -499,22 +537,6 @@ def verify(firewall): return None def generate(firewall): - if not os.path.exists(nftables_conf): - firewall['first_install'] = True - - if 'zone' in firewall: - for local_zone, local_zone_conf in firewall['zone'].items(): - if 'local_zone' not in local_zone_conf: - continue - - local_zone_conf['from_local'] = {} - - for zone, zone_conf in firewall['zone'].items(): - if zone == local_zone or 'from' not in zone_conf: - continue - if local_zone in zone_conf['from']: - local_zone_conf['from_local'][zone] = zone_conf['from'][local_zone] - render(nftables_conf, 'firewall/nftables.j2', firewall) render(sysctl_file, 'firewall/sysctl-firewall.conf.j2', firewall) return None diff --git a/src/conf_mode/interfaces_openvpn.py b/src/conf_mode/interfaces_openvpn.py index 8c1213e2b..a9b4e570d 100755 --- a/src/conf_mode/interfaces_openvpn.py +++ b/src/conf_mode/interfaces_openvpn.py @@ -32,6 +32,7 @@ from vyos.base import DeprecationWarning from vyos.config import Config from vyos.configdict import get_interface_dict from vyos.configdict import is_node_changed +from vyos.configdiff import get_config_diff from vyos.configverify import verify_vrf from vyos.configverify import verify_bridge_delete from vyos.configverify import verify_mirror_redirect @@ -94,6 +95,23 @@ def get_config(config=None): if 'deleted' in openvpn: return openvpn + if not is_node_changed(conf, base) and dict_search_args(openvpn, 'tls'): + diff = get_config_diff(conf) + if diff.get_child_nodes_diff(['pki'], recursive=True).get('add') == ['ca', 'certificate']: + crl_path = os.path.join(cfg_dir, f'{ifname}_crl.pem') + if os.path.exists(crl_path): + # do not restart service when changed only CRL and crl file already exist + openvpn.update({'no_restart_crl': True}) + for rec in diff.get_child_nodes_diff(['pki', 'ca'], recursive=True).get('add'): + if diff.get_child_nodes_diff(['pki', 'ca', rec], recursive=True).get('add') != ['crl']: + openvpn.update({'no_restart_crl': False}) + break + if openvpn.get('no_restart_crl'): + for rec in diff.get_child_nodes_diff(['pki', 'certificate'], recursive=True).get('add'): + if diff.get_child_nodes_diff(['pki', 'certificate', rec], recursive=True).get('add') != ['revoke']: + openvpn.update({'no_restart_crl': False}) + break + if is_node_changed(conf, base + [ifname, 'openvpn-option']): openvpn.update({'restart_required': {}}) if is_node_changed(conf, base + [ifname, 'enable-dco']): @@ -786,10 +804,12 @@ def apply(openvpn): # No matching OpenVPN process running - maybe it got killed or none # existed - nevertheless, spawn new OpenVPN process - action = 'reload-or-restart' - if 'restart_required' in openvpn: - action = 'restart' - call(f'systemctl {action} openvpn@{interface}.service') + + if not openvpn.get('no_restart_crl'): + action = 'reload-or-restart' + if 'restart_required' in openvpn: + action = 'restart' + call(f'systemctl {action} openvpn@{interface}.service') o = VTunIf(**openvpn) o.update(openvpn) diff --git a/src/conf_mode/service_monitoring_prometheus.py b/src/conf_mode/service_monitoring_prometheus.py index e0a9fc4ef..9a07d8593 100755 --- a/src/conf_mode/service_monitoring_prometheus.py +++ b/src/conf_mode/service_monitoring_prometheus.py @@ -26,15 +26,18 @@ from vyos.utils.process import call from vyos import ConfigError from vyos import airbag - airbag.enable() node_exporter_service_file = '/etc/systemd/system/node_exporter.service' node_exporter_systemd_service = 'node_exporter.service' +node_exporter_collector_path = '/run/node_exporter/collector' frr_exporter_service_file = '/etc/systemd/system/frr_exporter.service' frr_exporter_systemd_service = 'frr_exporter.service' +blackbox_exporter_service_file = '/etc/systemd/system/blackbox_exporter.service' +blackbox_exporter_systemd_service = 'blackbox_exporter.service' + def get_config(config=None): if config: @@ -57,6 +60,12 @@ def get_config(config=None): if tmp: monitoring.update({'frr_exporter_restart_required': {}}) + tmp = False + for node in ['vrf', 'config-file']: + tmp = tmp or is_node_changed(conf, base + ['blackbox-exporter', node]) + if tmp: + monitoring.update({'blackbox_exporter_restart_required': {}}) + return monitoring @@ -70,6 +79,22 @@ def verify(monitoring): if 'frr_exporter' in monitoring: verify_vrf(monitoring['frr_exporter']) + if 'blackbox_exporter' in monitoring: + verify_vrf(monitoring['blackbox_exporter']) + + if ( + 'modules' in monitoring['blackbox_exporter'] + and 'dns' in monitoring['blackbox_exporter']['modules'] + and 'name' in monitoring['blackbox_exporter']['modules']['dns'] + ): + for mod_name, mod_config in monitoring['blackbox_exporter']['modules'][ + 'dns' + ]['name'].items(): + if 'query_name' not in mod_config: + raise ConfigError( + f'query name not specified in dns module {mod_name}' + ) + return None @@ -84,6 +109,11 @@ def generate(monitoring): if os.path.isfile(frr_exporter_service_file): os.unlink(frr_exporter_service_file) + if not monitoring or 'blackbox_exporter' not in monitoring: + # Delete systemd files + if os.path.isfile(blackbox_exporter_service_file): + os.unlink(blackbox_exporter_service_file) + if not monitoring: return None @@ -94,6 +124,13 @@ def generate(monitoring): 'prometheus/node_exporter.service.j2', monitoring['node_exporter'], ) + if ( + 'collectors' in monitoring['node_exporter'] + and 'textfile' in monitoring['node_exporter']['collectors'] + ): + # Create textcollector folder + if not os.path.isdir(node_exporter_collector_path): + os.makedirs(node_exporter_collector_path) if 'frr_exporter' in monitoring: # Render frr_exporter service_file @@ -103,6 +140,20 @@ def generate(monitoring): monitoring['frr_exporter'], ) + if 'blackbox_exporter' in monitoring: + # Render blackbox_exporter service_file + render( + blackbox_exporter_service_file, + 'prometheus/blackbox_exporter.service.j2', + monitoring['blackbox_exporter'], + ) + # Render blackbox_exporter config file + render( + '/run/blackbox_exporter/config.yml', + 'prometheus/blackbox_exporter.yml.j2', + monitoring['blackbox_exporter'], + ) + return None @@ -113,6 +164,8 @@ def apply(monitoring): call(f'systemctl stop {node_exporter_systemd_service}') if not monitoring or 'frr_exporter' not in monitoring: call(f'systemctl stop {frr_exporter_systemd_service}') + if not monitoring or 'blackbox_exporter' not in monitoring: + call(f'systemctl stop {blackbox_exporter_systemd_service}') if not monitoring: return @@ -133,6 +186,14 @@ def apply(monitoring): call(f'systemctl {systemd_action} {frr_exporter_systemd_service}') + if 'blackbox_exporter' in monitoring: + # we need to restart the service if e.g. the VRF name changed + systemd_action = 'reload-or-restart' + if 'blackbox_exporter_restart_required' in monitoring: + systemd_action = 'restart' + + call(f'systemctl {systemd_action} {blackbox_exporter_systemd_service}') + if __name__ == '__main__': try: diff --git a/src/conf_mode/service_ssh.py b/src/conf_mode/service_ssh.py index 9abdd33dc..759f87bb2 100755 --- a/src/conf_mode/service_ssh.py +++ b/src/conf_mode/service_ssh.py @@ -23,10 +23,16 @@ from syslog import LOG_INFO from vyos.config import Config from vyos.configdict import is_node_changed from vyos.configverify import verify_vrf +from vyos.configverify import verify_pki_ca_certificate from vyos.utils.process import call from vyos.template import render from vyos import ConfigError from vyos import airbag +from vyos.pki import find_chain +from vyos.pki import encode_certificate +from vyos.pki import load_certificate +from vyos.utils.file import write_file + airbag.enable() config_file = r'/run/sshd/sshd_config' @@ -38,6 +44,9 @@ key_rsa = '/etc/ssh/ssh_host_rsa_key' key_dsa = '/etc/ssh/ssh_host_dsa_key' key_ed25519 = '/etc/ssh/ssh_host_ed25519_key' +trusted_user_ca_key = '/etc/ssh/trusted_user_ca_key' + + def get_config(config=None): if config: conf = config @@ -47,10 +56,13 @@ def get_config(config=None): if not conf.exists(base): return None - ssh = conf.get_config_dict(base, key_mangling=('-', '_'), get_first_key=True) + ssh = conf.get_config_dict( + base, key_mangling=('-', '_'), get_first_key=True, with_pki=True + ) tmp = is_node_changed(conf, base + ['vrf']) - if tmp: ssh.update({'restart_required': {}}) + if tmp: + ssh.update({'restart_required': {}}) # We have gathered the dict representation of the CLI, but there are default # options which we need to update into the dictionary retrived. @@ -62,20 +74,32 @@ def get_config(config=None): # Ignore default XML values if config doesn't exists # Delete key from dict if not conf.exists(base + ['dynamic-protection']): - del ssh['dynamic_protection'] + del ssh['dynamic_protection'] return ssh + def verify(ssh): if not ssh: return None if 'rekey' in ssh and 'data' not in ssh['rekey']: - raise ConfigError(f'Rekey data is required!') + raise ConfigError('Rekey data is required!') + + if 'trusted_user_ca_key' in ssh: + if 'ca_certificate' not in ssh['trusted_user_ca_key']: + raise ConfigError('CA certificate is required for TrustedUserCAKey') + + ca_key_name = ssh['trusted_user_ca_key']['ca_certificate'] + verify_pki_ca_certificate(ssh, ca_key_name) + pki_ca_cert = ssh['pki']['ca'][ca_key_name] + if 'certificate' not in pki_ca_cert or not pki_ca_cert['certificate']: + raise ConfigError(f"CA certificate '{ca_key_name}' is not valid or missing") verify_vrf(ssh) return None + def generate(ssh): if not ssh: if os.path.isfile(config_file): @@ -95,6 +119,24 @@ def generate(ssh): syslog(LOG_INFO, 'SSH ed25519 host key not found, generating new key!') call(f'ssh-keygen -q -N "" -t ed25519 -f {key_ed25519}') + if 'trusted_user_ca_key' in ssh: + ca_key_name = ssh['trusted_user_ca_key']['ca_certificate'] + pki_ca_cert = ssh['pki']['ca'][ca_key_name] + + loaded_ca_cert = load_certificate(pki_ca_cert['certificate']) + loaded_ca_certs = { + load_certificate(c['certificate']) + for c in ssh['pki']['ca'].values() + if 'certificate' in c + } + + ca_full_chain = find_chain(loaded_ca_cert, loaded_ca_certs) + write_file( + trusted_user_ca_key, '\n'.join(encode_certificate(c) for c in ca_full_chain) + ) + elif os.path.exists(trusted_user_ca_key): + os.unlink(trusted_user_ca_key) + render(config_file, 'ssh/sshd_config.j2', ssh) if 'dynamic_protection' in ssh: @@ -103,12 +145,12 @@ def generate(ssh): return None + def apply(ssh): - systemd_service_ssh = 'ssh.service' systemd_service_sshguard = 'sshguard.service' if not ssh: # SSH access is removed in the commit - call(f'systemctl stop ssh@*.service') + call('systemctl stop ssh@*.service') call(f'systemctl stop {systemd_service_sshguard}') return None @@ -122,13 +164,14 @@ def apply(ssh): if 'restart_required' in ssh: # this is only true if something for the VRFs changed, thus we # stop all VRF services and only restart then new ones - call(f'systemctl stop ssh@*.service') + call('systemctl stop ssh@*.service') systemd_action = 'restart' for vrf in ssh['vrf']: call(f'systemctl {systemd_action} ssh@{vrf}.service') return None + if __name__ == '__main__': try: c = get_config() diff --git a/src/etc/skel/.bashrc b/src/etc/skel/.bashrc index ba7d50003..f807f0c72 100644 --- a/src/etc/skel/.bashrc +++ b/src/etc/skel/.bashrc @@ -92,6 +92,9 @@ fi #alias la='ls -A' #alias l='ls -CF' +# Disable iproute2 auto color +alias ip="ip --color=never" + # Alias definitions. # You may want to put all your additions into a separate file like # ~/.bash_aliases, instead of adding them here directly. diff --git a/src/etc/udev/rules.d/90-vyos-serial.rules b/src/etc/udev/rules.d/90-vyos-serial.rules index 30c1d3170..f86b2258f 100644 --- a/src/etc/udev/rules.d/90-vyos-serial.rules +++ b/src/etc/udev/rules.d/90-vyos-serial.rules @@ -8,7 +8,7 @@ SUBSYSTEMS=="pci", IMPORT{builtin}="hwdb --subsystem=pci" SUBSYSTEMS=="usb", IMPORT{builtin}="usb_id", IMPORT{builtin}="hwdb --subsystem=usb" # /dev/serial/by-path/, /dev/serial/by-id/ for USB devices -KERNEL!="ttyUSB[0-9]*", GOTO="serial_end" +KERNEL!="ttyUSB[0-9]*|ttyACM[0-9]*", GOTO="serial_end" SUBSYSTEMS=="usb-serial", ENV{.ID_PORT}="$attr{port_number}" diff --git a/src/migration-scripts/firewall/16-to-17 b/src/migration-scripts/firewall/16-to-17 index ad0706f04..ad0706f04 100755..100644 --- a/src/migration-scripts/firewall/16-to-17 +++ b/src/migration-scripts/firewall/16-to-17 diff --git a/src/migration-scripts/firewall/17-to-18 b/src/migration-scripts/firewall/17-to-18 new file mode 100755 index 000000000..34ce6aa07 --- /dev/null +++ b/src/migration-scripts/firewall/17-to-18 @@ -0,0 +1,41 @@ +# Copyright (C) 2024-2025 VyOS maintainers and contributors +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with this library. If not, see <http://www.gnu.org/licenses/>. + +# From +# set firewall zone <zone> interface RED +# set firewall zone <zone> interface eth0 +# To +# set firewall zone <zone> member vrf RED +# set firewall zone <zone> member interface eth0 + +from vyos.configtree import ConfigTree + +base = ['firewall', 'zone'] + +def migrate(config: ConfigTree) -> None: + if not config.exists(base): + # Nothing to do + return + + for zone in config.list_nodes(base): + zone_iface_base = base + [zone, 'interface'] + zone_member_base = base + [zone, 'member'] + if config.exists(zone_iface_base): + for iface in config.return_values(zone_iface_base): + if config.exists(['vrf', 'name', iface]): + config.set(zone_member_base + ['vrf'], value=iface, replace=False) + else: + config.set(zone_member_base + ['interface'], value=iface, replace=False) + config.delete(zone_iface_base) diff --git a/src/op_mode/tech_support.py b/src/op_mode/tech_support.py index f60bb87ff..24ac0af1b 100644 --- a/src/op_mode/tech_support.py +++ b/src/op_mode/tech_support.py @@ -97,21 +97,22 @@ def _get_boot_config(): return strip_config_source(config) def _get_config_scripts(): - from os import listdir + from os import walk from os.path import join from vyos.utils.file import read_file scripts = [] dir = '/config/scripts' - for f in listdir(dir): - script = {} - path = join(dir, f) - data = read_file(path) - script["path"] = path - script["data"] = data - - scripts.append(script) + for dirpath, _, filenames in walk(dir): + for filename in filenames: + script = {} + path = join(dirpath, filename) + data = read_file(path) + script["path"] = path + script["data"] = data + + scripts.append(script) return scripts diff --git a/src/op_mode/zone.py b/src/op_mode/zone.py index 49fecdf28..df39549d2 100644 --- a/src/op_mode/zone.py +++ b/src/op_mode/zone.py @@ -56,10 +56,15 @@ def _convert_one_zone_data(zone: str, zone_config: dict) -> dict: from_zone_dict['firewall_v6'] = dict_search( 'firewall.ipv6_name', from_zone_config) list_of_rules.append(from_zone_dict) + zone_members =[] + interface_members = dict_search('member.interface', zone_config) + vrf_members = dict_search('member.vrf', zone_config) + zone_members += interface_members if interface_members is not None else [] + zone_members += vrf_members if vrf_members is not None else [] zone_dict = { 'name': zone, - 'interface': dict_search('interface', zone_config), + 'members': zone_members, 'type': 'LOCAL' if dict_search('local_zone', zone_config) is not None else None, } @@ -126,7 +131,7 @@ def output_zone_list(zone_conf: dict) -> list: if zone_conf['type'] == 'LOCAL': zone_info.append('LOCAL') else: - zone_info.append("\n".join(zone_conf['interface'])) + zone_info.append("\n".join(zone_conf['members'])) from_zone = [] firewall = [] @@ -175,7 +180,7 @@ def get_formatted_output(zone_policy: list) -> str: :rtype: str """ headers = ["Zone", - "Interfaces", + "Members", "From Zone", "Firewall IPv4", "Firewall IPv6" diff --git a/src/services/vyos-configd b/src/services/vyos-configd index d558e8c26..b161fe6ba 100755 --- a/src/services/vyos-configd +++ b/src/services/vyos-configd @@ -211,9 +211,6 @@ def initialization(socket): scripts_called = [] setattr(config, 'scripts_called', scripts_called) - if not hasattr(config, 'frrender_cls'): - setattr(config, 'frrender_cls', FRRender()) - return config @@ -312,8 +309,10 @@ if __name__ == '__main__': remove_if_file(configd_env_file) os.symlink(configd_env_set_file, configd_env_file) - config = None + # We only need one long-lived instance of FRRender + frr = FRRender() + config = None while True: # Wait for next request from client msg = socket.recv().decode() @@ -332,10 +331,11 @@ if __name__ == '__main__': scripts_called = getattr(config, 'scripts_called', []) logger.debug(f'scripts_called: {scripts_called}') - if hasattr(config, 'frrender_cls') and res == R_SUCCESS: - frrender_cls = getattr(config, 'frrender_cls') + if res == R_SUCCESS: tmp = get_frrender_dict(config) - frrender_cls.generate(tmp) - frrender_cls.apply() + if frr.generate(tmp): + # only apply a new FRR configuration if anything changed + # in comparison to the previous applied configuration + frr.apply() else: logger.critical(f'Unexpected message: {message}') diff --git a/src/helpers/vyos-domain-resolver.py b/src/services/vyos-domain-resolver index f5a1d9297..bc74a05d1 100755 --- a/src/helpers/vyos-domain-resolver.py +++ b/src/services/vyos-domain-resolver @@ -16,6 +16,7 @@ import json import time +import logging from vyos.configdict import dict_merge from vyos.configquery import ConfigTreeQuery @@ -48,6 +49,11 @@ ipv6_tables = { 'ip6 raw' } +logger = logging.getLogger(__name__) +logs_handler = logging.StreamHandler() +logger.addHandler(logs_handler) +logger.setLevel(logging.INFO) + def get_config(conf, node): node_config = conf.get_config_dict(node, key_mangling=('-', '_'), get_first_key=True, no_tag_node_value_mangle=True) @@ -163,15 +169,15 @@ def update_fqdn(config, node): nft_conf_str = "\n".join(conf_lines) + "\n" code = run(f'nft --file -', input=nft_conf_str) - print(f'Updated {count} sets in {node} - result: {code}') + logger.info(f'Updated {count} sets in {node} - result: {code}') if __name__ == '__main__': - print(f'VyOS domain resolver') + logger.info(f'VyOS domain resolver') count = 1 while commit_in_progress(): if ( count % 60 == 0 ): - print(f'Commit still in progress after {count}s - waiting') + logger.info(f'Commit still in progress after {count}s - waiting') count += 1 time.sleep(1) @@ -179,7 +185,7 @@ if __name__ == '__main__': firewall = get_config(conf, base_firewall) nat = get_config(conf, base_nat) - print(f'interval: {timeout}s - cache: {cache}') + logger.info(f'interval: {timeout}s - cache: {cache}') while True: update_fqdn(firewall, 'firewall') diff --git a/src/systemd/vyos-domain-resolver.service b/src/systemd/vyos-domain-resolver.service index e63ae5e34..87a4748f4 100644 --- a/src/systemd/vyos-domain-resolver.service +++ b/src/systemd/vyos-domain-resolver.service @@ -6,7 +6,9 @@ ConditionPathExistsGlob=/run/use-vyos-domain-resolver* [Service] Type=simple Restart=always -ExecStart=/usr/bin/python3 -u /usr/libexec/vyos/vyos-domain-resolver.py +ExecStart=/usr/bin/python3 -u /usr/libexec/vyos/services/vyos-domain-resolver +SyslogIdentifier=vyos-domain-resolver +SyslogFacility=daemon StandardError=journal StandardOutput=journal |