Skip to content

Commit

Permalink
ncm-network: dropin file support for main configuration of NetworkMan…
Browse files Browse the repository at this point in the history
…ager

dropin file support for main configuration of NetworkManager
  • Loading branch information
Abdul Karim authored and Abdul Karim committed Nov 20, 2024
1 parent 1c9024c commit 0da0970
Show file tree
Hide file tree
Showing 5 changed files with 64 additions and 42 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ include 'components/network/config';
prefix "/software/components/network";
"ncm-module" = "nmstate";



# Add dependency that can't be added to rpm directly
prefix '/software/packages';
'nmstate' = dict();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,16 +5,31 @@ declaration template components/network/types/network/backend/nmstate;
@documentation{
NetworkManager device configuration for drop in config file.
}

type structure_nm_main_config = {
@{Set the DNS processing mode for NetworkManager}
"dns" ? choice("dnsmasq", "default", "none", "systemd-resolved")
@{Specify devices for which NetworkManager should not create default wired connection}
"no-auto-default" ? string
@{Lists system settings plugin names}
"plugins" ? choice('keyfile', 'ifcfg-rh')
@{append a value to a previously-set list-valued}
"plugins+" ? choice('keyfile', 'ifcfg-rh')
@{remove a value to a previously-set list-valued}
"plugins-" ? choice('keyfile', 'ifcfg-rh')
};

type structure_nm_device_config = {
"keep-configuration" ? choice("yes", "no")
};

type structure_network_backend_specific = {
@{let NetworkManager manage the dns}
"manage_dns" : boolean = false
@{let ncm-network cleanup inactive connections}
"clean_inactive_conn" : boolean = true
@{NetworkManager configuration settings for device section}
"device_config" ? structure_nm_device_config
@{NetworkManager configuration settings for main section}
"main_config" ? structure_nm_main_config
};

type structure_network_rule_backend_specific = {
Expand Down
77 changes: 42 additions & 35 deletions ncm-network/src/main/perl/nmstate.pm
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ Readonly my $NMSTATECTL => '/usr/bin/nmstatectl';
Readonly my $NMCLI_CMD => '/usr/bin/nmcli';
# pick a config name for nmstate yml to configure dns-resolver: settings. if manage_dns=true
Readonly my $NM_RESOLV_YML => "/etc/nmstate/resolv.yml";
Readonly my $NM_DROPIN_CFG_FILE => "/etc/NetworkManager/conf.d/90-quattor.conf";
Readonly my $NM_MAIN_DROPIN_CFG_FILE => "/etc/NetworkManager/conf.d/90-quattor.conf";
Readonly my $NM_DEVICE_DROPIN_CFG_FILE => "/etc/NetworkManager/conf.d/89-device-quattor.conf";

# generate the correct fake yaml boolean value so TextRender can convert it in a yaml boolean
Expand Down Expand Up @@ -83,29 +83,7 @@ sub is_valid_interface
};
}

# By default, NetworkManager on Red Hat Enterprise Linux (RHEL) 8+ dynamically updates the /etc/resolv.conf
# file with the DNS settings from active NetworkManager connection profiles. we manage this using ncm-resolver.
# so disable this unless manage_dns = true. resolver details can be set using nmstate but not doing this now.
sub disable_nm_manage_dns
{
my ($self, $manage_dns, $nwsrv) = @_;
my @data = ('[main]');

if ( $manage_dns ) {
# set nothing, will use default.
$self->verbose("Networkmanager defaults will be used");
} else {
push @data, 'dns=none';
$self->verbose("Configuring networkmanager not to manage dns");
}
my $fh = CAF::FileWriter->new($NM_DROPIN_CFG_FILE, mode => oct(444), log => $self, keeps_state => 1);
print $fh join("\n", @data, '');
if ($fh->close()) {
$self->info("File $NM_DROPIN_CFG_FILE changed, reload network");
$nwsrv->reload();
};
}

# manage NetworkManager [device] settings
sub nm_create_device_config_dropin
{
my ($self, $nm_device_config, $nwsrv) = @_;
Expand All @@ -117,12 +95,35 @@ sub nm_create_device_config_dropin
};

$self->verbose("setting device configuration dropin");

my $fh = CAF::FileWriter->new($NM_DEVICE_DROPIN_CFG_FILE, mode => oct(444), log => $self);
print $fh join("\n", @data, '');
if ($fh->close()) {
$self->info("File $NM_DEVICE_DROPIN_CFG_FILE changed, reload network");
$nwsrv->reload();
};
}
my $fh = CAF::FileWriter->new($NM_DEVICE_DROPIN_CFG_FILE, mode => oct(444), log => $self);
print $fh join("\n", @data, '');
if ($fh->close()) {
$self->info("File $NM_DEVICE_DROPIN_CFG_FILE changed, reload network");
$nwsrv->reload();
}

