Exemple #1
0
def update_node_instance_attrs(cib, node_name, attrs, state_nodes=None):
    """
    Update nvpairs in instance_attributes for a node specified by its name.

    Automatically creates instance_attributes element if needed. If the node has
    more than one instance_attributes element, the first one is modified. If the
    node is missing in the CIB, it is automatically created if its state is
    provided in state_nodes.

    etree cib -- cib
    string node_name -- name of the node to be updated
    dict attrs -- attrs to update, e.g. {'A': 'a', 'B': ''}
    iterable state_nodes -- optional list of node state objects
    """
    node_el = _ensure_node_exists(get_nodes(cib), node_name, state_nodes)
    # If no instance_attributes id is specified, crm_attribute modifies the
    # first one found. So we just mimic this behavior here.
    attrs_el = node_el.find("./instance_attributes")
    if attrs_el is None:
        attrs_el = etree.SubElement(
            node_el,
            "instance_attributes",
            id=find_unique_id(cib, "nodes-{0}".format(node_el.get("id")))
        )
    update_nvset(attrs_el, attrs)
Exemple #2
0
 def test_updates_nvset(self):
     nvset_element = etree.fromstring("""
         <instance_attributes id="iattrs">
             <nvpair id="iattrs-a" name="a" value="b"/>
             <nvpair id="iattrs-c" name="c" value="d"/>
             <nvpair id="iattrs-e" name="e" value="f"/>
         </instance_attributes>
     """)
     id_provider = IdProvider(nvset_element)
     nvpair.update_nvset(
         nvset_element,
         {
             "a": "B",
             "c": "",
             "g": "h",
         },
         id_provider
     )
     assert_xml_equal(
         """
         <instance_attributes id="iattrs">
             <nvpair id="iattrs-a" name="a" value="B"/>
             <nvpair id="iattrs-e" name="e" value="f"/>
             <nvpair id="iattrs-g" name="g" value="h"/>
         </instance_attributes>
         """,
         etree_to_str(nvset_element)
     )
Exemple #3
0
 def test_empty_value_has_no_effect(self):
     xml = """
         <instance_attributes id="iattrs">
             <nvpair id="1" name="a" value="b"/>
             <nvpair id="2" name="c" value="d"/>
             <nvpair id="3" name="e" value="f"/>
         </instance_attributes>
     """
     nvset_element = etree.fromstring(xml)
     nvpair.update_nvset(nvset_element, {})
     assert_xml_equal(xml, etree.tostring(nvset_element).decode())
Exemple #4
0
 def test_empty_value_has_no_effect(self):
     xml = """
         <instance_attributes id="iattrs">
             <nvpair id="iattrs-b" name="a" value="b"/>
             <nvpair id="iattrs-d" name="c" value="d"/>
             <nvpair id="iattrs-f" name="e" value="f"/>
         </instance_attributes>
     """
     nvset_element = etree.fromstring(xml)
     id_provider = IdProvider(nvset_element)
     nvpair.update_nvset(nvset_element, {}, id_provider)
     assert_xml_equal(xml, etree_to_str(nvset_element))
Exemple #5
0
 def test_remove_empty_nvset(self):
     xml_pre = """
         <resource>
             <instance_attributes id="iattrs">
                 <nvpair id="1" name="a" value="b"/>
             </instance_attributes>
         </resource>
     """
     xml_post = """
         <resource>
         </resource>
     """
     xml = etree.fromstring(xml_pre)
     nvset_element = xml.find("instance_attributes")
     nvpair.update_nvset(nvset_element, {"a": ""})
     assert_xml_equal(xml_post, etree_to_str(xml))
Exemple #6
0
 def test_new(self):
     root = etree.Element("root", id="root")
     assert_xml_equal(
         """
         <nvset id="root-nvset">
             <nvpair id="root-nvset-attr" name="attr" value="10"/>
             <nvpair id="root-nvset-new_one" name="new_one" value="20"/>
             <nvpair id="root-nvset-test" name="test" value="0"/>
         </nvset>
         """,
         etree.tostring(nvpair.update_nvset("nvset", root, root, {
             "attr": "10",
             "new_one": "20",
             "test": "0",
             "attr2": ""
         })).decode()
     )
     assert_xml_equal(
         """
         <root id="root">
             <nvset id="root-nvset">
                 <nvpair id="root-nvset-attr" name="attr" value="10"/>
                 <nvpair id="root-nvset-new_one" name="new_one" value="20"/>
                 <nvpair id="root-nvset-test" name="test" value="0"/>
             </nvset>
         </root>
         """,
         etree.tostring(root).decode()
     )
