Ejemplo n.º 1
0
    def test_do_not_go_to_next_question_for_date_answer(self):

        goto_rule = {
            'id':
            'next-question',
            'when': [{
                'id': 'date-answer',
                'condition': 'equals',
                'date_comparison': {
                    'value': '2018-01'
                }
            }]
        }

        answer_store = AnswerStore({})
        answer_store.add_or_update(
            Answer(answer_id='date_answer', value='2018-02-01'))

        self.assertFalse(
            evaluate_goto(goto_rule, get_schema_mock(), {}, answer_store, 0))
Ejemplo n.º 2
0
    def test_evaluate_skip_condition_returns_true_when_that_rule_true(self):

        skip_condition = [{
            'when': [{
                'id': 'this',
                'condition': 'equals',
                'value': 'value'
            }]
        }, {
            'when': [{
                'id': 'that',
                'condition': 'equals',
                'value': 'other value'
            }]
        }]
        answer_store = AnswerStore()
        answer_store.add(Answer(answer_id='that', value='other value'))

        self.assertTrue(
            evaluate_skip_condition(skip_condition, {}, answer_store))
    def test_case_id_should_be_set_in_payload(self):
        with self._app.test_request_context():

            questionnaire = {'survey_id': '021', 'data_version': '0.0.2'}

            answer_object = convert_answers(self.metadata,
                                            QuestionnaireSchema(questionnaire),
                                            AnswerStore(), {})

            self.assertEqual(answer_object['case_id'],
                             self.metadata['case_id'])
Ejemplo n.º 4
0
    def test_evaluate_date_rule_greater_than_with_id(self):

        when = {
            'id': 'date-answer',
            'condition': 'greater than',
            'date_comparison': {
                'id': 'compare_date_answer'
            }
        }

        answer_store = AnswerStore({})
        answer_store.add(Answer(answer_id='compare_date_answer', value='2018-02-03'))

        answer_value = '2018-02-04'
        result = evaluate_date_rule(when, answer_store, get_schema_mock(), 0, None, answer_value)
        self.assertTrue(result)

        answer_value = '2018-02-03'
        result = evaluate_date_rule(when, answer_store, get_schema_mock(), 0, None, answer_value)
        self.assertFalse(result)
Ejemplo n.º 5
0
    def test_get_checkbox_answer_with_duplicate_child_answer_ids(self):
        with self._app.test_request_context():
            routing_path = [
                Location(group_id='favourite-food',
                         group_instance=0,
                         block_id='crisps')
            ]
            answers = [
                create_answer('crisps-answer', ['Ready salted', 'Other'],
                              group_id='favourite-food',
                              block_id='crisps')
            ]

            answers += [
                create_answer('other-answer-mandatory',
                              'Other',
                              group_id='favourite-food',
                              block_id='crisps',
                              group_instance=1)
            ]
            answers += [
                create_answer('other-answer-mandatory',
                              'Other',
                              group_id='favourite-food',
                              block_id='crisps',
                              group_instance=1)
            ]

            questionnaire = make_schema(
                '0.0.1', 'section-1', 'favourite-food', 'crisps', [{
                    'id':
                    'crisps-question',
                    'answers': [{
                        'id':
                        'crisps-answer',
                        'type':
                        'Checkbox',
                        'options': [{
                            'label': 'Other',
                            'q_code': '4',
                            'description': 'Choose any other flavour',
                            'value': 'Other',
                            'child_answer_id': 'other-answer-mandatory'
                        }]
                    }]
                }])

        with self.assertRaises(Exception) as err:
            convert_answers(self.metadata, self.collection_metadata,
                            QuestionnaireSchema(questionnaire),
                            AnswerStore(answers), routing_path)
        self.assertEqual(
            'Multiple answers found for {}'.format('other-answer-mandatory'),
            str(err.exception))
Ejemplo n.º 6
0
    def test_do_not_go_to_next_question_for_multiple_answers(self):
        # Given
        goto_rule = {
            'id':
            'next-question',
            'when': [{
                'id': 'my_answer',
                'condition': 'equals',
                'value': 'Yes'
            }, {
                'id': 'my_other_answer',
                'condition': 'equals',
                'value': '2'
            }]
        }
        answer_store = AnswerStore({})
        answer_store.add(Answer(answer_id='my_answer', value='No'))

        self.assertFalse(
            evaluate_goto(goto_rule, get_schema_mock(), {}, answer_store, 0))
