import nmstate-0.3.2-6.el8

This commit is contained in:
CentOS Sources 2020-07-28 02:08:29 -04:00 committed by Stepan Oksanichenko
parent f39e2f06d4
commit ea34f8f454
11 changed files with 874 additions and 27 deletions

4
.gitignore vendored
View File

@ -1,2 +1,2 @@
SOURCES/gpgkey-F7910D93CA83D77348595C0E899014C0463C12BB.gpg
SOURCES/nmstate-0.2.0.tar.gz
SOURCES/nmstate-0.3.2.tar.gz
SOURCES/nmstate.gpg

View File

@ -1,2 +1,2 @@
7bcc63976a8d449b3adc57f40d7a476106889042 SOURCES/gpgkey-F7910D93CA83D77348595C0E899014C0463C12BB.gpg
33afae47f344d5908b7772fbfd33fef26eb88ffb SOURCES/nmstate-0.2.0.tar.gz
5f07dbfc599578c7b90fd3efd044bf01f7aa7c4c SOURCES/nmstate-0.3.2.tar.gz
c3efe2931425e910002e11ff34ef102fbfa0b9de SOURCES/nmstate.gpg

View File

@ -0,0 +1,217 @@
From 83a9a81c38463c66ad512aacccfe627aa2b5a17e Mon Sep 17 00:00:00 2001
From: Fernando Fernandez Mancera <ffmancera@riseup.net>
Date: Tue, 23 Jun 2020 10:18:51 +0200
Subject: [PATCH 1/3] base_iface: rename iface_type property to type
In order to follow the property naming, it makes sense to rename
"iface_type" property to "type".
Signed-off-by: Fernando Fernandez Mancera <ffmancera@riseup.net>
Signed-off-by: Gris Ge <fge@redhat.com>
---
libnmstate/ifaces/base_iface.py | 4 ++--
libnmstate/ifaces/ifaces.py | 9 ++++-----
libnmstate/ifaces/ovs.py | 4 ++--
libnmstate/plugins/nmstate_plugin_ovsdb.py | 4 ++--
4 files changed, 10 insertions(+), 11 deletions(-)
diff --git a/libnmstate/ifaces/base_iface.py b/libnmstate/ifaces/base_iface.py
index 56a1115..6c55f6a 100644
--- a/libnmstate/ifaces/base_iface.py
+++ b/libnmstate/ifaces/base_iface.py
@@ -152,7 +152,7 @@ class BaseIface:
return self._name
@property
- def iface_type(self):
+ def type(self):
return self._info.get(Interface.TYPE, InterfaceType.UNKNOWN)
@property
@@ -285,7 +285,7 @@ class BaseIface:
if self.is_master and not self.is_absent:
for slave_name in self.slaves:
slave_iface = ifaces[slave_name]
- slave_iface.set_master(self.name, self.iface_type)
+ slave_iface.set_master(self.name, self.type)
def update(self, info):
self._info.update(info)
diff --git a/libnmstate/ifaces/ifaces.py b/libnmstate/ifaces/ifaces.py
index 9c254ac..e85123c 100644
--- a/libnmstate/ifaces/ifaces.py
+++ b/libnmstate/ifaces/ifaces.py
@@ -74,7 +74,7 @@ class Ifaces:
if iface_info.get(Interface.TYPE) is None:
if cur_iface:
- iface_info[Interface.TYPE] = cur_iface.iface_type
+ iface_info[Interface.TYPE] = cur_iface.type
elif iface.is_up:
raise NmstateValueError(
f"Interface {iface.name} has no type defined "
@@ -82,7 +82,7 @@ class Ifaces:
)
iface = _to_specific_iface_obj(iface_info, save_to_disk)
if (
- iface.iface_type == InterfaceType.UNKNOWN
+ iface.type == InterfaceType.UNKNOWN
# Allowing deletion of down profiles
and not iface.is_absent
):
@@ -147,7 +147,7 @@ class Ifaces:
When OVS patch peer does not exist or is down, raise an error.
"""
for iface in self._ifaces.values():
- if iface.iface_type == InterfaceType.OVS_INTERFACE and iface.is_up:
+ if iface.type == InterfaceType.OVS_INTERFACE and iface.is_up:
if iface.peer:
peer_iface = self._ifaces.get(iface.peer)
if not peer_iface or not peer_iface.is_up:
@@ -156,8 +156,7 @@ class Ifaces:
"be up"
)
elif (
- not peer_iface.iface_type
- == InterfaceType.OVS_INTERFACE
+ not peer_iface.type == InterfaceType.OVS_INTERFACE
or not peer_iface.is_patch_port
):
raise NmstateValueError(
diff --git a/libnmstate/ifaces/ovs.py b/libnmstate/ifaces/ovs.py
index 0a5abe9..cd04cef 100644
--- a/libnmstate/ifaces/ovs.py
+++ b/libnmstate/ifaces/ovs.py
@@ -84,7 +84,7 @@ class OvsBridgeIface(BridgeIface):
slave_iface.update(
{BridgeIface.BRPORT_OPTIONS_METADATA: port_config}
)
- if slave_iface.iface_type == InterfaceType.OVS_INTERFACE:
+ if slave_iface.type == InterfaceType.OVS_INTERFACE:
slave_iface.parent = self.name
super().gen_metadata(ifaces)
@@ -101,7 +101,7 @@ class OvsBridgeIface(BridgeIface):
}
)
slave_iface.mark_as_changed()
- slave_iface.set_master(self.name, self.iface_type)
+ slave_iface.set_master(self.name, self.type)
slave_iface.parent = self.name
return slave_iface
diff --git a/libnmstate/plugins/nmstate_plugin_ovsdb.py b/libnmstate/plugins/nmstate_plugin_ovsdb.py
index a0cfbc0..83965e1 100644
--- a/libnmstate/plugins/nmstate_plugin_ovsdb.py
+++ b/libnmstate/plugins/nmstate_plugin_ovsdb.py
@@ -168,9 +168,9 @@ class NmstateOvsdbPlugin(NmstatePlugin):
continue
if not iface.is_up:
continue
- if iface.iface_type == OVSBridge.TYPE:
+ if iface.type == OVSBridge.TYPE:
table_name = "Bridge"
- elif iface.iface_type == OVSInterface.TYPE:
+ elif iface.type == OVSInterface.TYPE:
table_name = "Interface"
else:
continue
--
2.27.0
From 80a0a200fc198d9f2f31cfa67fbd3d2c776256df Mon Sep 17 00:00:00 2001
From: Adwait Thattey <coderdude1999@gmail.com>
Date: Thu, 18 Jun 2020 23:11:33 +0530
Subject: [PATCH 2/3] iface: add setter method for mtu of interface
Signed-off-by: Adwait Thattey <coderdude1999@gmail.com>
Signed-off-by: Gris Ge <fge@redhat.com>
---
libnmstate/ifaces/base_iface.py | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/libnmstate/ifaces/base_iface.py b/libnmstate/ifaces/base_iface.py
index 6c55f6a..edccb1f 100644
--- a/libnmstate/ifaces/base_iface.py
+++ b/libnmstate/ifaces/base_iface.py
@@ -298,6 +298,10 @@ class BaseIface:
def mtu(self):
return self._info.get(Interface.MTU)
+ @mtu.setter
+ def mtu(self, value):
+ self._info[Interface.MTU] = value
+
def _capitalize_mac(self):
if self.mac:
self._info[Interface.MAC] = self.mac.upper()
--
2.27.0
From 60ef20b6b4a4cd76b47b5fa8f989eee2ca2608fd Mon Sep 17 00:00:00 2001
From: Adwait Thattey <coderdude1999@gmail.com>
Date: Thu, 18 Jun 2020 23:58:11 +0530
Subject: [PATCH 3/3] vlan: validate mtu not greater than base iface
A new validator is added that verifies that the
MTU of VLAN/VXLAN is not more than MTU of base iface
If base iface MTU doesn't exist, set as vlan MTU
Multiple tests are added to check if appropriate errors are thrown
Signed-off-by: Adwait Thattey <coderdude1999@gmail.com>
Signed-off-by: Gris Ge <fge@redhat.com>
---
libnmstate/ifaces/ifaces.py | 26 ++++++++++++++++++++++++++
1 file changed, 26 insertions(+)
diff --git a/libnmstate/ifaces/ifaces.py b/libnmstate/ifaces/ifaces.py
index e85123c..c216dd8 100644
--- a/libnmstate/ifaces/ifaces.py
+++ b/libnmstate/ifaces/ifaces.py
@@ -123,6 +123,7 @@ class Ifaces:
def _pre_edit_validation_and_cleanup(self):
self._validate_over_booked_slaves()
+ self._validate_vlan_mtu()
self._handle_master_slave_list_change()
self._match_child_iface_state_with_parent()
self._mark_orphen_as_absent()
@@ -164,6 +165,31 @@ class Ifaces:
" patch port"
)
+ def _validate_vlan_mtu(self):
+ """
+ Validate that mtu of vlan or vxlan is less than
+ or equal to it's base interface's MTU
+
+ If base MTU is not present, set same as vlan MTU
+ """
+ for iface in self._ifaces.values():
+
+ if (
+ iface.type in [InterfaceType.VLAN, InterfaceType.VXLAN]
+ and iface.is_up
+ and iface.mtu
+ ):
+ base_iface = self._ifaces.get(iface.parent)
+ if not base_iface.mtu:
+ base_iface.mtu = iface.mtu
+ if iface.mtu > base_iface.mtu:
+ raise NmstateValueError(
+ f"Interface {iface.name} has bigger "
+ f"MTU({iface.mtu}) "
+ f"than its base interface: {iface.parent} "
+ f"MTU({base_iface.mtu})"
+ )
+
def _handle_master_slave_list_change(self):
"""
* Mark slave interface as changed if master removed.
--
2.27.0

