def test_edit_slave(self): desired_state = state.State({ Interface.KEY: [ _create_iface_state( IFACE0, InterfaceType.UNKNOWN, extra={"fookey": "fooval"}, ), ] }) current_state = state.State({ Interface.KEY: [ _create_bridge_state(BRIDGE0, (IFACE0, IFACE1)), _create_iface_state(IFACE0, InterfaceType.UNKNOWN), _create_iface_state(IFACE1, InterfaceType.UNKNOWN), ] }) extra_iface0_state = _create_metadata_state(BRIDGE0, IFACE0) extra_iface0_state["fookey"] = "fooval" expected_dstate = state.State({ Interface.KEY: [ _create_iface_state( IFACE0, InterfaceType.UNKNOWN, extra=extra_iface0_state, ), ] }) expected_cstate = state.State(current_state.state) metadata.generate_ifaces_metadata(desired_state, current_state) assert state.State(desired_state.state) == expected_dstate assert current_state == expected_cstate
def test_creation_with_existing_ports(self): desired_state = state.State( {Interface.KEY: [_create_bridge_state(BRIDGE0, (IFACE0, IFACE1))]}) current_state = state.State({ Interface.KEY: [ _create_iface_state(IFACE0, InterfaceType.UNKNOWN, InterfaceState.UP), _create_iface_state(IFACE1, InterfaceType.UNKNOWN, InterfaceState.UP), ] }) expected_dstate = state.State({ Interface.KEY: [ _create_bridge_state(BRIDGE0, (IFACE0, IFACE1)), _create_iface_state( IFACE0, ifstate=InterfaceState.UP, extra=_create_metadata_state(BRIDGE0, IFACE0), ), _create_iface_state( IFACE1, ifstate=InterfaceState.UP, extra=_create_metadata_state(BRIDGE0, IFACE1), ), ] }) expected_cstate = state.State(current_state.state) metadata.generate_ifaces_metadata(desired_state, current_state) assert state.State(desired_state.state) == expected_dstate assert current_state == expected_cstate
def test_edit_bridge_with_unmanaged_slave(self): desired_state = state.State( {Interface.KEY: [_create_bridge_state(BRIDGE0, (IFACE0, ))]}) current_state = state.State({ Interface.KEY: [ _create_bridge_state(BRIDGE0, (IFACE0, IFACE1)), _create_iface_state(IFACE0, InterfaceType.ETHERNET, InterfaceState.UP), _create_iface_state(IFACE1, InterfaceType.UNKNOWN, InterfaceState.UP), ] }) expected_dstate = state.State({ Interface.KEY: [ _create_bridge_state(BRIDGE0, (IFACE0, )), _create_iface_state( IFACE0, ifstate=InterfaceState.UP, extra=_create_metadata_state(BRIDGE0, IFACE0), ), ] }) expected_cstate = state.State(current_state.state) metadata.generate_ifaces_metadata(desired_state, current_state) assert state.State(desired_state.state) == expected_dstate assert current_state == expected_cstate
def test_dns_gen_metadata_static_gateway_ipv6_name_server_after_ipv4( nm_dns_mock, ): dns_config = { DNS.SERVER: ["8.8.8.8", "2001:4860:4860::8888"], DNS.SEARCH: ["example.org", "example.com"], } desired_state = state.State({ Interface.KEY: _get_test_iface_states(), Route.KEY: { Route.CONFIG: _gen_default_gateway_route(TEST_IFACE1) }, DNS.KEY: { DNS.CONFIG: dns_config }, }) current_state = state.State({}) metadata.generate_ifaces_metadata(desired_state, current_state) ipv4_dns_config = { DNS.SERVER: ["8.8.8.8"], DNS.SEARCH: ["example.org", "example.com"], nm_dns.DNS_METADATA_PRIORITY: nm_dns.DNS_PRIORITY_STATIC_BASE, } ipv6_dns_config = { DNS.SERVER: ["2001:4860:4860::8888"], DNS.SEARCH: [], nm_dns.DNS_METADATA_PRIORITY: nm_dns.DNS_PRIORITY_STATIC_BASE + 1, } iface_state = desired_state.interfaces[TEST_IFACE1] assert ipv4_dns_config == iface_state[Interface.IPV4][nm_dns.DNS_METADATA] assert ipv6_dns_config == iface_state[Interface.IPV6][nm_dns.DNS_METADATA]
def test_bond_creation_with_existing_slaves(self): desired_state = state.State({ Interface.KEY: [create_bond_state_dict(BOND_NAME, ['eth0', 'eth1'])] }) current_state = state.State({ Interface.KEY: [ { 'name': 'eth0', 'type': 'unknown' }, { 'name': 'eth1', 'type': 'unknown' }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces['eth0'] = {'name': 'eth0', 'state': 'up'} expected_dstate.interfaces['eth0'][metadata.MASTER] = BOND_NAME expected_dstate.interfaces['eth0'][metadata.MASTER_TYPE] = TYPE_BOND expected_dstate.interfaces['eth1'] = {'name': 'eth1', 'state': 'up'} expected_dstate.interfaces['eth1'][metadata.MASTER] = BOND_NAME expected_dstate.interfaces['eth1'][metadata.MASTER_TYPE] = TYPE_BOND metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_edit_slave(self): desired_state = state.State({ Interface.KEY: [{ 'name': 'eth0', 'type': 'unknown', 'fookey': 'fooval' }] }) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ['eth0', 'eth1']), { 'name': 'eth0', 'type': 'unknown' }, { 'name': 'eth1', 'type': 'unknown' }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces['eth0'][metadata.MASTER] = BOND_NAME expected_dstate.interfaces['eth0'][metadata.MASTER_TYPE] = TYPE_BOND metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_bond_creation_with_new_slaves(self): desired_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { Interface.NAME: "eth0", Interface.TYPE: InterfaceType.UNKNOWN, }, { Interface.NAME: "eth1", Interface.TYPE: InterfaceType.UNKNOWN, }, ] }) current_state = state.State({}) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces["eth0"][metadata.MASTER] = BOND_NAME expected_dstate.interfaces["eth1"][metadata.MASTER] = BOND_NAME expected_dstate.interfaces["eth0"][metadata.MASTER_TYPE] = TYPE_BOND expected_dstate.interfaces["eth1"][metadata.MASTER_TYPE] = TYPE_BOND metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state.state == expected_dstate.state assert current_state == expected_cstate
def test_bond_editing_option(self): desired_state = state.State({ Interface.KEY: [{ 'name': BOND_NAME, 'type': TYPE_BOND, 'state': 'down' }] }) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ['eth0', 'eth1']), { 'name': 'eth0', 'type': 'unknown' }, { 'name': 'eth1', 'type': 'unknown' }, ] }) expected_desired_state = state.State(desired_state.state) expected_current_state = state.State(current_state.state) metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_desired_state assert current_state == expected_current_state
def test_bond_editing_option(self): desired_state = state.State({ Interface.KEY: [{ "name": BOND_NAME, "type": TYPE_BOND, "state": "down" }] }) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { "name": "eth0", "type": "unknown" }, { "name": "eth1", "type": "unknown" }, ] }) expected_desired_state = state.State(desired_state.state) expected_current_state = state.State(current_state.state) metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_desired_state assert current_state == expected_current_state
def test_bond_reusing_slave_used_by_existing_bond(self): BOND2_NAME = "bond88" desired_state = state.State( {Interface.KEY: [create_bond_state_dict(BOND2_NAME, ["eth0"])]}) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { Interface.NAME: "eth0", Interface.STATE: InterfaceState.UP, Interface.TYPE: InterfaceType.UNKNOWN, }, { Interface.NAME: "eth1", Interface.STATE: InterfaceState.UP, Interface.TYPE: InterfaceType.UNKNOWN, }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces["eth0"] = { Interface.NAME: "eth0", Interface.STATE: InterfaceState.UP, } expected_dstate.interfaces["eth0"][metadata.MASTER] = BOND2_NAME expected_dstate.interfaces["eth0"][metadata.MASTER_TYPE] = TYPE_BOND metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_with_empty_states(self): desired_state = state.State({}) current_state = state.State({}) metadata.generate_ifaces_metadata(desired_state, current_state) assert {} == desired_state.interfaces
def test_bond_editing_option(self): desired_state = state.State({ Interface.KEY: [{ Interface.NAME: BOND_NAME, Interface.TYPE: TYPE_BOND, Interface.STATE: InterfaceState.DOWN, }] }) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { Interface.NAME: "eth0", Interface.TYPE: InterfaceType.UNKNOWN, }, { Interface.NAME: "eth1", Interface.TYPE: InterfaceType.UNKNOWN, }, ] }) expected_desired_state = state.State(desired_state.state) expected_current_state = state.State(current_state.state) metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_desired_state assert current_state == expected_current_state
def test_bond_removing_slaves(self): desired_state = state.State( {Interface.KEY: [create_bond_state_dict(BOND_NAME, ["eth0"])]}) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { Interface.NAME: "eth0", Interface.STATE: InterfaceState.UP, Interface.TYPE: InterfaceType.ETHERNET, }, { Interface.NAME: "eth1", Interface.STATE: InterfaceState.UP, Interface.TYPE: InterfaceType.ETHERNET, }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces["eth0"] = { Interface.NAME: "eth0", Interface.STATE: InterfaceState.UP, } expected_dstate.interfaces["eth0"][metadata.MASTER] = BOND_NAME expected_dstate.interfaces["eth0"][metadata.MASTER_TYPE] = TYPE_BOND expected_dstate.interfaces["eth1"] = {Interface.NAME: "eth1"} metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_dns_metadata_interface_not_included_in_desire(nm_dns_mock): dns_config = { DNS.SERVER: ['2001:4860:4860::8888', '8.8.8.8'], DNS.SEARCH: ['example.org', 'example.com'], } desired_state = state.State({ Interface.KEY: [], Route.KEY: { Route.CONFIG: _gen_default_gateway_route(TEST_IFACE1) }, DNS.KEY: { DNS.CONFIG: dns_config }, }) current_state = state.State({ Interface.KEY: _get_test_iface_states(), Route.KEY: { Route.CONFIG: _gen_default_gateway_route(TEST_IFACE1) }, }) metadata.generate_ifaces_metadata(desired_state, current_state) iface_state = desired_state.interfaces[TEST_IFACE1] ipv4_dns_config = { DNS.SERVER: ['8.8.8.8'], DNS.SEARCH: [], nm_dns.DNS_METADATA_PRIORITY: nm_dns.DNS_PRIORITY_STATIC_BASE + 1, } ipv6_dns_config = { DNS.SERVER: ['2001:4860:4860::8888'], DNS.SEARCH: ['example.org', 'example.com'], nm_dns.DNS_METADATA_PRIORITY: nm_dns.DNS_PRIORITY_STATIC_BASE, } assert ipv4_dns_config == iface_state[Interface.IPV4][nm_dns.DNS_METADATA] assert ipv6_dns_config == iface_state[Interface.IPV6][nm_dns.DNS_METADATA]
def test_two_routes_with_matching_interfaces(self): route0 = self._create_route0() route1 = self._create_route1() desired_state = state.State({ Interface.KEY: [_create_interface_state('eth1')], Route.KEY: { Route.CONFIG: [route0.to_dict(), route1.to_dict()] }, }) current_state = state.State({ Interface.KEY: [_create_interface_state('eth2')], Route.KEY: { Route.CONFIG: [] }, }) metadata.generate_ifaces_metadata(desired_state, current_state) iface0_state = desired_state.interfaces['eth1'] iface1_state = desired_state.interfaces['eth2'] route0_metadata, = iface0_state[Interface.IPV4][metadata.ROUTES] route1_metadata, = iface1_state[Interface.IPV6][metadata.ROUTES] assert route0.to_dict() == route0_metadata assert route1.to_dict() == route1_metadata
def test_bond_reusing_slave_used_by_existing_bond(self): BOND2_NAME = "bond88" desired_state = state.State( {Interface.KEY: [create_bond_state_dict(BOND2_NAME, ["eth0"])]}) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { "name": "eth0", "state": "up", "type": "unknown" }, { "name": "eth1", "state": "up", "type": "unknown" }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces["eth0"] = {"name": "eth0", "state": "up"} expected_dstate.interfaces["eth0"][metadata.MASTER] = BOND2_NAME expected_dstate.interfaces["eth0"][metadata.MASTER_TYPE] = TYPE_BOND metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_edit_slave(self): desired_state = state.State({ Interface.KEY: [{ "name": "eth0", "type": "unknown", "fookey": "fooval" }] }) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { "name": "eth0", "type": "unknown" }, { "name": "eth1", "type": "unknown" }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces["eth0"][metadata.MASTER] = BOND_NAME expected_dstate.interfaces["eth0"][metadata.MASTER_TYPE] = TYPE_BOND metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_bond_removing_slaves(self): desired_state = state.State( {Interface.KEY: [create_bond_state_dict(BOND_NAME, ["eth0"])]}) current_state = state.State({ Interface.KEY: [ create_bond_state_dict(BOND_NAME, ["eth0", "eth1"]), { "name": "eth0", "state": "up", "type": "ethernet" }, { "name": "eth1", "state": "up", "type": "ethernet" }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces["eth0"] = {"name": "eth0", "state": "up"} expected_dstate.interfaces["eth0"][metadata.MASTER] = BOND_NAME expected_dstate.interfaces["eth0"][metadata.MASTER_TYPE] = TYPE_BOND expected_dstate.interfaces["eth1"] = {"name": "eth1"} metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def _apply_ifaces_state( desired_state, verify_change, commit, rollback_timeout ): current_state = state.State(netinfo.show()) desired_state.sanitize_ethernet(current_state) desired_state.sanitize_dynamic_ip() desired_state.merge_routes(current_state) desired_state.merge_dns(current_state) metadata.generate_ifaces_metadata(desired_state, current_state) validator.validate_interfaces_state(desired_state, current_state) validator.validate_routes(desired_state, current_state) new_interfaces = _list_new_interfaces(desired_state, current_state) try: with nm.checkpoint.CheckPoint( autodestroy=commit, timeout=rollback_timeout ) as checkpoint: with _setup_providers(): _add_interfaces(new_interfaces, desired_state) state2edit = _create_editable_desired_state( desired_state, current_state, new_interfaces ) _edit_interfaces(state2edit) if verify_change: _verify_change(desired_state) if not commit: return checkpoint except nm.checkpoint.NMCheckPointPermissionError: raise NmstatePermissionError('Error creating a check point') except nm.checkpoint.NMCheckPointCreationError: raise NmstateConflictError('Error creating a check point')
def test_ovs_reusing_slave_used_by_existing_bridge(self): OVS2_NAME = 'ovs-br88' desired_state = state.State({ Interface.KEY: [{ 'name': OVS2_NAME, 'type': TYPE_OVS_BR, 'state': 'up', 'bridge': { 'port': [{ 'name': 'eth0', 'type': OBPortType.SYSTEM }] }, }] }) current_state = state.State({ Interface.KEY: [ { 'name': OVS_NAME, 'type': TYPE_OVS_BR, 'state': 'up', 'bridge': { 'port': [ { 'name': 'eth0', 'type': OBPortType.SYSTEM }, { 'name': 'eth1', 'type': OBPortType.SYSTEM }, ] }, }, { 'name': 'eth0', 'state': 'up', 'type': 'unknown' }, { 'name': 'eth1', 'state': 'up', 'type': 'unknown' }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces['eth0'] = {'name': 'eth0', 'state': 'up'} expected_dstate.interfaces['eth0'][metadata.MASTER] = OVS2_NAME expected_dstate.interfaces['eth0'][metadata.MASTER_TYPE] = TYPE_OVS_BR expected_dstate.interfaces['eth0'][ metadata.BRPORT_OPTIONS] = desired_state.interfaces[OVS2_NAME][ 'bridge']['port'][0] metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_empty_states(self): desired_state = state.State({}) current_state = state.State({}) metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state.state == {Interface.KEY: []} assert current_state.state == {Interface.KEY: []}
def test_ovs_adding_slaves(self, bonded): if bonded: ports = [_create_lag_port_state((PORT0, PORT1))] else: ports = [ { OVSBridge.Port.NAME: PORT0 }, { OVSBridge.Port.NAME: PORT1 }, ] ports_state = {OVSBridge.PORT_SUBTREE: ports} desired_state = state.State({ Interface.KEY: [ { Interface.NAME: OVS_NAME, Interface.TYPE: TYPE_OVS_BR, Interface.STATE: InterfaceState.UP, OVSBridge.CONFIG_SUBTREE: ports_state, }, { Interface.NAME: PORT1, Interface.STATE: InterfaceState.UP, Interface.TYPE: InterfaceType.UNKNOWN, }, ] }) current_state = state.State({ Interface.KEY: [{ Interface.NAME: PORT0, Interface.STATE: InterfaceState.UP, Interface.TYPE: InterfaceType.UNKNOWN, }] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces[PORT0] = { Interface.NAME: PORT0, Interface.STATE: InterfaceState.UP, } expected_dstate.interfaces[PORT0][metadata.MASTER] = OVS_NAME expected_dstate.interfaces[PORT1][metadata.MASTER] = OVS_NAME expected_dstate.interfaces[PORT0][metadata.MASTER_TYPE] = TYPE_OVS_BR expected_dstate.interfaces[PORT1][metadata.MASTER_TYPE] = TYPE_OVS_BR desired_p0 = _get_bridge_port_state(desired_state, OVS_NAME, 0) expected_dstate.interfaces[PORT0][metadata.BRPORT_OPTIONS] = desired_p0 if bonded: desired_p1 = desired_p0 else: desired_p1 = _get_bridge_port_state(desired_state, OVS_NAME, 1) expected_dstate.interfaces[PORT1][metadata.BRPORT_OPTIONS] = desired_p1 metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_ovs_reusing_slave_used_by_existing_bridge(self): OVS2_NAME = "ovs-br88" desired_state = state.State({ Interface.KEY: [{ "name": OVS2_NAME, "type": TYPE_OVS_BR, "state": "up", "bridge": { "port": [{ "name": "eth0" }] }, }] }) current_state = state.State({ Interface.KEY: [ { "name": OVS_NAME, "type": TYPE_OVS_BR, "state": "up", "bridge": { "port": [{ "name": "eth0" }, { "name": "eth1" }] }, }, { "name": "eth0", "state": "up", "type": "unknown" }, { "name": "eth1", "state": "up", "type": "unknown" }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces["eth0"] = {"name": "eth0", "state": "up"} expected_dstate.interfaces["eth0"][metadata.MASTER] = OVS2_NAME expected_dstate.interfaces["eth0"][metadata.MASTER_TYPE] = TYPE_OVS_BR expected_dstate.interfaces["eth0"][ metadata.BRPORT_OPTIONS] = desired_state.interfaces[OVS2_NAME][ "bridge"]["port"][0] metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate
def test_dns_metadata_empty(): desired_state = state.State({ Interface.KEY: _get_test_iface_states(), Route.KEY: {}, DNS.KEY: {} }) current_state = state.State({}) metadata.generate_ifaces_metadata(desired_state, current_state) assert (nm_dns.DNS_METADATA not in desired_state.interfaces[TEST_IFACE1][Interface.IPV4]) assert (nm_dns.DNS_METADATA not in desired_state.interfaces[TEST_IFACE1][Interface.IPV6])
def test_route_with_no_desired_or_current_interfaces(self): route0 = self._create_route0() desired_state = state.State({ Interface.KEY: [], Route.KEY: { Route.CONFIG: [route0.to_dict()] } }) current_state = state.State({}) metadata.generate_ifaces_metadata(desired_state, current_state) assert {} == desired_state.interfaces
def _apply_ifaces_state(desired_state, verify_change, commit, rollback_timeout): original_desired_state = copy.deepcopy(desired_state) current_state = state.State(netinfo.show()) desired_state.sanitize_ethernet(current_state) desired_state.sanitize_dynamic_ip() desired_state.merge_routes(current_state) desired_state.merge_dns(current_state) desired_state.merge_route_rules(current_state) desired_state.remove_unknown_interfaces() desired_state.complement_master_interfaces_removal(current_state) metadata.generate_ifaces_metadata(desired_state, current_state) validator.validate_interfaces_state(original_desired_state, current_state) validator.validate_routes(desired_state, current_state) try: with nm.checkpoint.CheckPoint(autodestroy=commit, timeout=rollback_timeout) as checkpoint: with _setup_providers(): state2edit = state.State(desired_state.state) state2edit.merge_interfaces(current_state) nm.applier.apply_changes( list(state2edit.interfaces.values()), original_desired_state, ) verified = False if verify_change: for _ in range(VERIFY_RETRY_TIMEOUT): try: _verify_change(desired_state) verified = True break except NmstateVerificationError: time.sleep(VERIFY_RETRY_INTERNAL) if not verified: _verify_change(desired_state) if not commit: return checkpoint except nm.checkpoint.NMCheckPointPermissionError: raise NmstatePermissionError("Error creating a check point") except nm.checkpoint.NMCheckPointCreationError: raise NmstateConflictError("Error creating a check point") except NmstateError: # Assume rollback occurred. # Checkpoint rollback is async, there is a need to wait for it to # finish before proceeding with other actions. time.sleep(5) raise
def test_rule_with_no_route(self): rule0 = self._create_rule0() desired_state = state.State({ Route.KEY: { Route.CONFIG: [] }, RouteRule.KEY: { RouteRule.CONFIG: [rule0.to_dict()] }, }) current_state = state.State({}) with pytest.raises(NmstateValueError): metadata.generate_ifaces_metadata(desired_state, current_state)
def test_rule_with_no_matching_route_table(self): rule0 = self._create_rule0() route = _create_route( "198.51.100.0/24", "192.0.2.1", "eth1", TestRouteRuleMetadata.TEST_ROUTE_TABLE + 1, 103, ) desired_state = state.State({ Interface.KEY: [_create_interface_state("eth1")], Route.KEY: { Route.CONFIG: [route.to_dict()] }, RouteRule.KEY: { RouteRule.CONFIG: [rule0.to_dict()] }, }) current_state = state.State({ Interface.KEY: [_create_interface_state("eth1")], Route.KEY: { Route.CONFIG: [route.to_dict()] }, }) rule0 = self._create_rule0() route = _create_route( "198.51.100.0/24", "192.0.2.1", "eth1", TestRouteRuleMetadata.TEST_ROUTE_TABLE + 1, 103, ) desired_state = state.State({ Interface.KEY: [_create_interface_state("eth1")], Route.KEY: { Route.CONFIG: [route.to_dict()] }, RouteRule.KEY: { RouteRule.CONFIG: [rule0.to_dict()] }, }) current_state = state.State({ Interface.KEY: [_create_interface_state("eth1")], Route.KEY: { Route.CONFIG: [route.to_dict()] }, }) with pytest.raises(NmstateValueError): metadata.generate_ifaces_metadata(desired_state, current_state)
def _apply_ifaces_state( desired_state, verify_change, commit, rollback_timeout ): current_state = state.State(netinfo.show()) desired_state.sanitize_ethernet(current_state) desired_state.sanitize_dynamic_ip() desired_state.merge_routes(current_state) desired_state.merge_dns(current_state) metadata.generate_ifaces_metadata(desired_state, current_state) validator.validate_interfaces_state(desired_state, current_state) validator.validate_routes(desired_state, current_state) new_interfaces = _list_new_interfaces(desired_state, current_state) try: with nm.checkpoint.CheckPoint( autodestroy=commit, timeout=rollback_timeout ) as checkpoint: with _setup_providers(): ifaces2add, ifaces_add_configs = _add_interfaces( new_interfaces, desired_state ) state2edit = _create_editable_desired_state( desired_state, current_state, new_interfaces ) ifaces2edit, ifaces_edit_configs = _edit_interfaces(state2edit) nm.applier.set_ifaces_admin_state( ifaces2add + ifaces2edit, con_profiles=ifaces_add_configs + ifaces_edit_configs, ) _disable_ipv6(desired_state) if verify_change: _verify_change(desired_state) if not commit: return checkpoint except nm.checkpoint.NMCheckPointPermissionError: raise NmstatePermissionError('Error creating a check point') except nm.checkpoint.NMCheckPointCreationError: raise NmstateConflictError('Error creating a check point') except NmstateError: # Assume rollback occured, revert IPv6 stack state. # Checkpoint rollback is async, there is a need to wait for it to # finish before proceeding with other actions. # TODO: https://nmstate.atlassian.net/browse/NMSTATE-103 time.sleep(5) _disable_ipv6(current_state) raise
def test_ovs_edit_slave(self): desired_state = state.State({ Interface.KEY: [{ 'name': 'eth0', 'type': 'unknown', 'fookey': 'fooval' }] }) current_state = state.State({ Interface.KEY: [ { 'name': OVS_NAME, 'type': TYPE_OVS_BR, 'state': 'up', 'bridge': { 'port': [ { 'name': 'eth0', 'type': OBPortType.SYSTEM }, { 'name': 'eth1', 'type': OBPortType.SYSTEM }, ] }, }, { 'name': 'eth0', 'type': 'unknown' }, { 'name': 'eth1', 'type': 'unknown' }, ] }) expected_dstate = state.State(desired_state.state) expected_cstate = state.State(current_state.state) expected_dstate.interfaces['eth0'][metadata.MASTER] = OVS_NAME expected_dstate.interfaces['eth0'][metadata.MASTER_TYPE] = TYPE_OVS_BR expected_dstate.interfaces['eth0'][ metadata.BRPORT_OPTIONS] = current_state.interfaces[OVS_NAME][ 'bridge']['port'][0] metadata.generate_ifaces_metadata(desired_state, current_state) assert desired_state == expected_dstate assert current_state == expected_cstate