Ejemplo n.º 7
0
    def test_get_next_location_summary(self):
        survey = load_schema_file("0_star_wars.json")

        answer_1 = Answer(group_id="14ba4707-321d-441d-8d21-b8367366e766",
                          block_id="choose-your-side-block",
                          answer_id="ca3ce3a3-ae44-4e30-8f85-5b6a7a2fb23c",
                          value="Light Side")
        answer_2 = Answer(
            group_id="14ba4707-321d-441d-8d21-b8367366e766",
            block_id="96682325-47ab-41e4-a56e-8315a19ffe2a",
            answer_id="2e0989b8-5185-4ba6-b73f-c126e3a06ba7",
            value="No",
        )

        answers = AnswerStore()
        answers.add(answer_1)
        answers.add(answer_2)

        path_finder = PathFinder(survey, answer_store=answers)

        current_location = Location('14ba4707-321d-441d-8d21-b8367366e766', 0,
                                    'an3b74d1-b687-4051-9634-a8f9ce10ard')

        next_location = path_finder.get_next_location(
            current_location=current_location)

        expected_next_location = Location(
            "14ba4707-321d-441d-8d21-b8367366e766", 0,
            '846f8514-fed2-4bd7-8fb2-4b5fcb1622b1')

        self.assertEqual(expected_next_location, next_location)

        current_location = expected_next_location

        next_location = path_finder.get_next_location(
            current_location=current_location)

        expected_next_location = Location(
            "14ba4707-321d-441d-8d21-b8367366e766", 0, 'summary')

        self.assertEqual(expected_next_location, next_location)
    def test_previous_with_conditional_path(self):
        schema = load_schema_from_params('0', 'star_wars')
        schema.answer_is_in_repeating_group = MagicMock(return_value=False)

        expected_path = [
            Location('star-wars', 0, 'choose-your-side-block'),
            Location('star-wars', 0, 'dark-side-pick-character-ship'),
            Location('star-wars', 0, 'light-side-ship-type'),
            Location('star-wars', 0, 'star-wars-trivia'),
            Location('star-wars', 0, 'star-wars-trivia-part-2'),
            Location('star-wars', 0, 'star-wars-trivia-part-3'),
        ]

        answer_1 = Answer(
            answer_id='choose-your-side-answer',
            value='Dark Side'
        )
        answer_2 = Answer(
            answer_id='dark-side-pick-ship-answer',
            value='Can I be a pain and have a goodies ship',
        )

        answers = AnswerStore()
        answers.add(answer_1)
        answers.add(answer_2)

        current_location = expected_path[3]
        expected_previous_location = expected_path[2]

        path_finder = PathFinder(schema, answer_store=answers, metadata={}, completed_blocks=[])
        actual_previous_block = path_finder.get_previous_location(current_location=current_location)

        self.assertEqual(actual_previous_block, expected_previous_location)

        current_location = expected_path[2]
        expected_previous_location = expected_path[1]


        actual_previous_block = path_finder.get_previous_location(current_location=current_location)

        self.assertEqual(actual_previous_block, expected_previous_location)
    def test_sum_calculated_field(self):
        store = AnswerStore()

        answer_total = Answer(
            answer_id='total-answer',
            answer_instance=1,
            group_instance=1,
            value=10,
        )

        store.add(answer_total)

        with self.app_request_context():
            schema = load_schema_from_params(
                'test', 'sum_equal_validation_against_total')

            block_json = schema.get_block('breakdown-block')

            data = {
                'breakdown-1': '',
                'breakdown-2': '5',
                'breakdown-3': '4',
                'breakdown-4': '1'
            }

            expected_form_data = {
                'csrf_token': '',
                'breakdown-1': None,
                'breakdown-2': Decimal('5'),
                'breakdown-3': Decimal('4'),
                'breakdown-4': Decimal('1')
            }
            form = generate_form(schema,
                                 block_json,
                                 store,
                                 metadata=None,
                                 group_instance=0,
                                 formdata=data)

            form.validate()
            self.assertEqual(form.data, expected_form_data)
    def test_evaluate_not_set_when_rules_should_return_true(self):
        when = {
            'when': [
                {
                    'id': 'my_answers',
                    'condition': 'not set'
                }
            ]
        }
        answer_store = AnswerStore({})

        self.assertTrue(evaluate_when_rules(when, get_schema_mock(), {}, answer_store, 0))