View File

@ -0,0 +1,171 @@
From d0bfae4171f0d280241949a928654c84e63ed006 Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Mon, 29 Jun 2020 22:30:03 +0800
Subject: [PATCH] pretty state: Dumping state in the sorted order with priority
For OVS bond port, we would like the `name` been shown before other
properties.
To achieve that, we sort the dict keys and honoring the priority list which
means keys in `PRIORITY_LIST` will be shown before others.
Currently the `PRIORITY_LIST` is:
`("name", "type", "state", "enabled", "dns", "route-rules", "routes",
"interfaces")`
Test cases added.
Signed-off-by: Gris Ge <fge@redhat.com>
Signed-off-by: Till Maas <till@redhat.com>
---
libnmstate/prettystate.py | 94 ++++++++++++++++++---------------------
1 file changed, 43 insertions(+), 51 deletions(-)
diff --git a/libnmstate/prettystate.py b/libnmstate/prettystate.py
index da57618..10e22d6 100644
--- a/libnmstate/prettystate.py
+++ b/libnmstate/prettystate.py
@@ -1,5 +1,5 @@
#
-# Copyright (c) 2018-2019 Red Hat, Inc.
+# Copyright (c) 2018-2020 Red Hat, Inc.
#
# This file is part of nmstate
#
@@ -17,15 +17,29 @@
# along with this program. If not, see <https://www.gnu.org/licenses/>.
#
-from collections import OrderedDict
+from collections.abc import Mapping
+from collections.abc import Sequence
from copy import deepcopy
import difflib
import json
-from operator import itemgetter
import yaml
-from libnmstate.schema import Constants
+from .schema import DNS
+from .schema import Route
+from .schema import RouteRule
+from .schema import Interface
+
+PRIORITY_LIST = (
+ "name",
+ "type",
+ "state",
+ "enabled",
+ DNS.KEY,
+ RouteRule.KEY,
+ Route.KEY,
+ Interface.KEY,
+)
def format_desired_current_state_diff(desired_state, current_state):
@@ -57,8 +71,8 @@ def format_desired_current_state_diff(desired_state, current_state):
class PrettyState:
def __init__(self, state):
- yaml.add_representer(OrderedDict, represent_ordereddict)
- self.state = order_state(deepcopy(state))
+ yaml.add_representer(dict, represent_dict)
+ self.state = _sort_with_priority(state)
@property
def yaml(self):
@@ -71,35 +85,18 @@ class PrettyState:
return json.dumps(self.state, indent=4, separators=(",", ": "))
-def represent_ordereddict(dumper, data):
+def represent_dict(dumper, data):
+ """
+ Represent dictionary with insert order
"""
- Represent OrderedDict as regular dictionary
-
- Source: https://stackoverflow.com/questions/16782112/can-pyyaml-dump-dict-items-in-non-alphabetical-order
- """ # noqa: E501
value = []
for item_key, item_value in data.items():
node_key = dumper.represent_data(item_key)
node_value = dumper.represent_data(item_value)
-
value.append((node_key, node_value))
- return yaml.nodes.MappingNode(u"tag:yaml.org,2002:map", value)
-
-
-def order_state(state):
- iface_states = state.pop(Constants.INTERFACES, None)
-
- state = order_iface_state(state)
-
- if iface_states is not None:
- state[Constants.INTERFACES] = [
- order_iface_state(iface_state)
- for iface_state in sorted(iface_states, key=itemgetter("name"))
- ]
-
- return state
+ return yaml.nodes.MappingNode("tag:yaml.org,2002:map", value)
def represent_unicode(_, data):
@@ -112,30 +109,25 @@ def represent_unicode(_, data):
"""
return yaml.ScalarNode(
- tag=u"tag:yaml.org,2002:str", value=data.encode("utf-8")
+ tag="tag:yaml.org,2002:str", value=data.encode("utf-8")
)
-def order_iface_state(iface_state):
- ordered_state = OrderedDict()
-
- for setting in ("name", "type", "state"):
- try:
- ordered_state[setting] = iface_state.pop(setting)
- except KeyError:
- pass
-
- for key, value in order_dict(iface_state).items():
- ordered_state[key] = value
-
- return ordered_state
-
-
-def order_dict(dict_):
- ordered_dict = OrderedDict()
- for key, value in sorted(dict_.items()):
- if isinstance(value, dict):
- value = order_dict(value)
- ordered_dict[key] = value
-
- return ordered_dict
+def _sort_with_priority(data):
+ if isinstance(data, Sequence) and not isinstance(data, str):
+ return [_sort_with_priority(item) for item in data]
+ elif isinstance(data, Mapping):
+ new_data = {}
+ for key in sorted(data.keys(), key=_sort_with_priority_key_func):
+ new_data[key] = _sort_with_priority(data[key])
+ return new_data
+ else:
+ return deepcopy(data)
+
+
+def _sort_with_priority_key_func(key):
+ try:
+ priority = PRIORITY_LIST.index(key)
+ except ValueError:
+ priority = len(PRIORITY_LIST)
+ return (priority, key)
--
2.27.0

