示例#1
0
文件: rule.py 项目: deriamis/pcs
def dom_rule_add(dom_element, argv):
    options = {"id": None, "role": None, "score": None, "score-attribute": None}

    # parse options
    while argv:
        found = False
        option = argv.pop(0)
        for name in options:
            if option.startswith(name + "="):
                options[name] = option.split("=", 1)[1]
                found = True
                break
        if not found:
            argv.insert(0, option)
            break

    # validate options
    if options["score"] and options["score-attribute"]:
        utils.err("can not specify both score and score-attribute")
    if options["score"] and not utils.is_score(options["score"]):
        # preserving legacy behaviour
        print("Warning: invalid score '%s', setting score-attribute=pingd instead" % options["score"])
        options["score-attribute"] = "pingd"
        options["score"] = None
    if options["role"] and options["role"] not in ["master", "slave"]:
        utils.err("invalid role '%s', use 'master' or 'slave'" % options["role"])
    if options["id"]:
        id_valid, id_error = utils.validate_xml_id(options["id"], "rule id")
        if not id_valid:
            utils.err(id_error)
        if utils.does_id_exist(dom_element.ownerDocument, options["id"]):
            utils.err("id '%s' is already in use, please specify another one" % options["id"])

    # parse rule
    if not argv:
        utils.err("no rule expression was specified")
    try:
        dom_rule = CibBuilder().build(dom_element, RuleParser().parse(TokenPreprocessor().run(argv)), options["id"])
    except SyntaxError as e:
        utils.err("'%s' is not a valid rule expression: %s" % (" ".join(argv), e))
    except UnexpectedEndOfInput as e:
        utils.err("'%s' is not a valid rule expression: unexpected end of rule" % " ".join(argv))
    except (ParserException, CibBuilderException) as e:
        utils.err("'%s' is not a valid rule expression" % " ".join(argv))

    # add options into rule xml
    if not options["score"] and not options["score-attribute"]:
        options["score"] = "INFINITY"
    for name, value in options.iteritems():
        if name != "id" and value is not None:
            dom_rule.setAttribute(name, value)
    # score or score-attribute is required for the nested rules in order to have
    # valid CIB, pacemaker does not use the score of the nested rules
    for rule in dom_rule.getElementsByTagName("rule"):
        rule.setAttribute("score", "0")
    if dom_element.hasAttribute("score"):
        dom_element.removeAttribute("score")
    if dom_element.hasAttribute("node"):
        dom_element.removeAttribute("node")
    return dom_element
示例#2
0
def location_prefer(argv):
    rsc = argv.pop(0)
    prefer_option = argv.pop(0)

    if prefer_option == "prefers":
        prefer = True
    elif prefer_option == "avoids":
        prefer = False
    else:
        usage.constraint()
        sys.exit(1)


    for nodeconf in argv:
        nodeconf_a = nodeconf.split("=",1)
        if len(nodeconf_a) == 1:
            node = nodeconf_a[0]
            if prefer:
                score = "INFINITY"
            else:
                score = "-INFINITY"
        else:
            score = nodeconf_a[1]
            if not utils.is_score(score):
                utils.err("invalid score '%s', use integer or INFINITY or -INFINITY" % score)
            if not prefer:
                if score[0] == "-":
                    score = score[1:]
                else:
                    score = "-" + score
            node = nodeconf_a[0]
        location_add(["location-" +rsc+"-"+node+"-"+score,rsc,node,score])
示例#3
0
def location_add(argv, rm=False):
    if len(argv) != 4 and (rm == False or len(argv) < 1):
        usage.constraint()
        sys.exit(1)

    constraint_id = argv.pop(0)

    # If we're removing, we only care about the id
    if (rm == True):
        resource_name = ""
        node = ""
        score = ""
    else:
        id_valid, id_error = utils.validate_xml_id(constraint_id,
                                                   'constraint id')
        if not id_valid:
            utils.err(id_error)
        resource_name = argv.pop(0)
        node = argv.pop(0)
        score = argv.pop(0)
        resource_valid, resource_error = utils.validate_constraint_resource(
            utils.get_cib_dom(), resource_name)
        if not resource_valid:
            utils.err(resource_error)
        if not utils.is_score(score):
            utils.err(
                "invalid score '%s', use integer or INFINITY or -INFINITY" %
                score)

    # Verify current constraint doesn't already exist
    # If it does we replace it with the new constraint
    (dom, constraintsElement) = getCurrentConstraints()
    elementsToRemove = []

    # If the id matches, or the rsc & node match, then we replace/remove
    for rsc_loc in constraintsElement.getElementsByTagName('rsc_location'):
        if (constraint_id == rsc_loc.getAttribute("id")) or \
                (rsc_loc.getAttribute("rsc") == resource_name and \
                rsc_loc.getAttribute("node") == node and not rm):
            elementsToRemove.append(rsc_loc)

    for etr in elementsToRemove:
        constraintsElement.removeChild(etr)

    if (rm == True and len(elementsToRemove) == 0):
        utils.err("resource location id: " + constraint_id + " not found.")

    if (not rm):
        element = dom.createElement("rsc_location")
        element.setAttribute("id", constraint_id)
        element.setAttribute("rsc", resource_name)
        element.setAttribute("node", node)
        element.setAttribute("score", score)
        constraintsElement.appendChild(element)

    utils.replace_cib_configuration(dom)