def test_transform_variants_with_content(content_variant_schema):
    schema = QuestionnaireSchema(content_variant_schema)
    answer_store = AnswerStore({})
    answer_store.add_or_update(Answer(answer_id="age-answer", value="18"))
    metadata = {}

    block = schema.get_block("block1")
    section_id = schema.get_section_id_for_block_id(block["id"])

    transformed_block = transform_variants(
        block,
        schema,
        metadata,
        answer_store,
        ListStore({}),
        Location(section_id=section_id, block_id=block["id"]),
    )

    assert transformed_block != block
    assert "content_variants" not in transformed_block
    assert transformed_block["content"][0]["title"] == "You are over 16"
Ejemplo n.º 12
0
    def test_evaluate_skip_condition_returns_false_when_no_skip_condition(
            self):
        # Given
        skip_conditions = None

        # When
        condition = evaluate_skip_conditions(skip_conditions,
                                             get_schema_mock(), {},
                                             AnswerStore({}))

        # Then
        self.assertFalse(condition)
    def test_convert_answers_flushed_flag_overriden_to_true(self):
        with self._app.test_request_context():
            user_answer = [create_answer('GHI', 0)]

            questionnaire = {'survey_id': '021', 'data_version': '0.0.2'}

            answer_object = convert_answers(self.metadata,
                                            QuestionnaireSchema(questionnaire),
                                            AnswerStore(user_answer), {},
                                            flushed=True)

            self.assertTrue(answer_object['flushed'])
Ejemplo n.º 14
0
    def test_given_interstitial_page_when_get_page_title_then_group_title_and_survey_title(
            self):
        # Given
        schema = load_schema_from_params('test', 'interstitial_page')

        # When
        page_title = get_page_title_for_location(
            schema, Location('favourite-foods', 0, 'breakfast-interstitial'),
            {}, AnswerStore())

        # Then
        self.assertEqual(page_title, 'Favourite food - Interstitial Pages')
    def test_answer_count_when_rule_not_equal(self):  # pylint: disable=no-self-use
        """Assert that an `answer_count` can be used in a when block and the
            False is returned when the values do not match. """
        answer_group_id = 'repeated-answer'
        when = [{
            'answer_count': answer_group_id,
            'condition': 'equals',
            'value': 1,
        }]
        answer_store = AnswerStore({})

        self.assertFalse(evaluate_when_rules(when, get_schema_mock(), {}, answer_store, 0))
    def test_meta_comparison_missing(self):
        # Given
        goto_rule = {
            'id': 'next-question',
            'when': [
                {
                    'condition': 'equals',
                    'meta': 'varient_flags.does_not_exist.does_not_exist',
                    'value': True
                }
            ]
        }
        answer_store = AnswerStore({})
        answer_store.add(Answer(answer_id='my_answer', value='Yes'))
        metadata = {'varient_flags': {'sexual_identity': True}}

        # When
        goto = evaluate_goto(goto_rule, get_schema_mock(), metadata, answer_store, 0)

        # Then
        self.assertFalse(goto)
Ejemplo n.º 17
0
    def test_answer_count_when_rule_id_takes_precident(self):
        """Assert that if somehow, both `id` and `answer_count` are present in a when clause
            the `id` takes precident and no errors are thrown. """
        answer_group_id = 'repeated-answer'
        ref_id = 'just-a-regular-answer'
        when = [{
            'id': ref_id,
            'answer_count': answer_group_id,
            'condition': 'equals',
            'value': 10,
        }]
        answer_store = AnswerStore({})
        answer_store.add(Answer(
            answer_id=ref_id,
            group_instance=0,
            value=10,
        ))

        self.assertTrue(
            evaluate_when_rules(when, get_schema_mock(), {}, answer_store, 0,
                                None))