View File

@ -0,0 +1,176 @@
From c3a924203e8f0d3d6d6fc7882f006d60e7d8d985 Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Fri, 19 Jun 2020 10:14:25 +0800
Subject: [PATCH] ip: canonicalize IP address
Canonicalize these IP addresses:
* `InterfaceIP.ADDRESS_IP`
* `Route.DESTINATION`
* `Route.NEXT_HOP_ADDRESS`
* `RouteRule.IP_FROM`
* `RouteRule.IP_TO`
Introduced two functions to `libnmstate/iplib.py`:
* `canonicalize_ip_network()` returns address with prefix
* `canonicalize_ip_address()` returns address without prefix
Unit test cases added.
Signed-off-by: Gris Ge <fge@redhat.com>
---
libnmstate/ifaces/base_iface.py | 19 +++++++------------
libnmstate/iplib.py | 14 ++++++++++++++
libnmstate/route.py | 12 ++++++++++++
libnmstate/route_rule.py | 14 +++++++-------
4 files changed, 40 insertions(+), 19 deletions(-)
diff --git a/libnmstate/ifaces/base_iface.py b/libnmstate/ifaces/base_iface.py
index 33da69d..56a1115 100644
--- a/libnmstate/ifaces/base_iface.py
+++ b/libnmstate/ifaces/base_iface.py
@@ -20,13 +20,12 @@
from collections.abc import Mapping
from copy import deepcopy
import logging
-from ipaddress import ip_address
from operator import itemgetter
from libnmstate.error import NmstateInternalError
from libnmstate.error import NmstateValueError
-from libnmstate.iplib import is_ipv6_address
from libnmstate.iplib import is_ipv6_link_local_addr
+from libnmstate.iplib import canonicalize_ip_address
from libnmstate.schema import Interface
from libnmstate.schema import InterfaceIP
from libnmstate.schema import InterfaceIPv6
@@ -44,7 +43,7 @@ class IPState:
self._info = info
self._remove_stack_if_disabled()
self._sort_addresses()
- self._canonicalize_ipv6_addr()
+ self._canonicalize_ip_addr()
self._canonicalize_dynamic()
def _canonicalize_dynamic(self):
@@ -61,15 +60,11 @@ class IPState:
):
self._info.pop(dhcp_option, None)
- def _canonicalize_ipv6_addr(self):
- """
- Convert full IPv6 address to abbreviated address.
- """
- if self._family == Interface.IPV6:
- for addr in self.addresses:
- address = addr[InterfaceIP.ADDRESS_IP]
- if is_ipv6_address(address):
- addr[InterfaceIP.ADDRESS_IP] = str(ip_address(address))
+ def _canonicalize_ip_addr(self):
+ for addr in self.addresses:
+ addr[InterfaceIP.ADDRESS_IP] = canonicalize_ip_address(
+ addr[InterfaceIP.ADDRESS_IP]
+ )
def _sort_addresses(self):
self.addresses.sort(key=itemgetter(InterfaceIP.ADDRESS_IP))
diff --git a/libnmstate/iplib.py b/libnmstate/iplib.py
index 57fffd7..183b81b 100644
--- a/libnmstate/iplib.py
+++ b/libnmstate/iplib.py
@@ -52,3 +52,17 @@ def ip_address_full_to_tuple(addr):
raise NmstateValueError(f"Invalid IP address, error: {err}")
return f"{net.network_address}", net.prefixlen
+
+
+def canonicalize_ip_network(address):
+ try:
+ return ipaddress.ip_network(address, strict=False).with_prefixlen
+ except ValueError as e:
+ raise NmstateValueError(f"Invalid IP network address: {e}")
+
+
+def canonicalize_ip_address(address):
+ try:
+ return ipaddress.ip_address(address).compressed
+ except ValueError as e:
+ raise NmstateValueError(f"Invalid IP address: {e}")
diff --git a/libnmstate/route.py b/libnmstate/route.py
index 6534182..a182f99 100644
--- a/libnmstate/route.py
+++ b/libnmstate/route.py
@@ -22,6 +22,8 @@ from collections import defaultdict
from libnmstate.error import NmstateValueError
from libnmstate.error import NmstateVerificationError
from libnmstate.iplib import is_ipv6_address
+from libnmstate.iplib import canonicalize_ip_network
+from libnmstate.iplib import canonicalize_ip_address
from libnmstate.prettystate import format_desired_current_state_diff
from libnmstate.schema import Interface
from libnmstate.schema import Route
@@ -44,6 +46,7 @@ class RouteEntry(StateEntry):
# TODO: Convert IPv6 full address to abbreviated address
self.complement_defaults()
self._invalid_reason = None
+ self._canonicalize_ip_address()
@property
def is_ipv6(self):
@@ -148,6 +151,15 @@ class RouteEntry(StateEntry):
return False
return True
+ def _canonicalize_ip_address(self):
+ if not self.absent:
+ if self.destination:
+ self.destination = canonicalize_ip_network(self.destination)
+ if self.next_hop_address:
+ self.next_hop_address = canonicalize_ip_address(
+ self.next_hop_address
+ )
+
class RouteState:
def __init__(self, ifaces, des_route_state, cur_route_state):
diff --git a/libnmstate/route_rule.py b/libnmstate/route_rule.py
index 8b45367..f35d59c 100644
--- a/libnmstate/route_rule.py
+++ b/libnmstate/route_rule.py
@@ -6,7 +6,7 @@ from libnmstate.error import NmstateVerificationError
from libnmstate.error import NmstateValueError
from libnmstate.iplib import KERNEL_MAIN_ROUTE_TABLE_ID
from libnmstate.iplib import is_ipv6_address
-from libnmstate.iplib import to_ip_address_full
+from libnmstate.iplib import canonicalize_ip_network
from libnmstate.prettystate import format_desired_current_state_diff
from libnmstate.schema import Interface
from libnmstate.schema import RouteRule
@@ -23,7 +23,7 @@ class RouteRuleEntry(StateEntry):
self.priority = route_rule.get(RouteRule.PRIORITY)
self.route_table = route_rule.get(RouteRule.ROUTE_TABLE)
self._complement_defaults()
- self._append_prefix_length_for_host_only_ip()
+ self._canonicalize_ip_network()
def _complement_defaults(self):
if self.ip_from is None:
@@ -38,11 +38,11 @@ class RouteRuleEntry(StateEntry):
):
self.route_table = KERNEL_MAIN_ROUTE_TABLE_ID
- def _append_prefix_length_for_host_only_ip(self):
- if self.ip_from and "/" not in self.ip_from:
- self.ip_from = to_ip_address_full(self.ip_from)
- if self.ip_to and "/" not in self.ip_to:
- self.ip_to = to_ip_address_full(self.ip_to)
+ def _canonicalize_ip_network(self):
+ if self.ip_from:
+ self.ip_from = canonicalize_ip_network(self.ip_from)
+ if self.ip_to:
+ self.ip_to = canonicalize_ip_network(self.ip_to)
def _keys(self):
return (self.ip_from, self.ip_to, self.priority, self.route_table)
--
2.27.0

