def test_should_convert_multi_select_question(self):
        xls_parser_response = XlsFormParser(self.MULTI_SELECT, u"My questionnairé").parse()

        mangroveService = MangroveService(self.mock_request, xls_parser_response=xls_parser_response)
        questionnaire_id = mangroveService.create_project()

        self.assertIsNotNone(questionnaire_id)
    def test_should_create_project_using_xlsform_file(self):
        xls_parser_response = XlsFormParser(self.ALL_FIELDS, u"My questionnairé").parse()

        mangroveService = MangroveService(self.mock_request, xls_parser_response=xls_parser_response)
        quesionnaire_id = mangroveService.create_project()

        self.assertIsNotNone(quesionnaire_id)
    def test_should_convert_skip_logic_question(self):
        xls_parser_response = XlsFormParser(self.SKIP, u"My questionnairé").parse()

        mangroveService = MangroveService(self.mock_request, xls_parser_response=xls_parser_response)
        questionnaire_id = mangroveService.create_project()

        self.assertIsNotNone(questionnaire_id)
Example #4
0
    def post(self, request):
        project_name = request.GET['pname'].strip()
        manager = get_database_manager(request.user)

        try:
            xls_parser_response = _try_parse_xls(manager, request,
                                                 project_name)

            if isinstance(xls_parser_response, HttpResponse):
                return xls_parser_response

            send_email_if_unique_id_type_question_has_no_registered_unique_ids(
                xls_parser_response, request, project_name)
            questionnaire_code = generate_questionnaire_code(manager)
            excel_file = _temp_file(request)
            mangrove_service = MangroveService(
                request,
                questionnaire_code=questionnaire_code,
                project_name=project_name,
                xls_form=excel_file,
                xls_parser_response=xls_parser_response)
            questionnaire_id, form_code = mangrove_service.create_project()

            if not questionnaire_id:
                logger.info("User: %s. Upload Error: %s",
                            request.user.username,
                            "Questionnaire must be unique")

                return HttpResponse(
                    content_type='application/json',
                    content=json.dumps({
                        'success':
                        False,
                        'error_msg': [
                            _("Duplicate labels. All questions (labels) must be unique."
                              )
                        ],
                        'message_prefix':
                        _("Sorry! Current version of DataWinners does not support"
                          ),
                        'message_suffix':
                        _("Update your XLSForm and upload again.")
                    }))

            questionnaire = Project.get(manager, questionnaire_id)
            _save_questionnaire_as_dict_for_builder(questionnaire,
                                                    excel_file=excel_file)
        except QuestionAlreadyExistsException as e:
            return HttpResponse(content_type='application/json',
                                content=json.dumps({
                                    'success': False,
                                    'error_msg': [_(e.message)]
                                }))
        return HttpResponse(json.dumps({
            "success": True,
            "project_name": project_name,
            "project_id": questionnaire_id,
            "form_code": form_code
        }),
                            content_type='application/json')
    def test_should_verify_repeat_field_added_to_questionnaire(self):
        xls_parser_response = XlsFormParser(self.REPEAT, u"My questionnairé").parse()
        mangroveService = MangroveService(self.mock_request, xls_parser_response=xls_parser_response)
        mangroveService.create_project()

        questionnaire_code = mangroveService.questionnaire_code
        mgr = mangroveService.manager
        from_model = get_form_model_by_code(mgr, questionnaire_code)

        self.assertNotEqual([], [f for f in from_model.fields if type(f) is FieldSet and f.fields])
    def test_xform_is_the_default_namespace(self):
        # while parsing submission we assume that xform element without namespace since being default.
        xform_as_string = open(self.NAME_SPACE, 'r').read()
        default_namespace_definition_format = 'xmlns="http://www.w3.org/2002/xforms"'

        mangrove_service = MangroveService(self.mock_request, xls_parser_response=XlsParserResponse(xform_as_string=xform_as_string))
        mangrove_service.xform = xform_as_string
        updated_xform = mangrove_service.add_form_code(None)

        self.assertTrue(updated_xform.find(default_namespace_definition_format) != -1)
    def test_should_add_form_code_and_bind_element_to_xform(self):
        xform_as_string = open(self.NAME_SPACE, 'r').read()
        expected_form_code = '022-somthing-making-it-unique-in-xml'

        mangrove_service = MangroveService(self.mock_request, xls_parser_response=XlsParserResponse(xform_as_string=xform_as_string))
        mangrove_service.xform = xform_as_string
        updated_xform = mangrove_service \
            .add_form_code('%s' % expected_form_code)

        form_code = self._find_in_instance(updated_xform, 'form_code')
        self.assertEqual(form_code, expected_form_code)
    def test_should_verify_xform_is_stored_when_project_created(self):

        manager = get_database_manager(self.user)
        questionnaire_code = generate_questionnaire_code(manager)
        project_name = 'xform-' + questionnaire_code

        xls_parser_response = XlsFormParser(self.REPEAT, u"My questionnairé").parse()

        mangrove_service = MangroveService(self.mock_request, project_name=project_name, xls_parser_response=xls_parser_response)
        mangrove_service.create_project()

        questionnaire_code = mangrove_service.questionnaire_code
        mgr = mangrove_service.manager
        from_model = get_form_model_by_code(mgr, questionnaire_code)
        self.assertIsNotNone(from_model.xform)