Ejemplo n.º 18
0
    def test_submitted_at_should_be_set_in_payload(self):
        with self.application.test_request_context():
            user_answer = [create_answer('GHI', 0)]

            questionnaire = {
                "survey_id": "021",
                "data_version": "0.0.2"
            }

            answer_object = convert_answers(metadata, questionnaire, AnswerStore(user_answer), {})

            self.assertLess(datetime.now(timezone.utc) - dateutil.parser.parse(answer_object['submitted_at']), timedelta(seconds=5))
Ejemplo n.º 19
0
    def test_converter_raises_runtime_error_for_unsupported_version(self):
        with self.application.test_request_context():

            questionnaire = {
                "survey_id": "021",
                "data_version": "-0.0.1"
            }

            with self.assertRaises(DataVersionError) as err:
                convert_answers(metadata, questionnaire, AnswerStore(), {})

            self.assertEqual(str(err.exception), 'Data version -0.0.1 not supported')
    def test_id_when_rule_answer_count_equal_0(self):
        """Assert that an `answer_count` can be used in a when block and the
            correct value is fetched. """
        answer_group_id = 'repeated-answer'
        when = [{
            'answer_count': answer_group_id,
            'condition': 'equals',
            'value': 0,
        }]

        answer_store = AnswerStore({})
        self.assertTrue(evaluate_when_rules(when, get_schema_mock(), {}, answer_store, 0))
Ejemplo n.º 21
0
    def __init__(self, storage):
        self._storage = storage
        self._initial_data = {}
        self.metadata = {}
        self.answer_store = AnswerStore()
        self.completed_blocks = []

        if self._storage.exists():
            raw_data = self._storage.get_user_data()
            self._initial_data = self._deserialise(raw_data)
            data_copy = self._deserialise(raw_data)
            self._set_data(data_copy)
Ejemplo n.º 22
0
    def test_given_introduction_page_when_get_page_title_then_defaults_to_survey_title(
            self):
        # Given
        schema = load_schema_from_params('test', 'final_confirmation')

        # When
        page_title = get_page_title_for_location(
            schema, Location('final-confirmation', 0, 'introduction'), {},
            AnswerStore())

        # Then
        self.assertEqual(page_title, 'Final confirmation to submit')
    def test_convert_answers_flushed_flag_default_is_false(self):
        with self._app.test_request_context():
            user_answer = [create_answer('GHI', 0)]

            questionnaire = {'survey_id': '021', 'data_version': '0.0.2'}

            answer_object = convert_answers(self.metadata,
                                            self.collection_metadata,
                                            QuestionnaireSchema(questionnaire),
                                            AnswerStore(user_answer), {})

            self.assertFalse(answer_object['flushed'])
    def test_date_form_empty_data(self):
        schema = load_schema_from_params('test', 'dates')
        error_messages = schema.error_messages

        answers = schema.get_answers_by_id_for_block('date-block')

        with self.app_request_context('/'):
            form = get_date_form(AnswerStore(), {},
                                 answers['single-date-answer'],
                                 error_messages=error_messages)

        self.assertIsNone(form().data)
def test_get_referenced_offset_value_for_answer_id(app):
    answer_store = AnswerStore()

    test_answer_id = Answer(answer_id="date", value="2018-03-20")
    answer_store.add_or_update(test_answer_id)

    answer = {
        "maximum": {
            "value": {
                "identifier": "date",
                "source": "answers"
            }
        }
    }

    handler = DateHandler(answer, answer_store=answer_store)
    maximum_date = handler.get_date_value("maximum")
    maximum_date = handler.transform_date_by_offset(maximum_date,
                                                    {"months": 1})

    assert maximum_date == convert_to_datetime("2018-04-20")