View File

@ -0,0 +1,63 @@
From 26ca4e3a1a96829ca115f436872d4a575490cce6 Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Wed, 24 Jun 2020 15:27:42 +0800
Subject: [PATCH] nm/device: Only invoke reapply on activated device
Only invoke `NM.Device.reapply_async()` on activated device.
Signed-off-by: Gris Ge <fge@redhat.com>
---
libnmstate/nm/device.py | 32 ++++++++++++++++++--------------
1 file changed, 18 insertions(+), 14 deletions(-)
diff --git a/libnmstate/nm/device.py b/libnmstate/nm/device.py
index 92447b0..528f57d 100644
--- a/libnmstate/nm/device.py
+++ b/libnmstate/nm/device.py
@@ -53,25 +53,29 @@ def delete(context, dev):
con_profile.delete()
-def modify(context, dev, connection_profile):
+def modify(context, nm_dev, connection_profile):
"""
Modify the given connection profile on the device.
Implemented by the reapply operation with a fallback to the
connection profile activation.
"""
- version_id = 0
- flags = 0
- action = f"Reapply device config: {dev.get_iface()}"
- context.register_async(action)
- user_data = context, dev, action
- dev.reapply_async(
- connection_profile,
- version_id,
- flags,
- context.cancellable,
- _modify_callback,
- user_data,
- )
+ nm_ac = nm_dev.get_active_connection()
+ if connection.is_activated(nm_ac, nm_dev):
+ version_id = 0
+ flags = 0
+ action = f"Reapply device config: {nm_dev.get_iface()}"
+ context.register_async(action)
+ user_data = context, nm_dev, action
+ nm_dev.reapply_async(
+ connection_profile,
+ version_id,
+ flags,
+ context.cancellable,
+ _modify_callback,
+ user_data,
+ )
+ else:
+ _activate_async(context, nm_dev)
def _modify_callback(src_object, result, user_data):
--
2.27.0