Example #9
0
    def post(self, request):
        file_content = None
        tmp_file = None
        try:
            file_content = request.raw_post_data
            file_errors, file_extension = _perform_file_validations(request)
            tmp_file = NamedTemporaryFile(delete=True, suffix=file_extension)
            if file_errors:
                logger.info(
                    "User: %s. Upload File validation failed: %s. File name: %s, size: %d",
                    request.user.username, json.dumps(file_errors),
                    request.GET.get("qqfile"),
                    int(request.META.get('CONTENT_LENGTH')))

                return HttpResponse(json.dumps({
                    'success': False,
                    'error_msg': file_errors
                }),
                                    content_type='application/json')

            tmp_file.write(file_content)
            tmp_file.seek(0)

            project_name = request.GET['pname'].strip()
            manager = get_database_manager(request.user)
            questionnaire_code = generate_questionnaire_code(manager)

            xls_parser_response = XlsFormParser(tmp_file, project_name,
                                                manager).parse()

            send_email_if_unique_id_type_question_has_no_registered_unique_ids(
                xls_parser_response, request, project_name)

            profile = request.user.get_profile()
            organization = Organization.objects.get(org_id=profile.org_id)
            if xls_parser_response.is_multiple_languages:
                logger.info(
                    "Creating Questionnaire %s with Multi Language support for organization : %s(%s) and email: %s",
                    project_name, organization.name, profile.org_id,
                    profile.user.email)

            if xls_parser_response.errors:
                error_list = list(xls_parser_response.errors)
                logger.info("User: %s. Upload Errors: %s",
                            request.user.username, json.dumps(error_list))

                return HttpResponse(
                    content_type='application/json',
                    content=json.dumps({
                        'success':
                        False,
                        'error_msg':
                        error_list,
                        'message_prefix':
                        _("Sorry! Current version of DataWinners does not support"
                          ),
                        'message_suffix':
                        _("Update your XLSForm and upload again.")
                    }))
            tmp_file.seek(0)
            mangrove_service = MangroveService(
                request,
                questionnaire_code=questionnaire_code,
                project_name=project_name,
                xls_form=tmp_file,
                xls_parser_response=xls_parser_response)
            questionnaire_id, form_code = mangrove_service.create_project()

        except PyXFormError as e:
            logger.info("User: %s. Upload Error: %s", request.user.username,
                        e.message)

            message = transform_error_message(e.message)
            if 'name_type_error' in message or 'choice_name_type_error' in message:
                if 'choice_name_type_error' in message:
                    message_prefix = _(
                        "On your \"choices\" sheet the first and second column must be \"list_name\" and \"name\".  Possible errors:"
                    )
                else:
                    message_prefix = _(
                        "On your \"survey\" sheet the first and second column must be \"type\" and \"name\".  Possible errors:"
                    )
                return HttpResponse(
                    content_type='application/json',
                    content=json.dumps({
                        'success':
                        False,
                        'error_msg': [
                            _("Columns are missing"),
                            _("Column name is misspelled"),
                            _("Additional space in column name")
                        ],
                        'message_prefix':
                        message_prefix,
                        'message_suffix':
                        _("Update your XLSForm and upload again.")
                    }))
            else:
                return HttpResponse(
                    content_type='application/json',
                    content=json.dumps({
                        'success':
                        False,
                        'error_msg': [
                            message if message else ugettext(
                                "all XLSForm features. Please check the list of unsupported features."
                            )
                        ]
                    }))

        except QuestionAlreadyExistsException as e:
            logger.info("User: %s. Upload Error: %s", request.user.username,
                        e.message)

            return HttpResponse(
                content_type='application/json',
                content=json.dumps({
                    'success':
                    False,
                    'error_msg': [
                        _("Duplicate labels. All questions (labels) must be unique."
                          )
                    ],
                    'message_prefix':
                    _("Sorry! Current version of DataWinners does not support"
                      ),
                    'message_suffix':
                    _("Update your XLSForm and upload again.")
                }))

        except UnicodeDecodeError as e:
            logger.info("User: %s. Upload Error: %s", request.user.username,
                        e.message)

            return HttpResponse(
                content_type='application/json',
                content=json.dumps({
                    'success':
                    False,
                    'error_msg': [
                        _("Check your columns for errors.<br>There are missing symbols (like $ for relevant or calculate) or incorrect characters<br>"
                          ) + _("Update your XLSForm and upload again.")
                    ],
                }))

        except Exception as e:

            message = e.message if e.message else _("Errors in excel")

            logger.info("User: %s. Upload Exception message: %s",
                        request.user.username, e.message)

            odk_message = ''
            if not 'ODK Validate Errors:' in e.message:
                send_email_on_exception(
                    request.user,
                    "Questionnaire Create",
                    traceback.format_exc(),
                    additional_details={'file_contents': file_content})
            else:
                odk_message = translate_odk_message(e.message)
            message = odk_message if odk_message else message
            return HttpResponse(content_type='application/json',
                                content=json.dumps({
                                    'success': False,
                                    'error_msg': [message],
                                }))

        finally:

            if tmp_file:
                tmp_file.close()

        if not questionnaire_id:
            org = get_organization(request)
            if org.is_pro_sms:
                message = _(
                    "Questionnaire or Poll with same name already exists.Upload was cancelled."
                )
            else:
                message = _(
                    "Questionnaire with same name already exists.Upload was cancelled."
                )
            return HttpResponse(json.dumps({
                'success': False,
                'duplicate_project_name': True,
                'error_msg': [message]
            }),
                                content_type='application/json')

        return HttpResponse(json.dumps({
            "success": True,
            "project_name": project_name,
            "project_id": questionnaire_id,
            "form_code": form_code
        }),
                            content_type='application/json')