# manage NetworkManager [main] settings
sub nm_create_main_config_dropin
{
my ($self, $nm_main_config, $nwsrv) = @_;
my @data = ('[main]');

if ( scalar keys %$nm_main_config gt 0 ) {
foreach my $key (sort keys %$nm_main_config){
push @data, $key."=".$nm_main_config->{$key};
};

$self->verbose("setting NetworkManager main configuration dropin");

my $fh = CAF::FileWriter->new($NM_MAIN_DROPIN_CFG_FILE, mode => oct(444), log => $self);
print $fh join("\n", @data, '');
if ($fh->close()) {
$self->info("File $NM_MAIN_DROPIN_CFG_FILE changed, reload network");
$nwsrv->reload();
};
};
}

Expand Down Expand Up @@ -865,7 +866,11 @@ sub Configure
my $nwtree = $config->getTree($NETWORK_PATH);

my $hostname = $nwtree->{realhostname} || "$nwtree->{hostname}.$nwtree->{domainname}";
my $manage_dns = $nwtree->{manage_dns} || 0;
# NetworkManager main configuration
my $nm_main_cfg = $nwtree->{main_config};
# set to none if main_config/dns is not defined.
my $main_cfg_dns = $nm_main_cfg->{dns} || 'none';
my $manage_dns = ($main_cfg_dns eq 'none') ? 0 : 1;
my $dgw = $nwtree->{default_gateway};
if (!$dgw) {
$self->warn ("No default gateway configured");
Expand Down Expand Up @@ -949,17 +954,19 @@ sub Configure
# 3. (re)start things
my $nwsrv = CAF::Service->new(['NetworkManager'], log => $self);

if ( scalar keys %$nm_main_cfg gt 0 ) {
$self->nm_create_main_config_dropin($nm_main_cfg, $nwsrv);
} else {
$self->cleanup($NM_MAIN_DROPIN_CFG_FILE);
}
# NetworkManager device configuration, if defined.
my $nm_device_cfg = $nwtree->{device_config};
if ($nm_device_cfg){
if (scalar keys %$nm_device_cfg gt 0){
$self->nm_create_device_config_dropin($nm_device_cfg, $nwsrv);
} else {
$self->cleanup($NM_DEVICE_DROPIN_CFG_FILE);
}

# NetworkManager manages dns by default, but we manage dns with e.g. ncm-resolver, new option to enable/disable it.
$self->disable_nm_manage_dns($manage_dns, $nwsrv);


my $dnsconfig = $self->generate_nm_resolver_config($nwtree, $manage_dns);
$exifiles->{$NM_RESOLV_YML} = $self->nmstate_file_dump($NM_RESOLV_YML, $dnsconfig);
# nmstate files are applied uinsg nmstate apply via this component. We don't want nmstate svc to manage it.
Expand Down
7 changes: 3 additions & 4 deletions ncm-network/src/test/perl/nmstate_simple.t
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ Readonly my $RESOLV => <<EOF;
managed by something else
EOF

Readonly my $NODNS => <<EOF;
Readonly my $MAIN_CONFIG => <<EOF;
[main]
dns=none
EOF
Expand Down Expand Up @@ -88,13 +88,12 @@ command_history_reset();
is($cmp->Configure($cfg), 1, "Component runs correctly with a test profile");

my $fh;

# resolv.conf is unchanged
is(get_file_contents("/etc/resolv.conf"), $RESOLV, "Exact network config");

# set nm config to disable dns mgmt
is(get_file_contents("/etc/NetworkManager/conf.d/90-quattor.conf"), $NODNS, "disable NM dns mgmt");
is(get_file_contents("/etc/NetworkManager/conf.d/89-device-quattor.conf"), $DEVICE_CONFIG, "networkmanager config for device");
is(get_file_contents("/etc/NetworkManager/conf.d/90-quattor.conf"), $MAIN_CONFIG, "NetworkManager config for main");
is(get_file_contents("/etc/NetworkManager/conf.d/89-device-quattor.conf"), $DEVICE_CONFIG, "NetworkManager config for device");

# unconfigure nmstate yml is removed
ok(!$cmp->file_exists("/etc/nmstate/toremove0.yml"), "unconfigured yml nmstate is removed");
Expand Down
1 change: 0 additions & 1 deletion ncm-network/src/test/resources/nmstate_simple.pan
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@ include 'simple_base_profile';
"/hardware/cards/nic/eth0/hwaddr" = "6e:a5:1b:55:77:0a";

"/system/network/device_config/keep-configuration" = "no";

# the next include is mainly to the profile, it is not used in the tests
# (unless the component gets specific schema things)
include 'components/network/config-nmstate';

0 comments on commit 0da0970

Please sign in to comment.