示例#4
0
文件: rule.py 项目: ingted/pcs
def dom_rule_add(dom_element, options, rule_argv):
    # validate options
    if options.get("score") and options.get("score-attribute"):
        utils.err("can not specify both score and score-attribute")
    if options.get("score") and not utils.is_score(options["score"]):
        # preserving legacy behaviour
        print(
            "Warning: invalid score '%s', setting score-attribute=pingd instead"
            % options["score"])
        options["score-attribute"] = "pingd"
        options["score"] = None
    if options.get("role") and options["role"] not in ["master", "slave"]:
        utils.err("invalid role '%s', use 'master' or 'slave'" %
                  options["role"])
    if options.get("id"):
        id_valid, id_error = utils.validate_xml_id(options["id"], 'rule id')
        if not id_valid:
            utils.err(id_error)
        if utils.does_id_exist(dom_element.ownerDocument, options["id"]):
            utils.err("id '%s' is already in use, please specify another one" %
                      options["id"])

    # parse rule
    if not rule_argv:
        utils.err("no rule expression was specified")
    try:
        dom_rule = CibBuilder().build(
            dom_element,
            RuleParser().parse(TokenPreprocessor().run(rule_argv)),
            options.get("id"))
    except SyntaxError as e:
        utils.err("'%s' is not a valid rule expression: %s" %
                  (" ".join(rule_argv), e))
    except UnexpectedEndOfInput as e:
        utils.err(
            "'%s' is not a valid rule expression: unexpected end of rule" %
            " ".join(rule_argv))
    except (ParserException, CibBuilderException) as e:
        utils.err("'%s' is not a valid rule expression" % " ".join(rule_argv))

    # add options into rule xml
    if not options.get("score") and not options.get("score-attribute"):
        options["score"] = "INFINITY"
    for name, value in options.iteritems():
        if name != "id" and value is not None:
            dom_rule.setAttribute(name, value)
    # score or score-attribute is required for the nested rules in order to have
    # valid CIB, pacemaker does not use the score of the nested rules
    for rule in dom_rule.getElementsByTagName("rule"):
        rule.setAttribute("score", "0")
    if dom_element.hasAttribute("score"):
        dom_element.removeAttribute("score")
    if dom_element.hasAttribute("node"):
        dom_element.removeAttribute("node")
    return dom_element
示例#5
0
def location_add(argv,rm=False):
    if len(argv) != 4 and (rm == False or len(argv) < 1): 
        usage.constraint()
        sys.exit(1)

    constraint_id = argv.pop(0)

    # If we're removing, we only care about the id
    if (rm == True):
        resource_name = ""
        node = ""
        score = ""
    else:
        id_valid, id_error = utils.validate_xml_id(constraint_id, 'constraint id')
        if not id_valid:
            utils.err(id_error)
        resource_name = argv.pop(0)
        node = argv.pop(0)
        score = argv.pop(0)
        resource_valid, resource_error = utils.validate_constraint_resource(
            utils.get_cib_dom(), resource_name
        )
        if not resource_valid:
            utils.err(resource_error)
        if not utils.is_score(score):
            utils.err("invalid score '%s', use integer or INFINITY or -INFINITY" % score)

    # Verify current constraint doesn't already exist
    # If it does we replace it with the new constraint
    (dom,constraintsElement) = getCurrentConstraints()
    elementsToRemove = []

    # If the id matches, or the rsc & node match, then we replace/remove
    for rsc_loc in constraintsElement.getElementsByTagName('rsc_location'):
        if (constraint_id == rsc_loc.getAttribute("id")) or \
                (rsc_loc.getAttribute("rsc") == resource_name and \
                rsc_loc.getAttribute("node") == node and not rm):
            elementsToRemove.append(rsc_loc)

    for etr in elementsToRemove:
        constraintsElement.removeChild(etr)

    if (rm == True and len(elementsToRemove) == 0):
        utils.err("resource location id: " + constraint_id + " not found.")

    if (not rm):
        element = dom.createElement("rsc_location")
        element.setAttribute("id",constraint_id)
        element.setAttribute("rsc",resource_name)
        element.setAttribute("node",node)
        element.setAttribute("score",score)
        constraintsElement.appendChild(element)

    utils.replace_cib_configuration(dom)