Example #10
0
    def post(self, request, project_id):

        manager = get_database_manager(request.user)
        questionnaire = Project.get(manager, project_id)
        file_content = None
        tmp_file = None
        try:
            file_content = request.raw_post_data

            file_errors, file_extension = _perform_file_validations(request)
            tmp_file = NamedTemporaryFile(delete=True, suffix=file_extension)

            if file_errors:
                logger.info(
                    "User: %s. Edit upload File validation failed: %s. File name: %s, size: %d",
                    request.user.username, json.dumps(file_errors),
                    request.GET.get("qqfile"),
                    int(request.META.get('CONTENT_LENGTH')))

                return HttpResponse(content_type='application/json',
                                    content=json.dumps({
                                        'success': False,
                                        'error_msg': file_errors
                                    }))

            tmp_file.write(file_content)
            tmp_file.seek(0)

            xls_parser_response = XlsFormParser(tmp_file, questionnaire.name,
                                                manager).parse()

            send_email_if_unique_id_type_question_has_no_registered_unique_ids(
                xls_parser_response, request, questionnaire.name)

            profile = request.user.get_profile()
            organization = Organization.objects.get(org_id=profile.org_id)
            if xls_parser_response.is_multiple_languages:
                logger.info(
                    "Edit Questionnaire %s with Multi Language support for organization : %s(%s) and email: %s",
                    questionnaire.name, organization.name, profile.org_id,
                    profile.user.email)

            if xls_parser_response.errors:
                info_list = list(xls_parser_response.errors)
                logger.info("User: %s. Edit upload Errors: %s",
                            request.user.username, json.dumps(info_list))

                return HttpResponse(
                    content_type='application/json',
                    content=json.dumps({
                        'success':
                        False,
                        'error_msg':
                        info_list,
                        'message_prefix':
                        _("Sorry! Current version of DataWinners does not support"
                          ),
                        'message_suffix':
                        _("Update your XLSForm and upload again.")
                    }))

            mangrove_service = MangroveService(
                request,
                questionnaire_code=questionnaire.form_code,
                project_name=questionnaire.name,
                xls_parser_response=xls_parser_response)

            questionnaire.xform = mangrove_service.xform_with_form_code
            QuestionnaireBuilder(questionnaire,
                                 manager).update_questionnaire_with_questions(
                                     xls_parser_response.json_xform_data)

            tmp_file.seek(0)
            questionnaire.update_media_field_flag()
            questionnaire.save(process_post_update=False)

            base_name, extension = os.path.splitext(tmp_file.name)
            questionnaire.update_attachments(tmp_file,
                                             'questionnaire%s' % extension)
            self._purge_submissions(manager, questionnaire)
            self._purge_feed_documents(questionnaire, request)
            self._purge_media_details_documents(manager, questionnaire)
            self.recreate_submissions_mapping(manager, questionnaire)
            if xls_parser_response.info:
                info_list = list(xls_parser_response.info)
                logger.info("User: %s. Edit upload Errors: %s",
                            request.user.username, json.dumps(info_list))
                return HttpResponse(content_type='application/json',
                                    content=json.dumps({
                                        'success':
                                        True,
                                        'information':
                                        info_list,
                                    }))
        except PyXFormError as e:
            logger.info("User: %s. Upload Error: %s", request.user.username,
                        e.message)

            message = transform_error_message(e.message)
            if 'name_type_error' in message or 'choice_name_type_error' in message:
                if 'choice_name_type_error' in message:
                    message_prefix = _(
                        "On your \"choices\" sheet the first and second column must be \"list_name\" and \"name\".  Possible errors:"
                    )
                else:
                    message_prefix = _(
                        "On your \"survey\" sheet the first and second column must be \"type\" and \"name\".  Possible errors:"
                    )
                return HttpResponse(
                    content_type='application/json',
                    content=json.dumps({
                        'success':
                        False,
                        'error_msg': [
                            _("Columns are missing"),
                            _("Column name is misspelled"),
                            _("Additional space in column name")
                        ],
                        'message_prefix':
                        message_prefix,
                        'message_suffix':
                        _("Update your XLSForm and upload again.")
                    }))
            else:
                return HttpResponse(
                    content_type='application/json',
                    content=json.dumps({
                        'success':
                        False,
                        'error_msg': [
                            message if message else ugettext(
                                "all XLSForm features. Please check the list of unsupported features."
                            )
                        ]
                    }))

        except QuestionAlreadyExistsException as e:
            logger.info("User: %s. Upload Error: %s", request.user.username,
                        e.message)

            return HttpResponse(
                content_type='application/json',
                content=json.dumps({
                    'success':
                    False,
                    'error_msg': [
                        _("Duplicate labels. All questions (labels) must be unique."
                          )
                    ],
                    'message_prefix':
                    _("Sorry! Current version of DataWinners does not support"
                      ),
                    'message_suffix':
                    _("Update your XLSForm and upload again.")
                }))

        except UnicodeDecodeError as e:
            logger.info("User: %s. Upload Error: %s", request.user.username,
                        e.message)

            return HttpResponse(
                content_type='application/json',
                content=json.dumps({
                    'success':
                    False,
                    'error_msg': [
                        _("Check your columns for errors.<br>There are missing symbols (like $ for relevant or calculate) or incorrect characters<br>"
                          ) + _("Update your XLSForm and upload again.")
                    ],
                }))

        except Exception as e:

            logger.info("User: %s. Edit Upload Exception message: %s",
                        request.user.username, e.message)

            message = e.message if e.message else _("Some error in excel")
            odk_message = ''
            if not 'ODK Validate Errors:' in e.message:
                send_email_on_exception(
                    request.user,
                    "Questionnaire Edit",
                    traceback.format_exc(),
                    additional_details={'file_contents': file_content})
            else:
                odk_message = translate_odk_message(e.message)
            message = odk_message if odk_message else message
            return HttpResponse(content_type='application/json',
                                content=json.dumps({
                                    'error_msg': [message],
                                    'success': False,
                                }))

        finally:
            if tmp_file:
                tmp_file.close()

        return HttpResponse(
            json.dumps({
                "success":
                True,
                "project_name":
                questionnaire.name,
                "project_id":
                questionnaire.id,
                "file_name":
                "%s%s" % (slugify(questionnaire.name), extension),
                # "xls_dict": XlsProjectParser().parse(file_content)
            }),
            content_type='application/json')