View File

@ -0,0 +1,68 @@
From 69bed0e79bd951b4e5496cae6b3738649030b5ae Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Tue, 23 Jun 2020 20:28:30 +0800
Subject: [PATCH] ovs: Eliminate the repeat call of is_ovs_running()
The `validate_interface_capabilities()` is invoking `is_ovs_running()`
on every interface. Fixed by using `set()` for interface types for
duplicate types and also caching ovs daemon status.
The `NetworkManagerPlugin.get_interfaces()` is invoking
`is_ovs_running()` on every interface. Fixed by caching ovs daemon
status.
Signed-off-by: Gris Ge <fge@redhat.com>
---
libnmstate/nm/plugin.py | 3 ++-
libnmstate/validator.py | 5 +++--
2 files changed, 5 insertions(+), 3 deletions(-)
diff --git a/libnmstate/nm/plugin.py b/libnmstate/nm/plugin.py
index 20fa77e..4032359 100644
--- a/libnmstate/nm/plugin.py
+++ b/libnmstate/nm/plugin.py
@@ -97,6 +97,7 @@ class NetworkManagerPlugin(NmstatePlugin):
def get_interfaces(self):
info = []
+ capabilities = self.capabilities
devices_info = [
(dev, nm_device.get_device_common_info(dev))
@@ -122,7 +123,7 @@ class NetworkManagerPlugin(NmstatePlugin):
if nm_bond.is_bond_type_id(type_id):
bondinfo = nm_bond.get_bond_info(dev)
iface_info.update(_ifaceinfo_bond(bondinfo))
- elif NmstatePlugin.OVS_CAPABILITY in self.capabilities:
+ elif NmstatePlugin.OVS_CAPABILITY in capabilities:
if nm_ovs.is_ovs_bridge_type_id(type_id):
iface_info["bridge"] = nm_ovs.get_ovs_info(
self.context, dev, devices_info
diff --git a/libnmstate/validator.py b/libnmstate/validator.py
index ee30166..02890b4 100644
--- a/libnmstate/validator.py
+++ b/libnmstate/validator.py
@@ -47,9 +47,10 @@ def validate_capabilities(state, capabilities):
def validate_interface_capabilities(ifaces_state, capabilities):
- ifaces_types = [iface_state.get("type") for iface_state in ifaces_state]
+ ifaces_types = {iface_state.get("type") for iface_state in ifaces_state}
has_ovs_capability = NmstatePlugin.OVS_CAPABILITY in capabilities
has_team_capability = NmstatePlugin.TEAM_CAPABILITY in capabilities
+ ovs_is_running = is_ovs_running()
for iface_type in ifaces_types:
is_ovs_type = iface_type in (
InterfaceType.OVS_BRIDGE,
@@ -57,7 +58,7 @@ def validate_interface_capabilities(ifaces_state, capabilities):
InterfaceType.OVS_PORT,
)
if is_ovs_type and not has_ovs_capability:
- if not is_ovs_running():
+ if not ovs_is_running:
raise NmstateDependencyError(
"openvswitch service is not started."
)
--
2.27.0

View File

@ -0,0 +1,60 @@
From 54e49943b636eab9453189381e93c68050c1e423 Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Sun, 28 Jun 2020 20:05:08 +0800
Subject: [PATCH] dns: Fix remove dns config
Current code raise NmstateVerificationError when user not providing
the full state:
DNS.CONFIG: {DNS.SERVER: [], DNS.SEARCH: []}
Now supporting remove static DNS config via:
* DNS.CONFIG: {}
* DNS.CONFIG: {DNS.SERVER: []}
* DNS.CONFIG: {DNS.SEARCH: []}
* DNS.CONFIG: {DNS.SERVER: [], DNS.SEARCH: []}
Test case updated for this.
Signed-off-by: Gris Ge <fge@redhat.com>
---
libnmstate/dns.py | 12 ++++++++----
1 file changed, 8 insertions(+), 4 deletions(-)
diff --git a/libnmstate/dns.py b/libnmstate/dns.py
index 3196fc4..1ec0d81 100644
--- a/libnmstate/dns.py
+++ b/libnmstate/dns.py
@@ -33,14 +33,16 @@ class DnsState:
def __init__(self, des_dns_state, cur_dns_state):
self._config_changed = False
- if des_dns_state:
+ if des_dns_state is None or des_dns_state.get(DNS.CONFIG) is None:
+ # Use current config if DNS.KEY not defined or DNS.CONFIG not
+ # defined.
+ self._dns_state = cur_dns_state or {}
+ else:
self._dns_state = des_dns_state
self._validate()
self._config_changed = _is_dns_config_changed(
des_dns_state, cur_dns_state
)
- else:
- self._dns_state = cur_dns_state or {}
self._cur_dns_state = deepcopy(cur_dns_state) if cur_dns_state else {}
@property
@@ -179,7 +181,9 @@ class DnsState:
def verify(self, cur_dns_state):
cur_dns = DnsState(des_dns_state=None, cur_dns_state=cur_dns_state,)
- if self.config != cur_dns.config:
+ if self.config.get(DNS.SERVER) != cur_dns.config.get(
+ DNS.SERVER
+ ) or self.config.get(DNS.SEARCH) != cur_dns.config.get(DNS.SEARCH):
raise NmstateVerificationError(
format_desired_current_state_diff(
{DNS.KEY: self.config}, {DNS.KEY: cur_dns.config},
--
2.27.0

View File

@ -1,17 +0,0 @@
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v2.0.22 (GNU/Linux)
iQIcBAABAgAGBQJd5R19AAoJEImQFMBGPBK7Q3QP/j0+keNS1M7i0LeCjv4r0/rU
3eqfGBwEUH8s8Jb8mSOyveWOZeVrNg8GXO8kv36DLWUBoCJ1r0iYtG+u5IuusUjp
AXuIS86jmIT1s3kuSXnOhybeD5ZQm8WS5mG/Kmd/I1m24oo+KDrQgkBfiXnqTNIm
OYPfI5hACK9b3AxAVATJHjDvF87YAKKa9xgpFPvUhJE0hjoJ4nx2aI9x09kWsxdT
aT5Mjc/3gu+ARabJdE0p2amNQW+lCs3O8TKU8ZOjYrBKV3VMD/V+rqLzqR3QvBcj
67VNHl5bq01r0PoN9U2MW/2g3sKpbGhtHEwwDxuzymxk/Z7Wyzjk8+9c3sFxL/VU
t/iezDgkT23IwU2clzP8V3Rjc2GKd+rq7M8G86mxV9ausaj8SZWfuUpnFkjStm8V
d2LNfuKiquR+0qhcSoFdeyKhIISlhNMymzkyBDucC3LRXKt7kfhXCwRx7RYDfVbZ
q/Yw+xzLtGmNjOz/hK+5V3wxonwZRob0JLOoRfsqi0BaXVq/Q/AcFIah9oZghBxT
AtDBLor9qM572PLSV7W8rPJ7fGlsFETIvF4erqC5yxzjZ4dgX/3zr3Zpwr/xE/RV
wDeiRjkkWo8i1lCQtS3Cd8yY4WZ/iI7egEMyLojWgrirz1uMNBZFtntwe+IoG9VH
2WTL8od4f/gk7xKPbCIY
=69KO
-----END PGP SIGNATURE-----

View File

@ -0,0 +1,16 @@
-----BEGIN PGP SIGNATURE-----
iQIzBAABCAAdFiEE8f1XsqXpyNthgIbGbM3lj+QeKP8FAl7nxvAACgkQbM3lj+Qe
KP/6yw/9GBET+XD86qCuzu9sxZt2vZTw3CIqvieuCPkzquqymoI2owJ2rCrNpnZy
jdhrobV992pt4qpHo12k8o8LubO38rzVkG6lXSJ8rlLrRkJc5c3APJPzeEnuWsrB
HL0JZ4Z2MA+q4TdLGPDNrN/XpnOEDphRZcuD6sFIa9nmiCbj6aI2BaQRriwr8bbh
W0LBzQ71u5tIXLVKo+Z3XYmQwFcjW8jQkxrfQbTYT80JORc2aC+yBdfayw+5GSsm
Us41H8cStfayv4m5t3Cvy8DMoxe1YC/GBY16sPDdmX+qTS43de8vtCgBho3KZrXx
cHi2V2/vlxo2Zra2a8wpwDFOU0nPbgRR+79R7w5/2f9U6g0sok3Qa4WLYjYE1tbK
l2gw/hdzHRLzq7UuVN8nchNDGmqQErtLJALvf7kWucVgN/u9VqrteEh6ZL7/eZ9G
AE3Dot2I+TWBgQ7D1feD9TGj7riY2/m3hNMMG5KeiyifHWDIo3tVqwO4WgaBU25h
L2AAQKtS0aBMp034cN1nFUxRAw0cFZPQmE52kSNaIbzQpy+3jR6o43IvLuTOVA4j
2FlGr9wGLk/Rom/mt2gGY6agiTnfkIV32Muesqwr0zr55ktbQ64xcIlXlXVpIL4j
ysbj8f2dBBR/4J/UrNTtzjEofTsDyO4+2NdXS3HuWTw3X74UFyY=
=EP3F
-----END PGP SIGNATURE-----

View File

@ -3,14 +3,20 @@
%define libname libnmstate
Name: nmstate
Version: 0.2.0
Release: 2%{?dist}
Version: 0.3.2
Release: 6%{?dist}
Summary: Declarative network manager API
License: LGPLv2+
URL: https://github.com/%{srcname}/%{srcname}
Source0: %{url}/releases/download/v%{version}/%{srcname}-%{version}.tar.gz
Source1: %{url}/releases/download/v%{version}/%{srcname}-%{version}.tar.gz.asc
Source2: gpgkey-F7910D93CA83D77348595C0E899014C0463C12BB.gpg
Source2: https://www.nmstate.io/nmstate.gpg
Patch1: BZ_1850698-Fix-remove-dns-config.patch
Patch2: BZ_1788763_improve_vlan_mtu_error_message.patch
Patch3: BZ_1816612_canonicalize-IP-address.patch
Patch4: BZ_1806474-sort-pretty-state-with-priority.patch
Patch5: BZ_1820009_remove_duplicate_call_of_is_ovs_running.patch
Patch6: BZ_1820009_only_reapply_if_activated.patch
BuildArch: noarch
BuildRequires: python3-devel
BuildRequires: python3-setuptools
@ -27,21 +33,33 @@ provider support on the southbound.
%package -n python3-%{libname}
Summary: nmstate Python 3 API library
Requires: NetworkManager-libnm
Requires: NetworkManager-libnm >= 1:1.22.16
# Use Recommends for NetworkManager because only access to NM DBus is required,
# but NM could be running on a different host
Recommends: NetworkManager
# Avoid automatically generated profiles
Recommends: NetworkManager-config-server
# Use Suggests for NetworkManager-ovs since it is only required for OVS support
# Use Suggests for NetworkManager-ovs and NetworkManager-team since it is only
# required for OVS and team support
Suggests: NetworkManager-ovs
Suggests: NetworkManager-team
%package -n nmstate-plugin-ovsdb
Summary: nmstate plugin for OVS database manipulation
Requires: python3-%{libname} = %{?epoch:%{epoch}:}%{version}-%{release}
# The python-openvswitch rpm pacakge is not in the same repo with nmstate,
# hence state it as Recommends, no requires.
Recommends: python3dist(ovs)
%description -n python3-%{libname}
This package contains the Python 3 library for nmstate.
%description -n nmstate-plugin-ovsdb
This package contains the nmstate plugin for OVS database manipulation.
%prep
gpgv2 --keyring %{SOURCE2} %{SOURCE1} %{SOURCE0}
gpg2 --import --import-options import-export,import-minimal %{SOURCE2} > ./gpgkey-mantainers.gpg
gpgv2 --keyring ./gpgkey-mantainers.gpg %{SOURCE1} %{SOURCE0}
%autosetup -p1
%build
@ -61,8 +79,83 @@ gpgv2 --keyring %{SOURCE2} %{SOURCE1} %{SOURCE0}
%license LICENSE
%{python3_sitelib}/%{libname}
%{python3_sitelib}/%{srcname}-*.egg-info/
%exclude %{python3_sitelib}/%{libname}/plugins/nmstate_plugin_*
%exclude %{python3_sitelib}/%{libname}/plugins/__pycache__/nmstate_plugin_*
%files -n nmstate-plugin-ovsdb
%{python3_sitelib}/%{libname}/plugins/nmstate_plugin_ovsdb*
%{python3_sitelib}/%{libname}/plugins/__pycache__/nmstate_plugin_ovsdb*
%changelog
* Mon Jun 29 2020 Gris Ge <fge@redhat.com> - 0.3.2-6
- Improve performance by remove unneeded calls. RHBZ#1820009
* Mon Jun 29 2020 Gris Ge <fge@redhat.com> - 0.3.2-5
- Sort the pretty state with priority. RHBZ#1806474
* Mon Jun 29 2020 Gris Ge <fge@redhat.com> - 0.3.2-4
- Canonicalize IP address. RHBZ#1816612
* Mon Jun 29 2020 Gris Ge <fge@redhat.com> - 0.3.2-3
- Improve VLAN MTU error message. RHBZ#1788763
* Mon Jun 29 2020 Gris Ge <fge@redhat.com> - 0.3.2-2
- Fix bug 1850698
* Mon Jun 15 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.3.2-1
- Upgrade to 0.3.2
- Sync. up with upstream spec file
* Thu Jun 11 2020 Gris Ge <fge@redhat.com> - 0.3.1-1
- Upgrade to 0.3.1
* Wed May 13 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.3.0-1
- Upgrade to 0.3.0
- Sync. up with upstream spec file.
- Update signature verification.
* Tue Mar 31 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.2.9-1
- Upgrade to 0.2.9
* Wed Mar 25 2020 Gris Ge <fge@redhat.com> - 0.2.6-6
- Support 3+ DNS name server(IPv4 only or IPv6 only). RHBZ #1816043
* Fri Mar 20 2020 Gris Ge <fge@redhat.com> - 0.2.6-5
- Support static DNS with DHCP. RHBZ #1815112
* Thu Mar 12 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.2.6-4.8
- Fix bond mac and options regression. RHBZ #1809330
* Mon Mar 09 2020 Gris Ge <fge@redhat.com> - 0.2.6-3.8
- Fix change bond mode. RHBZ #1809330
* Mon Mar 02 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.2.6-2.7
- Fix cmd stuck when trying to create ovs-bond. RHBZ #1806249.
* Tue Feb 25 2020 Gris Ge <fge@redhat.com> - 0.2.6-1
- Upgrade to 0.2.6
* Thu Feb 20 2020 Gris Ge <fge@redhat.com> - 0.2.5-1
- Upgrade to 0.2.5
* Thu Feb 13 2020 Gris Ge <fge@redhat.com> - 0.2.4-2
- Fix failure when editing existing OVS interface. RHBZ #1786935
* Thu Feb 13 2020 Gris Ge <fge@redhat.com> - 0.2.4-1
- Upgrade to 0.2.4
* Wed Feb 05 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.2.3-1
- Upgrade to 0.2.3
* Tue Feb 04 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.2.2-3
- Fix the incorrect source
* Tue Feb 04 2020 Fernando Fernandez Mancera <ferferna@redhat.com> - 0.2.2-2
- Upgrade to 0.2.2
* Wed Jan 22 2020 Gris Ge <fge@redhat.com> - 0.2.0-3.1
- Fix the memeory leak of NM.Client. RHBZ #1784707
* Mon Dec 02 2019 Gris Ge <fge@redhat.com> - 0.2.0-2
- Fix the incorrect source tarbal.