示例#6
0
def colocation_set(argv):
    setoptions = []
    for i in range(len(argv)):
        if argv[i] == "setoptions":
            setoptions = argv[i+1:]
            argv[i:] = []
            break

    current_set = set_args_into_array(argv)
    colocation_id = "pcs_rsc_colocation"
    for a in argv:
        if a.find('=') == -1:
            colocation_id = colocation_id + "_" + a

    cib = utils.get_cib_etree()
    constraints = cib.find(".//constraints")
    if constraints == None:
        constraints = ET.SubElement(cib, "constraints")
    rsc_colocation = ET.SubElement(constraints,"rsc_colocation")
    rsc_colocation.set("id", utils.find_unique_id(cib,colocation_id))
    rsc_colocation.set("score","INFINITY")
    score_options = ("score", "score-attribute", "score-attribute-mangle")
    score_specified = False
    for opt in setoptions:
        if opt.find("=") != -1:
            name,value = opt.split("=")
            if name not in score_options:
                utils.err(
                    "invalid option '%s', allowed options are: %s"
                    % (name, ", ".join(score_options))
                )
            if score_specified:
                utils.err("you cannot specify multiple score options")
            score_specified = True
            if name == "score" and not utils.is_score(value):
                utils.err(
                    "invalid score '%s', use integer or INFINITY or -INFINITY"
                    % value
                )
            rsc_colocation.set(name,value)
    set_add_resource_sets(rsc_colocation, current_set, cib)
    utils.replace_cib_configuration(cib)
示例#7
0
文件: test_utils.py 项目: krig/pcs
    def test_is_score(self):
        self.assertTrue(utils.is_score("INFINITY"))
        self.assertTrue(utils.is_score("+INFINITY"))
        self.assertTrue(utils.is_score("-INFINITY"))
        self.assertTrue(utils.is_score("0"))
        self.assertTrue(utils.is_score("+0"))
        self.assertTrue(utils.is_score("-0"))
        self.assertTrue(utils.is_score("123"))
        self.assertTrue(utils.is_score("-123"))
        self.assertTrue(utils.is_score("+123"))

        self.assertFalse(utils.is_score(""))
        self.assertFalse(utils.is_score("abc"))
        self.assertFalse(utils.is_score("+abc"))
        self.assertFalse(utils.is_score("-abc"))
        self.assertFalse(utils.is_score("10a"))
        self.assertFalse(utils.is_score("+10a"))
        self.assertFalse(utils.is_score("-10a"))
        self.assertFalse(utils.is_score("a10"))
        self.assertFalse(utils.is_score("+a10"))
        self.assertFalse(utils.is_score("a-10"))
        self.assertFalse(utils.is_score("infinity"))
        self.assertFalse(utils.is_score("+infinity"))
        self.assertFalse(utils.is_score("-infinity"))
        self.assertFalse(utils.is_score("+InFiNiTy"))
        self.assertFalse(utils.is_score("INFINITY10"))
        self.assertFalse(utils.is_score("INFINITY+10"))
        self.assertFalse(utils.is_score("-INFINITY10"))
        self.assertFalse(utils.is_score("+INFINITY+10"))
        self.assertFalse(utils.is_score("10INFINITY"))
        self.assertFalse(utils.is_score("+10+INFINITY"))