Example #11
0
    def _overwrite(self, project_id, request):
        try:
            manager = get_database_manager(request.user)
            questionnaire = Project.get(manager, project_id)
            xls_parser_response = _try_parse_xls(manager, request,
                                                 questionnaire.name)
            if isinstance(xls_parser_response, HttpResponse):
                return xls_parser_response
            send_email_if_unique_id_type_question_has_no_registered_unique_ids(
                xls_parser_response, request, questionnaire.name)
            mangrove_service = MangroveService(
                request,
                questionnaire_code=questionnaire.form_code,
                project_name=questionnaire.name,
                xls_parser_response=xls_parser_response)
            questionnaire.xform = mangrove_service.xform_with_form_code
            QuestionnaireBuilder(questionnaire,
                                 manager).update_questionnaire_with_questions(
                                     xls_parser_response.json_xform_data)
            questionnaire.update_media_field_flag()
            questionnaire.save(process_post_update=False)
            UserActivityLog().log(self.request,
                                  action=EDITED_QUESTIONNAIRE,
                                  project=questionnaire.name,
                                  detail=questionnaire.name)
            tmp_file = _temp_file(request)
            base_name, extension = os.path.splitext(tmp_file.name)
            questionnaire.update_attachments(tmp_file,
                                             'questionnaire%s' % extension)
            questionnaire.update_external_itemset(
                mangrove_service.itemsets_csv)
            self._purge_submissions(manager, questionnaire)
            self._purge_feed_documents(questionnaire, request)
            self._purge_media_details_documents(manager, questionnaire)
            self.recreate_submissions_mapping(manager, questionnaire)
            excel_file = _temp_file(request)
            excel_file.seek(0)
            _save_questionnaire_as_dict_for_builder(questionnaire,
                                                    excel_file=excel_file)
            if xls_parser_response.info:
                info_list = list(xls_parser_response.info)
                logger.info("User: %s. Edit upload Errors: %s",
                            request.user.username, json.dumps(info_list))
                return HttpResponse(content_type='application/json',
                                    content=json.dumps({
                                        'success':
                                        True,
                                        'information':
                                        info_list,
                                    }))

        except QuestionAlreadyExistsException as e:
            return HttpResponse(
                content_type='application/json',
                content=json.dumps({
                    'success': False,
                    'error_msg': [_(e.message)],
                    "status": "error",
                    'reason': "Save Failed",  # TODO: i18n translation
                    'details': _(e.message)
                }))

        return HttpResponse(
            json.dumps({
                "success":
                True,
                "project_name":
                questionnaire.name,
                "project_id":
                questionnaire.id,
                "file_name":
                "%s%s" % (slugify(questionnaire.name), extension),
                # "xls_dict": XlsProjectParser().parse(file_content)
            }),
            content_type='application/json')