Ejemplo n.º 26
0
    def test_get_next_location_should_not_skip_group(self):
        # Given
        survey = load_schema_file('test_skip_condition_group.json')
        current_location = Location('do-you-want-to-skip-group', 0,
                                    'do-you-want-to-skip')
        answer_store = AnswerStore()
        answer_store.add(
            Answer(group_id='do-you-want-to-skip-group',
                   block_id='do-you-want-to-skip',
                   answer_id='do-you-want-to-skip-answer',
                   value='No'))

        # When
        path_finder = PathFinder(survey, answer_store=answer_store)

        # Then
        expected_location = Location('should-skip-group', 0, 'should-skip')

        self.assertEqual(
            path_finder.get_next_location(current_location=current_location),
            expected_location)
Ejemplo n.º 27
0
    def test_go_to_next_question_for_multiple_answers(self):
        # Given
        goto = {
            "id":
            "next-question",
            "when": [
                {
                    "id": "my_answer",
                    "condition": "equals",
                    "value": "Yes"
                },
                {
                    "id": "my_other_answer",
                    "condition": "equals",
                    "value": "2"
                },
            ],
        }
        answer_store = AnswerStore()
        answer_store.add_or_update(Answer(answer_id="my_answer", value="Yes"))
        answer_store.add_or_update(
            Answer(answer_id="my_other_answer", value="2"))

        current_location = Location(section_id="some-section",
                                    block_id="some-block")

        self.assertTrue(
            evaluate_goto(
                goto_rule=goto,
                schema=get_schema(),
                metadata={},
                answer_store=answer_store,
                list_store=ListStore(),
                current_location=current_location,
            ))
    def test_route_based_on_answer_count(self):
        schema = load_schema_from_params('test', 'routing_answer_count')

        answer_group_id = 'first-name'

        answer_store = AnswerStore({})
        answer_store.add(Answer(
            answer_id=answer_group_id,
            answer_instance=0,
            value='alice',
        ))
        answer_store.add(Answer(
            answer_id=answer_group_id,
            answer_instance=1,
            value='bob',
        ))

        completed_blocks = [
            Location('multiple-questions-group', 0, 'household-composition')
        ]
        expected_next_location = Location('group-equal-2', 0, 'group-equal-2-block')
        should_not_be_present = Location('group-less-than-2', 0, 'group-less-than-2-block')

        path_finder = PathFinder(schema, answer_store, metadata={}, completed_blocks=completed_blocks)
        path = path_finder.build_path()

        self.assertNotIn(should_not_be_present, path)
        self.assertIn(expected_next_location, path)
Ejemplo n.º 29
0
    def test_repeating_groups_no_of_answers_minus_one(self):
        survey = load_schema_file("test_repeating_household.json")

        # Default is to count answers, so switch to using value
        survey['groups'][-1]['routing_rules'][0]['repeat'][
            'type'] = 'answer_count_minus_one'

        expected_path = [
            Location("multiple-questions-group", 0, "household-composition"),
            Location("repeating-group", 0, "repeating-block-1"),
            Location("repeating-group", 0, "repeating-block-2"),
        ]

        answer = Answer(group_id="multiple-questions-group",
                        group_instance=0,
                        answer_instance=0,
                        answer_id="first-name",
                        block_id="household-composition",
                        value="Joe Bloggs")

        answer_2 = Answer(group_id="multiple-questions-group",
                          group_instance=0,
                          answer_instance=1,
                          answer_id="first-name",
                          block_id="household-composition",
                          value="Sophie Bloggs")

        answers = AnswerStore()

        answers.add(answer)
        answers.add(answer_2)

        path_finder = PathFinder(survey, answer_store=answers)

        self.assertEqual(expected_path, path_finder.get_routing_path())
    def test_evaluate_skip_condition_returns_true_when_more_than_one_rule_is_true(self):
        # Given
        skip_conditions = [
            {
                'when': [
                    {
                        'id': 'this',
                        'condition': 'equals',
                        'value': 'value'
                    }
                ]
            },
            {
                'when': [
                    {
                        'id': 'that',
                        'condition': 'equals',
                        'value': 'other value'
                    }
                ]
            }
        ]
        answer_store = AnswerStore({})
        answer_store.add(Answer(answer_id='this', value='value'))
        answer_store.add(Answer(answer_id='that', value='other value'))

        # When
        condition = evaluate_skip_conditions(skip_conditions, get_schema_mock(), {}, answer_store)

        # Then
        self.assertTrue(condition)