def validate_routing_rule(self, rule): rule = rule.get("goto") if rule and "when" in rule: when_validator = WhenRuleValidator(rule["when"], self.schema_element["id"], self.questionnaire_schema) self.errors += when_validator.validate()
def validate_variants(self, block): question_variants = block.get("question_variants", []) content_variants = block.get("content_variants", []) all_variants = question_variants + content_variants for variant in question_variants: self.validate_question(variant) # This is validated in json schema, but the error message is not good at the moment. if len(question_variants) == 1 or len(content_variants) == 1: self.add_error( error_messages.VARIANTS_HAS_ONE_VARIANT, block_id=block["id"] ) for variant in all_variants: when_clause = variant.get("when", []) if isinstance(when_clause, list): when_validator = WhenRuleValidator( when_clause, block["id"], self.questionnaire_schema ) self.errors += when_validator.validate() elif isinstance(when_clause, dict): when_validator = NewWhenRuleValidator( when_clause, self.section["id"], self.questionnaire_schema ) self.errors += when_validator.validate() self.validate_variant_fields(block, question_variants)
def validate_skip_condition(self, skip_condition): """ Validate skip condition is valid :return: list of dictionaries containing error messages, otherwise it returns an empty list """ when = skip_condition.get("when") when_validator = WhenRuleValidator( when, self.schema_element["id"], self.questionnaire_schema ) self.errors += when_validator.validate()
def test_validate_answer_value_in_when_rule_valid(): when_rule = {"id": "answer-1", "condition": "equals", "value": "Yes"} option_value_to_answer_id_map = { "answer-1": {"Yes", "No"}, "answer-2": {"Yes", "No"}, } questionnaire_schema = QuestionnaireSchema({}) validator = WhenRuleValidator(when_rule, {}, questionnaire_schema) validator.questionnaire_schema.answer_id_to_option_values_map = ( option_value_to_answer_id_map) validator.validate_answer_value_in_when_rule(when_rule) assert not validator.errors
def validate_section_enabled(self): section_enabled = self.section.get("enabled", None) if isinstance(section_enabled, list): for enabled in section_enabled: when = enabled["when"] when_validator = WhenRuleValidator( when, self.section["id"], self.questionnaire_schema ) self.errors += when_validator.validate() elif isinstance(section_enabled, dict): when = section_enabled["when"] when_validator = NewWhenRuleValidator( when, self.section["id"], self.questionnaire_schema ) self.errors += when_validator.validate()
def test_validate_answer_value_in_when_rule_invalid(): when_rule = {"id": "answer-1", "condition": "equals", "value": "Yes"} option_value_to_answer_id_map = { "answer-1": {"Maybe", "No"}, "answer-2": {"Yes", "No"}, } questionnaire_schema = QuestionnaireSchema({}) validator = WhenRuleValidator(when_rule, {}, questionnaire_schema) validator.questionnaire_schema.answer_id_to_option_values_map = ( option_value_to_answer_id_map) validator.validate_answer_value_in_when_rule(when_rule) assert validator.errors[0] == { "message": WhenRuleValidator.INVALID_WHEN_RULE_ANSWER_VALUE, "answer_id": "answer-1", "value": "Yes", }
def test_invalid_answer_value_in_when_rule(): filename = "schemas/invalid/test_invalid_answer_value_in_when_rule.json" questionnaire_schema = QuestionnaireSchema( _open_and_load_schema_file(filename)) validator = WhenRuleValidator({}, {}, questionnaire_schema) when = { "id": "country-checkbox-answer", "condition": "contains any", "values": ["France", 7, "Italian"], } expected_error_messages = [{ "message": WhenRuleValidator.INVALID_WHEN_RULE_ANSWER_VALUE, "answer_id": "country-checkbox-answer", "value": value, } for value in ["France", 7, "Italian"]] validator.validate_answer_value_in_when_rule(when) assert validator.errors == expected_error_messages
def test_answer_comparisons_different_types_skip_group(): """Ensures that when answer comparison is used, the type of the variables must be the same""" when_rule = { "id": "comparison-1-answer", "condition": "less than", "comparison": { "id": "comparison-2-answer", "source": "answers" }, } questionnaire_schema = QuestionnaireSchema({}) questionnaire_schema.answers_with_context = { "comparison-1-answer": { "answer": { "id": "comparison-1-answer", "type": "Number" }, "block": "route-comparison-1", }, "comparison-2-answer": { "answer": { "id": "comparison-2-answer", "type": "TextField" }, "block": "comparison-2", }, } validator = WhenRuleValidator(when_rule, {}, questionnaire_schema) validator.validate_comparison_in_when_rule(when_rule, "block-id") expected_errors = [{ "message": WhenRuleValidator.NON_MATCHING_WHEN_ANSWER_AND_COMPARISON_TYPES, "comparison_id": "comparison-2-answer", "answer_id": "comparison-1-answer", "referenced_id": "block-id", }] assert expected_errors == validator.errors
def test_answer_comparisons_different_types(): """Ensures that when answer comparison is used, the type of the variables must be the same""" when_rule = { "id": "comparison-1-answer", "condition": "equals any", "comparison": { "id": "comparison-2-answer", "source": "answers" }, } questionnaire_schema = QuestionnaireSchema({}) questionnaire_schema.answers_with_context = { "comparison-1-answer": { "answer": { "id": "comparison-1-answer", "type": "Number" }, "block": "route-comparison-1", }, "comparison-2-answer": { "answer": { "id": "comparison-2-answer", "type": "TextField" }, "block": "comparison-2", }, } validator = WhenRuleValidator(when_rule, {}, questionnaire_schema) validator.validate_comparison_in_when_rule(when_rule, "block-id") expected_errors = [{ "message": WhenRuleValidator.NON_CHECKBOX_COMPARISON_ID, "comparison_id": "comparison-2-answer", "condition": "equals any", }] assert expected_errors == validator.errors
def validate_skip_conditions(self, skip_conditions, origin_id): for skip_condition in skip_conditions: when_validator = WhenRuleValidator( skip_condition["when"], origin_id, self.questionnaire_schema ) self.errors += when_validator.validate()