Example #12
0
def _edit_questionnaire(request,
                        project_id,
                        excel_file=None,
                        excel_as_dict=None):
    manager = get_database_manager(request.user)
    questionnaire = Project.get(manager, project_id)
    try:
        xls_parser_response = _try_parse_xls(manager, request,
                                             questionnaire.name, excel_file)

        if isinstance(xls_parser_response, HttpResponse):
            return xls_parser_response

        doc = deepcopy(questionnaire._doc)
        doc.xform = MangroveService(
            request,
            questionnaire_code=questionnaire.form_code,
            xls_parser_response=xls_parser_response).xform_with_form_code
        new_questionnaire = Project.new_from_doc(manager, doc)
        QuestionnaireBuilder(new_questionnaire,
                             manager).update_questionnaire_with_questions(
                                 xls_parser_response.json_xform_data)
        xform_rules = get_all_rules()
        if excel_file is None:
            excel_file = _temp_file(request)
        else:
            excel_file.seek(0)
        questionnaire_wrapper = Questionnaire(excel_file)
        activity_log_detail = {}
        XFormEditor(
            Submission(manager, get_database_name(request.user), xform_rules),
            Validator(xform_rules),
            questionnaire_wrapper).edit(new_questionnaire, questionnaire,
                                        activity_log_detail)
        questionnaire = Project.get(manager, project_id)
        _save_questionnaire_as_dict_for_builder(questionnaire, excel_as_dict,
                                                excel_file)
        UserActivityLog().log(request,
                              action=EDITED_QUESTIONNAIRE,
                              project=questionnaire.name,
                              detail=json.dumps(activity_log_detail))

    except UnsupportedXformEditException as e:
        return HttpResponse(
            content_type='application/json',
            content=json.dumps({
                'success': False,
                'unsupported': True,
                'error_msg': [_("Unsupported edit operation")],
                "status": "error",
                'reason':
                "Unsupported edit operation",  # TODO: i18n translation
                'details': e.message
            }))
    except QuestionAlreadyExistsException as e:
        return HttpResponse(
            content_type='application/json',
            content=json.dumps({
                'success': False,
                'error_msg': [_(e.message)],
                "status": "error",
                'reason': "Save Failed",  # TODO: i18n translation
                'details': _(e.message)
            }))
    return HttpResponse(
        json.dumps({
            "success": True,
            "status": "success",
            'reason': 'Successfully updated'  # TODO: i18n translation
        }),
        content_type='application/json')