Exemple #7
0
 def test_keep_empty_nvset(self):
     xml_pre = """
         <resource>
             <instance_attributes id="iattrs">
                 <nvpair id="iattrs-a" name="a" value="b"/>
             </instance_attributes>
         </resource>
     """
     xml_post = """
         <resource>
             <instance_attributes id="iattrs" />
         </resource>
     """
     xml = etree.fromstring(xml_pre)
     nvset_element = xml.find("instance_attributes")
     id_provider = IdProvider(nvset_element)
     nvpair.update_nvset(nvset_element, {"a": ""}, id_provider)
     assert_xml_equal(xml_post, etree_to_str(xml))
Exemple #8
0
def update_meta_attributes(tree, element, attribute_dict):
    """
    Updates meta attributes of element. Returns updated meta attributes element.

    tree -- cib etree node
    element -- parent element of meta attributes
    attribute_dict -- dictionary of nvpairs
    """
    return update_nvset("meta_attributes", tree, element, attribute_dict)
Exemple #9
0
def update_instance_attributes(tree, element, attribute_dict):
    """
    Updates instance attributes of element. Returns updated instance
    attributes element.

    tree -- cib etree node
    element -- parent element of instance attributes
    attribute_dict -- dictionary of nvpairs
    """
    return update_nvset("instance_attributes", tree, element, attribute_dict)
Exemple #10
0
def update_node_instance_attrs(cib,
                               id_provider,
                               node_name,
                               attrs,
                               state_nodes=None):
    """
    Update nvpairs in instance_attributes for a node specified by its name.

    Automatically creates instance_attributes element if needed. If the node has
    more than one instance_attributes element, the first one is modified. If the
    node is missing in the CIB, it is automatically created if its state is
    provided in state_nodes.

    etree cib -- cib
    IdProvider id_provider -- elements' ids generator
    string node_name -- name of the node to be updated
    dict attrs -- attrs to update, e.g. {'A': 'a', 'B': ''}
    iterable state_nodes -- optional list of node state objects
    """
    # Do not ever remove the nvset element or the node element, even if they
    # are empty. There may be ACLs set in pacemaker which allow "write" for
    # nvpairs (adding, changing and removing) but not nvsets. In such a case,
    # removing the nvset would cause the whole change to be rejected by
    # pacemaker with a "permission denied" message.
    # https://bugzilla.redhat.com/show_bug.cgi?id=1642514

    if not attrs:
        return

    cib_nodes = get_nodes(cib)
    node_el = _ensure_node_exists(cib_nodes, node_name, state_nodes)
    # If no instance_attributes id is specified, crm_attribute modifies the
    # first one found. So we just mimic this behavior here.
    attrs_el = node_el.find("./instance_attributes")
    if attrs_el is None:
        attrs_el = etree.Element(
            "instance_attributes",
            id=id_provider.allocate_id("nodes-{0}".format(node_el.get("id"))),
        )
    update_nvset(attrs_el, attrs, id_provider)
    append_when_useful(node_el, attrs_el)
    append_when_useful(cib_nodes, node_el)
Exemple #11
0
 def test_updates_nvset(self):
     nvset_element = etree.fromstring(
         """
         <instance_attributes id="iattrs">
             <nvpair id="1" name="a" value="b"/>
             <nvpair id="2" name="c" value="d"/>
             <nvpair id="3" name="e" value="f"/>
         </instance_attributes>
     """
     )
     nvpair.update_nvset(nvset_element, {"a": "B", "c": "", "g": "h"})
     assert_xml_equal(
         """
         <instance_attributes id="iattrs">
             <nvpair id="1" name="a" value="B"/>
             <nvpair id="3" name="e" value="f"/>
             <nvpair id="4" name="g" value="h"/>
         </instance_attributes>
         """,
         etree.tostring(nvset_element).decode(),
     )