示例#8
0
def location_add(argv,rm=False):
    if len(argv) < 4 and (rm == False or len(argv) < 1): 
        usage.constraint()
        sys.exit(1)

    constraint_id = argv.pop(0)

    # If we're removing, we only care about the id
    if (rm == True):
        resource_name = ""
        node = ""
        score = ""
    else:
        id_valid, id_error = utils.validate_xml_id(constraint_id, 'constraint id')
        if not id_valid:
            utils.err(id_error)
        resource_name = argv.pop(0)
        node = argv.pop(0)
        score = argv.pop(0)
        options = []
        # For now we only allow setting resource-discovery
        if len(argv) > 0:
            for arg in argv:
                if '=' in arg:
                    options.append(arg.split('=',1))
                else:
                    print("Error: bad option '%s'" % arg)
                    usage.constraint(["location add"])
                    sys.exit(1)
                if options[-1][0] != "resource-discovery" and "--force" not in utils.pcs_options:
                    utils.err("bad option '%s', use --force to override" % options[-1][0])


        resource_valid, resource_error, correct_id \
            = utils.validate_constraint_resource(
                utils.get_cib_dom(), resource_name
            )
        if "--autocorrect" in utils.pcs_options and correct_id:
            resource_name = correct_id
        elif not resource_valid:
            utils.err(resource_error)
        if not utils.is_score(score):
            utils.err("invalid score '%s', use integer or INFINITY or -INFINITY" % score)

    # Verify current constraint doesn't already exist
    # If it does we replace it with the new constraint
    (dom,constraintsElement) = getCurrentConstraints()
    elementsToRemove = []

    # If the id matches, or the rsc & node match, then we replace/remove
    for rsc_loc in constraintsElement.getElementsByTagName('rsc_location'):
        if (constraint_id == rsc_loc.getAttribute("id")) or \
                (rsc_loc.getAttribute("rsc") == resource_name and \
                rsc_loc.getAttribute("node") == node and not rm):
            elementsToRemove.append(rsc_loc)

    for etr in elementsToRemove:
        constraintsElement.removeChild(etr)

    if (rm == True and len(elementsToRemove) == 0):
        utils.err("resource location id: " + constraint_id + " not found.")

    if (not rm):
        element = dom.createElement("rsc_location")
        element.setAttribute("id",constraint_id)
        element.setAttribute("rsc",resource_name)
        element.setAttribute("node",node)
        element.setAttribute("score",score)
        for option in options:
            element.setAttribute(option[0], option[1])
        constraintsElement.appendChild(element)

    utils.replace_cib_configuration(dom)
示例#9
0
def colocation_set(argv):
    setoptions = []
    for i in range(len(argv)):
        if argv[i] == "setoptions":
            setoptions = argv[i+1:]
            argv[i:] = []
            break

    argv.insert(0, "set")
    resource_sets = set_args_into_array(argv)
    if not check_empty_resource_sets(resource_sets):
        usage.constraint(["colocation set"])
        sys.exit(1)
    cib, constraints = getCurrentConstraints(utils.get_cib_dom())

    attributes = []
    score_options = ("score", "score-attribute", "score-attribute-mangle")
    score_specified = False
    id_specified = False
    for opt in setoptions:
        if "=" not in opt:
            utils.err("missing value of '%s' option" % opt)
        name, value = opt.split("=", 1)
        if name == "id":
            id_valid, id_error = utils.validate_xml_id(value, 'constraint id')
            if not id_valid:
                utils.err(id_error)
            if utils.does_id_exist(cib, value):
                utils.err(
                    "id '%s' is already in use, please specify another one"
                    % value
                )
            id_specified = True
            attributes.append((name, value))
        elif name in score_options:
            if score_specified:
                utils.err("you cannot specify multiple score options")
            if name == "score" and not utils.is_score(value):
                utils.err(
                    "invalid score '%s', use integer or INFINITY or -INFINITY"
                    % value
                )
            score_specified = True
            attributes.append((name, value))
        else:
            utils.err(
                "invalid option '%s', allowed options are: %s"
                % (name, ", ".join(score_options + ("id",)))
            )

    if not score_specified:
        attributes.append(("score", "INFINITY"))
    if not id_specified:
        colocation_id = "pcs_rsc_colocation"
        for a in argv:
            if "=" not in a:
                colocation_id += "_" + a
        attributes.append(("id", utils.find_unique_id(cib, colocation_id)))

    rsc_colocation = cib.createElement("rsc_colocation")
    for name, value in attributes:
        rsc_colocation.setAttribute(name, value)
    set_add_resource_sets(rsc_colocation, resource_sets, cib)
    constraints.appendChild(rsc_colocation)
    utils.replace_cib_configuration(cib)
