def update_nvset(nvset_element, nvpair_dict): """ Add, remove or update nvpairs according to nvpair_dict into nvset_element If the resulting nvset is empty, it will be removed. etree nvset_element -- container where nvpairs are set dict nvpair_dict -- contains source for nvpair children """ for name, value in sorted(nvpair_dict.items()): set_nvpair_in_nvset(nvset_element, name, value) remove_when_pointless(nvset_element)
def update(id_provider, bundle_el, container_options, network_options, port_map_add, port_map_remove, storage_map_add, storage_map_remove, meta_attributes): """ Modify an existing bundle (does not touch encapsulated resources) IdProvider id_provider -- elements' ids generator and uniqueness checker etree bundle_el -- the bundle to be updated dict container_options -- container options to modify dict network_options -- network options to modify list of dict port_map_add -- list of port mapping options to add list of string port_map_remove -- list of port mapping ids to remove list of dict storage_map_add -- list of storage mapping options to add list of string storage_map_remove -- list of storage mapping ids to remove dict meta_attributes -- meta attributes to update """ bundle_id = bundle_el.get("id") update_attributes_remove_empty(_get_container_element(bundle_el), container_options) network_element = get_sub_element(bundle_el, "network") if network_options: update_attributes_remove_empty(network_element, network_options) # It's crucial to remove port maps prior to appending new ones: If we are # adding a port map which in any way conflicts with another one and that # another one is being removed in the very same command, the removal must # be done first, otherwise the conflict would manifest itself (and then # possibly the old mapping would be removed) if port_map_remove: _remove_map_elements(network_element.findall("port-mapping"), port_map_remove) for port_map_options in port_map_add: _append_port_map(network_element, id_provider, bundle_id, port_map_options) storage_element = get_sub_element(bundle_el, "storage") # See the comment above about removing port maps prior to adding new ones. if storage_map_remove: _remove_map_elements(storage_element.findall("storage-mapping"), storage_map_remove) for storage_map_options in storage_map_add: _append_storage_map(storage_element, id_provider, bundle_id, storage_map_options) if meta_attributes: arrange_first_meta_attributes(bundle_el, meta_attributes) # remove empty elements with no attributes # meta attributes are handled in their own function remove_when_pointless(network_element) remove_when_pointless(storage_element)
def assert_count_tags_after_call(self, count, tag, **kwargs): tree = etree.fromstring(""" <root> <empty /> <with-subelement> <subelement/> </with-subelement> <with-attr some="attribute"/> <with-only-id id="1"/> </root> """) xpath = ".//{0}".format(tag) lib.remove_when_pointless(tree.find(xpath), **kwargs) self.assertEqual(len(tree.xpath(xpath)), count)
def unset_guest(resource_element): """ Unset resource as guest node. etree.Element resource_element """ guest_nvpair_list = resource_element.xpath( "./meta_attributes/nvpair[{0}]".format(" or ".join([ '@name="{0}"'.format(option) for option in (GUEST_OPTIONS + ["remote-node"]) ]))) for nvpair in guest_nvpair_list: meta_attributes = nvpair.getparent() meta_attributes.remove(nvpair) remove_when_pointless(meta_attributes)
def assert_count_tags_after_call(self, count, tag, **kwargs): tree = etree.fromstring( """ <root> <empty /> <with-subelement> <subelement/> </with-subelement> <with-attr some="attribute"/> <with-only-id id="1"/> </root> """ ) xpath = ".//{0}".format(tag) lib.remove_when_pointless(tree.find(xpath), **kwargs) self.assertEqual(len(tree.xpath(xpath)), count)
def remove_with_resource_set(constraint_section, ticket_key, resource_id): ref_element_list = constraint_section.xpath( './/rsc_ticket[@ticket="{0}"]/resource_set/resource_ref[@id="{1}"]'. format(ticket_key, resource_id)) for ref_element in ref_element_list: set_element = ref_element.getparent() set_element.remove(ref_element) if not len(set_element): ticket_element = set_element.getparent() ticket_element.remove(set_element) #We do not care about attributes since without an attribute "rsc" #they are pointless. Attribute "rsc" is mutually exclusive with #resource_set (see rng) so it cannot be in this ticket_element. remove_when_pointless(ticket_element, attribs_important=False) return len(ref_element_list) > 0
def _set_any_defaults(section_name, env, options): """ string section_name -- determine the section of defaults LibraryEnvironment env -- provides access to outside environment dict options -- are desired options with its values; when value is empty the option have to be removed """ env.report_processor.process(reports.defaults_can_be_overriden()) if not options: return defaults_section = sections.get(env.get_cib(), section_name) arrange_first_meta_attributes(defaults_section, options, new_id="{0}-options".format(section_name)) remove_when_pointless(defaults_section) env.push_cib()
def remove_with_resource_set(constraint_section, ticket_key, resource_id): ref_element_list = constraint_section.xpath( './/rsc_ticket[@ticket="{0}"]/resource_set/resource_ref[@id="{1}"]' .format(ticket_key, resource_id) ) for ref_element in ref_element_list: set_element = ref_element.getparent() set_element.remove(ref_element) # set_element is lxml element, therefore we have to use len() here # pylint: disable=len-as-condition if not len(set_element): ticket_element = set_element.getparent() ticket_element.remove(set_element) #We do not care about attributes since without an attribute "rsc" #they are pointless. Attribute "rsc" is mutually exclusive with #resource_set (see rng) so it cannot be in this ticket_element. remove_when_pointless(ticket_element, attribs_important=False) return len(ref_element_list) > 0
def remove_with_resource_set(constraint_section, ticket_key, resource_id): ref_element_list = constraint_section.xpath( ".//rsc_ticket[@ticket=$ticket]/resource_set/resource_ref[@id=$resource]", ticket=ticket_key, resource=resource_id, ) for ref_element in ref_element_list: set_element = ref_element.getparent() set_element.remove(ref_element) # set_element is lxml element, therefore we have to use len() here # pylint: disable=len-as-condition if not len(set_element): ticket_element = set_element.getparent() ticket_element.remove(set_element) # We do not care about attributes since without an attribute "rsc" # they are pointless. Attribute "rsc" is mutually exclusive with # resource_set (see rng) so it cannot be in this ticket_element. remove_when_pointless(ticket_element, attribs_important=False) return len(ref_element_list) > 0