Exemple #12
0
 def test_updates_nvset(self):
     nvset_element = etree.fromstring("""
         <instance_attributes id="iattrs">
             <nvpair id="1" name="a" value="b"/>
             <nvpair id="2" name="c" value="d"/>
             <nvpair id="3" name="e" value="f"/>
         </instance_attributes>
     """)
     nvpair.update_nvset(nvset_element, {
         "a": "B",
         "c": "",
         "g": "h",
     })
     assert_xml_equal(
         """
         <instance_attributes id="iattrs">
             <nvpair id="1" name="a" value="B"/>
             <nvpair id="3" name="e" value="f"/>
             <nvpair id="4" name="g" value="h"/>
         </instance_attributes>
         """, etree_to_str(nvset_element))
Exemple #13
0
def update_node_instance_attrs(
    cib, id_provider, node_name, attrs, state_nodes=None
):
    """
    Update nvpairs in instance_attributes for a node specified by its name.

    Automatically creates instance_attributes element if needed. If the node has
    more than one instance_attributes element, the first one is modified. If the
    node is missing in the CIB, it is automatically created if its state is
    provided in state_nodes.

    etree cib -- cib
    IdProvider id_provider -- elements' ids generator
    string node_name -- name of the node to be updated
    dict attrs -- attrs to update, e.g. {'A': 'a', 'B': ''}
    iterable state_nodes -- optional list of node state objects
    """
    # Do not ever remove the nvset element or the node element, even if they
    # are empty. There may be ACLs set in pacemaker which allow "write" for
    # nvpairs (adding, changing and removing) but not nvsets. In such a case,
    # removing the nvset would cause the whole change to be rejected by
    # pacemaker with a "permission denied" message.
    # https://bugzilla.redhat.com/show_bug.cgi?id=1642514

    if not attrs:
        return

    cib_nodes = get_nodes(cib)
    node_el = _ensure_node_exists(cib_nodes, node_name, state_nodes)
    # If no instance_attributes id is specified, crm_attribute modifies the
    # first one found. So we just mimic this behavior here.
    attrs_el = node_el.find("./instance_attributes")
    if attrs_el is None:
        attrs_el = etree.Element(
            "instance_attributes",
            id=id_provider.allocate_id("nodes-{0}".format(node_el.get("id"))),
        )
    update_nvset(attrs_el, attrs, id_provider)
    append_when_useful(node_el, attrs_el)
    append_when_useful(cib_nodes, node_el)
Exemple #14
0
 def test_updates_nvset(self):
     nvset_element = etree.fromstring("""
         <instance_attributes id="iattrs">
             <nvpair id="iattrs-a" name="a" value="b"/>
             <nvpair id="iattrs-c" name="c" value="d"/>
             <nvpair id="iattrs-e" name="e" value="f"/>
         </instance_attributes>
     """)
     id_provider = IdProvider(nvset_element)
     nvpair.update_nvset(nvset_element, {
         "a": "B",
         "c": "",
         "g": "h",
     }, id_provider)
     assert_xml_equal(
         """
         <instance_attributes id="iattrs">
             <nvpair id="iattrs-a" name="a" value="B"/>
             <nvpair id="iattrs-e" name="e" value="f"/>
             <nvpair id="iattrs-g" name="g" value="h"/>
         </instance_attributes>
         """, etree_to_str(nvset_element))
Exemple #15
0
 def test_existing(self):
     self.assertEqual(
         self.nvset,
         nvpair.update_nvset("nvset", self.root, self.root, {
             "attr": "10",
             "new_one": "20",
             "test": "0",
             "attr2": ""
         })
     )
     assert_xml_equal(
         """
         <nvset id="nvset">
             <nvpair id="nvset-attr" name="attr" value="10"/>
             <notnvpair id="nvset-test" name="test" value="0"/>
             <nvpair id="nvset-new_one" name="new_one" value="20"/>
             <nvpair id="nvset-test-1" name="test" value="0"/>
         </nvset>
         """,
         etree.tostring(self.nvset).decode()
     )
Exemple #16
0
 def test_None(self):
     self.assertTrue(
         nvpair.update_nvset("nvset", self.root, self.root, None) is None
     )
Exemple #17
0
 def test_empty(self):
     self.assertTrue(
         nvpair.update_nvset("nvset", self.root, self.root, {}) is None
     )