示例#10
0
文件: constraint.py 项目: tradej/pcs
def location_add(argv, rm=False):
    if len(argv) < 4 and (rm == False or len(argv) < 1):
        usage.constraint()
        sys.exit(1)

    constraint_id = argv.pop(0)

    # If we're removing, we only care about the id
    if (rm == True):
        resource_name = ""
        node = ""
        score = ""
    else:
        id_valid, id_error = utils.validate_xml_id(constraint_id,
                                                   'constraint id')
        if not id_valid:
            utils.err(id_error)
        resource_name = argv.pop(0)
        node = argv.pop(0)
        score = argv.pop(0)
        options = []
        # For now we only allow setting resource-discovery
        if len(argv) > 0:
            for arg in argv:
                if '=' in arg:
                    options.append(arg.split('=', 1))
                else:
                    print("Error: bad option '%s'" % arg)
                    usage.constraint(["location add"])
                    sys.exit(1)
                if options[-1][
                        0] != "resource-discovery" and "--force" not in utils.pcs_options:
                    utils.err("bad option '%s', use --force to override" %
                              options[-1][0])


        resource_valid, resource_error, correct_id \
            = utils.validate_constraint_resource(
                utils.get_cib_dom(), resource_name
            )
        if "--autocorrect" in utils.pcs_options and correct_id:
            resource_name = correct_id
        elif not resource_valid:
            utils.err(resource_error)
        if not utils.is_score(score):
            utils.err(
                "invalid score '%s', use integer or INFINITY or -INFINITY" %
                score)

    # Verify current constraint doesn't already exist
    # If it does we replace it with the new constraint
    (dom, constraintsElement) = getCurrentConstraints()
    elementsToRemove = []

    # If the id matches, or the rsc & node match, then we replace/remove
    for rsc_loc in constraintsElement.getElementsByTagName('rsc_location'):
        if (constraint_id == rsc_loc.getAttribute("id")) or \
                (rsc_loc.getAttribute("rsc") == resource_name and \
                rsc_loc.getAttribute("node") == node and not rm):
            elementsToRemove.append(rsc_loc)

    for etr in elementsToRemove:
        constraintsElement.removeChild(etr)

    if (rm == True and len(elementsToRemove) == 0):
        utils.err("resource location id: " + constraint_id + " not found.")

    if (not rm):
        element = dom.createElement("rsc_location")
        element.setAttribute("id", constraint_id)
        element.setAttribute("rsc", resource_name)
        element.setAttribute("node", node)
        element.setAttribute("score", score)
        for option in options:
            element.setAttribute(option[0], option[1])
        constraintsElement.appendChild(element)

    utils.replace_cib_configuration(dom)
示例#11
0
文件: constraint.py 项目: tradej/pcs
def colocation_set(argv):
    setoptions = []
    for i in range(len(argv)):
        if argv[i] == "setoptions":
            setoptions = argv[i + 1:]
            argv[i:] = []
            break

    argv.insert(0, "set")
    resource_sets = set_args_into_array(argv)
    if not check_empty_resource_sets(resource_sets):
        usage.constraint(["colocation set"])
        sys.exit(1)
    cib, constraints = getCurrentConstraints(utils.get_cib_dom())

    attributes = []
    score_options = ("score", "score-attribute", "score-attribute-mangle")
    score_specified = False
    id_specified = False
    for opt in setoptions:
        if "=" not in opt:
            utils.err("missing value of '%s' option" % opt)
        name, value = opt.split("=", 1)
        if name == "id":
            id_valid, id_error = utils.validate_xml_id(value, 'constraint id')
            if not id_valid:
                utils.err(id_error)
            if utils.does_id_exist(cib, value):
                utils.err(
                    "id '%s' is already in use, please specify another one" %
                    value)
            id_specified = True
            attributes.append((name, value))
        elif name in score_options:
            if score_specified:
                utils.err("you cannot specify multiple score options")
            if name == "score" and not utils.is_score(value):
                utils.err(
                    "invalid score '%s', use integer or INFINITY or -INFINITY"
                    % value)
            score_specified = True
            attributes.append((name, value))
        else:
            utils.err("invalid option '%s', allowed options are: %s" %
                      (name, ", ".join(score_options + ("id", ))))

    if not score_specified:
        attributes.append(("score", "INFINITY"))
    if not id_specified:
        colocation_id = "pcs_rsc_colocation"
        for a in argv:
            if "=" not in a:
                colocation_id += "_" + a
        attributes.append(("id", utils.find_unique_id(cib, colocation_id)))

    rsc_colocation = cib.createElement("rsc_colocation")
    for name, value in attributes:
        rsc_colocation.setAttribute(name, value)
    set_add_resource_sets(rsc_colocation, resource_sets, cib)
    constraints.appendChild(rsc_colocation)
    utils.replace_cib_configuration(cib)