Esempio n. 1
0
    def _create_new_account(self, reg_form):
        activate_new_user(reg_form, ip=get_ip(self.request))
        new_user = authenticate(username=reg_form.cleaned_data['email'],
                                password=reg_form.cleaned_data['password'])
        if 'phone_number' in reg_form.cleaned_data and reg_form.cleaned_data[
                'phone_number']:
            web_user = WebUser.get_by_username(new_user.username)
            web_user.phone_numbers.append(
                reg_form.cleaned_data['phone_number'])
            web_user.save()

        is_mobile = reg_form.cleaned_data.get('is_mobile')
        email = new_user.email

        properties = {}
        if is_mobile:
            toggles.MOBILE_SIGNUP_REDIRECT_AB_TEST_CONTROLLER.set(email, True)
            variation = toggles.MOBILE_SIGNUP_REDIRECT_AB_TEST.enabled(
                email, toggles.NAMESPACE_USER)
            properties = {
                "mobile_signups_test_march2018test":
                "variation" if variation else "control"
            }

        track_workflow(email, "Requested new account", properties)
        login(self.request, new_user)
Esempio n. 2
0
    def _create_new_account(self, reg_form):
        activate_new_user(reg_form, ip=get_ip(self.request))
        new_user = authenticate(username=reg_form.cleaned_data['email'],
                                password=reg_form.cleaned_data['password'])
        web_user = WebUser.get_by_username(new_user.username)

        if 'phone_number' in reg_form.cleaned_data and reg_form.cleaned_data[
                'phone_number']:
            web_user.phone_numbers.append(
                reg_form.cleaned_data['phone_number'])
            web_user.save()

        email = new_user.email

        # registration analytics
        persona = reg_form.cleaned_data['persona']
        persona_other = reg_form.cleaned_data['persona_other']
        appcues_ab_test = toggles.APPCUES_AB_TEST.enabled(
            web_user.username, toggles.NAMESPACE_USER)

        track_workflow(email, "Requested New Account")
        track_workflow(email, "Persona Field Filled Out", {
            'personachoice': persona,
            'personaother': persona_other,
        })

        track_web_user_registration_hubspot.delay(
            web_user, {
                'buyer_persona': persona,
                'buyer_persona_other': persona_other,
                "appcues_test": "On" if appcues_ab_test else "Off",
            })

        login(self.request, new_user)
Esempio n. 3
0
    def post(self, request, *args, **kwargs):
        if self.form.is_valid():
            app_source = self.form.get_selected_source()
            url_names_map = {
                'list': 'configure_list_report',
                'chart': 'configure_chart_report',
                'table': 'configure_table_report',
                'worker': 'configure_worker_report',
                'map': 'configure_map_report',
            }
            url_name = url_names_map[self.report_type]
            get_params = {
                'report_name': self.form.cleaned_data['report_name'],
                'chart_type': self.form.cleaned_data['chart_type'],
                'application': app_source.application,
                'source_type': app_source.source_type,
                'source': app_source.source,
            }
            track_workflow(
                request.user.email,
                "Successfully submitted the first part of the Report Builder "
                "wizard where you give your report a name and choose a data source"
            )

            add_event(request, [
                "Report Builder",
                "Successful Click on Next (Data Source)",
                app_source.source_type,
            ])

            return HttpResponseRedirect(
                reverse(url_name, args=[self.domain], params=get_params))
        else:
            return self.get(request, *args, **kwargs)
Esempio n. 4
0
    def send_preparation_analytics(self, export_instances, export_filters):
        send_hubspot_form(HUBSPOT_DOWNLOADED_EXPORT_FORM_ID, self.request)

        track_workflow(self.request.couch_user.username, 'Downloaded {} Exports With {}Data'.format(
            self.model[0].upper() + self.model[1:],
            '' if any(get_export_size(instance, export_filters) > 0 for instance in export_instances) else 'No ',
        ))
Esempio n. 5
0
    def update_linked_model(self, in_data):
        model = in_data['model']
        type_ = model['type']
        detail = model['detail']
        detail_obj = wrap_detail(type_, detail) if detail else None

        master_link = get_domain_master_link(self.domain)
        error = ""
        try:
            update_model_type(master_link, type_, detail_obj)
            model_detail = detail_obj.to_json() if detail_obj else None
            master_link.update_last_pull(type_,
                                         self.request.couch_user._id,
                                         model_detail=model_detail)
        except (DomainLinkError, UnsupportedActionError) as e:
            error = str(e)

        track_workflow(self.request.couch_user.username,
                       "Linked domain: updated '{}' model".format(type_))

        timezone = get_timezone_for_request()
        return {
            'success': not error,
            'error': error,
            'last_update': server_to_user_time(master_link.last_pull, timezone)
        }
Esempio n. 6
0
def _track_build_for_app_preview(domain, couch_user, app_id, message):
    track_workflow(couch_user.username, message, properties={
        'domain': domain,
        'app_id': app_id,
        'is_dimagi': couch_user.is_dimagi,
        'preview_app_enabled': True,
    })
Esempio n. 7
0
def pull_master_app(request, domain, app_id):
    async_update = request.POST.get('notify') == 'on'
    if async_update:
        update_linked_app_and_notify_task.delay(domain, app_id,
                                                request.couch_user.get_id,
                                                request.couch_user.email)
        messages.success(
            request,
            _('Your request has been submitted. We will notify you via email once completed.'
              ))
    else:
        app = get_current_app(domain, app_id)
        try:
            update_linked_app(app, request.couch_user.get_id)
        except AppLinkError as e:
            messages.error(request, six.text_type(e))
            return HttpResponseRedirect(
                reverse_util('app_settings', params={}, args=[domain, app_id]))
        messages.success(
            request,
            _('Your linked application was successfully updated to the latest version.'
              ))
    track_workflow(request.couch_user.username,
                   "Linked domain: master app pulled")
    return HttpResponseRedirect(
        reverse_util('app_settings', params={}, args=[domain, app_id]))
Esempio n. 8
0
    def _process_invitation(request, invitation, web_user, is_new_user=False):
        """
        Processes the Invitation (if available) and sets up the user in the
        new domain they were invited to.
        :param request: HttpRequest
        :param invitation: Invitation or None
        :param web_user: WebUser
        """
        if invitation.is_expired:
            request.sso_new_user_messages['error'].append(
                _("Could not accept invitation because it is expired.")
            )
            return

        invitation.accept_invitation_and_join_domain(web_user)
        request.sso_new_user_messages['success'].append(
            _('You have been added to the "{}" project space.').format(
                invitation.domain,
            )
        )

        if settings.IS_SAAS_ENVIRONMENT and is_new_user:
            track_workflow(
                web_user.username,
                "New User Accepted a project invitation with SSO",
                {"New User Accepted a project invitation": "yes"}
            )
            send_hubspot_form(
                HUBSPOT_NEW_USER_INVITE_FORM,
                request,
                user=web_user
            )
Esempio n. 9
0
def _track_build_for_app_preview(domain, couch_user, app_id, message):
    track_workflow(couch_user.username, message, properties={
        'domain': domain,
        'app_id': app_id,
        'is_dimagi': couch_user.is_dimagi,
        'preview_app_enabled': True,
    })
Esempio n. 10
0
    def send_preparation_analytics(self, export_instances, export_filters):
        send_hubspot_form(HUBSPOT_DOWNLOADED_EXPORT_FORM_ID, self.request)

        track_workflow(self.request.couch_user.username, 'Downloaded {} Exports With {}Data'.format(
            self.model[0].upper() + self.model[1:],
            '' if any(get_export_size(instance, export_filters) > 0 for instance in export_instances) else 'No ',
        ))
Esempio n. 11
0
    def commit(self, request):
        export = self.export_instance_cls.wrap(
            json.loads(request.body.decode('utf-8')))
        if (self.domain != export.domain
                or (export.export_format == "html"
                    and not domain_has_privilege(self.domain, EXCEL_DASHBOARD))
                or
            (export.is_daily_saved_export
             and not domain_has_privilege(self.domain, DAILY_SAVED_EXPORT))):
            raise BadExportConfiguration()

        if not export._rev:
            if toggles.EXPORT_OWNERSHIP.enabled(request.domain):
                export.owner_id = request.couch_user.user_id
            if getattr(settings, "ENTERPRISE_MODE"):
                # default auto rebuild to False for enterprise clusters
                # only do this on first save to prevent disabling on every edit
                export.auto_rebuild_enabled = False

        if export.is_odata_config:
            for table_id, table in enumerate(export.tables):
                labels = []
                for column in table.columns:
                    is_reserved_number = (column.label == 'number'
                                          and table_id > 0 and table.selected)
                    if ((column.label in ['formid', 'caseid']
                         and PROPERTY_TAG_INFO in column.tags)
                            or is_reserved_number):
                        column.selected = True
                    elif (column.label in ['formid', 'caseid']
                          and PROPERTY_TAG_INFO not in column.tags):
                        # make sure hidden (eg deleted) labels that are
                        # formid/caseid are never selected
                        column.selected = False

                    if column.label not in labels and column.selected:
                        labels.append(column.label)
                    elif column.selected:
                        raise ExportODataDuplicateLabelException(
                            _("Column labels must be unique. "
                              "'{}' appears more than once.").format(
                                  column.label))
            num_nodes = sum(
                [1 for table in export.tables[1:] if table.selected])
            if hasattr(self, 'is_copy') and self.is_copy:
                event_title = "[BI Integration] Clicked Save button for feed copy"
            else:
                event_title = "[BI Integration] Clicked Save button for feed creation"
            track_workflow(
                request.user.username, event_title, {
                    "Feed Type": export.type,
                    "Number of additional nodes": num_nodes,
                })

        export.save()
        messages.success(
            request,
            mark_safe(
                _("Export <strong>{}</strong> saved.").format(export.name)))
        return export._id
Esempio n. 12
0
 def post(self, request, *args, **kwargs):
     if self.form.is_valid():
         app_source = self.form.get_selected_source()
         url_names_map = {
             'list': 'configure_list_report',
             'chart': 'configure_chart_report',
             'table': 'configure_table_report',
             'worker': 'configure_worker_report',
             'map': 'configure_map_report',
         }
         url_name = url_names_map[self.report_type]
         get_params = {
             'report_name': self.form.cleaned_data['report_name'],
             'chart_type': self.form.cleaned_data['chart_type'],
             'application': app_source.application,
             'source_type': app_source.source_type,
             'source': app_source.source,
         }
         track_workflow(
             request.user.email,
             "Successfully submitted the first part of the Report Builder "
             "wizard where you give your report a name and choose a data source"
         )
         return HttpResponseRedirect(
             reverse(url_name, args=[self.domain]) + '?' + urlencode(get_params)
         )
     else:
         return self.get(request, *args, **kwargs)
Esempio n. 13
0
    def _process_new_user_data(request, new_web_user):
        """
        If available, this makes sure we apply any relevant user data
        :param request: HttpRequest
        :param new_web_user: WebUser
        :return:
        """
        user_data = get_new_sso_user_data_from_session(request)
        if not user_data:
            return

        phone_number = user_data['phone_number']
        if phone_number:
            new_web_user.phone_numbers.append(phone_number)
            new_web_user.save()

        if settings.IS_SAAS_ENVIRONMENT:
            track_workflow(new_web_user.username,
                           "Requested New Account via SSO", {
                               'environment': settings.SERVER_ENVIRONMENT,
                           })
            track_workflow(
                new_web_user.username, "Persona Field Filled Out via SSO", {
                    'personachoice': user_data['persona'],
                    'personaother': user_data['persona_other'],
                })
            track_web_user_registration_hubspot(
                request,
                new_web_user,
                user_data['additional_hubspot_data'],
            )
Esempio n. 14
0
 def dispatch(self, request_type, request, **kwargs):
     if toggles.API_BLACKLIST.enabled_for_request(request):
         msg = ("API access has been temporarily cut off due to too many "
                "requests.  To re-enable, please contact support.")
         raise ImmediateHttpResponse(
             HttpResponse(json.dumps({"error": msg}),
                          content_type="application/json",
                          status=401))
     if request.user.is_superuser or domain_has_privilege(
             request.domain, privileges.API_ACCESS):
         if isinstance(self, DomainSpecificResourceMixin):
             track_workflow(
                 request.user.username,
                 "API Request",
                 properties={
                     'domain': request.domain,
                     'is_dimagi':
                     request.user.username.endswith('@dimagi.com'),
                 })
         return super(HqBaseResource,
                      self).dispatch(request_type, request, **kwargs)
     else:
         raise ImmediateHttpResponse(
             HttpResponse(json.dumps({
                 "error":
                 "Your current subscription does not have access to this feature"
             }),
                          content_type="application/json",
                          status=401))
Esempio n. 15
0
def confirm_domain(request, guid=None):
    error = None
    # Did we get a guid?
    if guid is None:
        error = _(
            'An account activation key was not provided.  If you think this '
            'is an error, please contact the system administrator.')

    # Does guid exist in the system?
    else:
        req = RegistrationRequest.get_by_guid(guid)
        if not req:
            error = _(
                'The account activation key "%s" provided is invalid. If you '
                'think this is an error, please contact the system '
                'administrator.') % guid

    if error is not None:
        context = {
            'message_body': error,
            'current_page': {
                'page_name': 'Account Not Activated'
            },
        }
        return render(request, 'registration/confirmation_error.html', context)

    requested_domain = Domain.get_by_name(req.domain)

    # Has guid already been confirmed?
    if requested_domain.is_active:
        assert (req.confirm_time is not None and req.confirm_ip is not None)
        messages.success(
            request, 'Your account %s has already been activated. '
            'No further validation is required.' % req.new_user_username)
        return HttpResponseRedirect(
            reverse("dashboard_default", args=[requested_domain]))

    # Set confirm time and IP; activate domain and new user who is in the
    req.confirm_time = datetime.utcnow()
    req.confirm_ip = get_ip(request)
    req.save()
    requested_domain.is_active = True
    requested_domain.save()
    requesting_user = WebUser.get_by_username(req.new_user_username)

    send_new_request_update_email(requesting_user,
                                  get_ip(request),
                                  requested_domain.name,
                                  is_confirming=True)

    messages.success(
        request,
        'Your account has been successfully activated.  Thank you for taking '
        'the time to confirm your email address: %s.' %
        (requesting_user.username))
    track_workflow(requesting_user.email, "Confirmed new project")
    track_confirmed_account_on_hubspot.delay(requesting_user)
    return HttpResponseRedirect(
        reverse("dashboard_default", args=[requested_domain]))
Esempio n. 16
0
 def _create_new_account(self, reg_form):
     activate_new_user(reg_form, ip=get_ip(self.request))
     new_user = authenticate(
         username=reg_form.cleaned_data['email'],
         password=reg_form.cleaned_data['password']
     )
     track_workflow(new_user.email, "Requested new account")
     login(self.request, new_user)
Esempio n. 17
0
    def create_new_export_instance(self, schema, username, export_settings=None):
        export = self.export_instance_cls.generate_instance_from_schema(schema, export_settings=export_settings)

        track_workflow(username, f'{self.metric_name} - Clicked Add Export Popup', properties={
            'domain': self.domain
        })

        return export
Esempio n. 18
0
def app_from_template(request, domain, slug):
    send_hubspot_form(HUBSPOT_APP_TEMPLATE_FORM_ID, request)
    track_workflow(request.couch_user.username, "User created an application from a template")
    clear_app_cache(request, domain)

    build = load_app_from_slug(domain, request.user.username, slug)
    cloudcare_state = '{{"appId":"{}"}}'.format(build._id)
    return HttpResponseRedirect(reverse(FormplayerMain.urlname, args=[domain]) + '#' + cloudcare_state)
Esempio n. 19
0
def app_from_template(request, domain, slug):
    send_hubspot_form(HUBSPOT_APP_TEMPLATE_FORM_ID, request)
    track_workflow(request.couch_user.username, "User created an application from a template")
    clear_app_cache(request, domain)

    build = load_app_from_slug(domain, request.user.username, slug)
    cloudcare_state = '{{"appId":"{}"}}'.format(build._id)
    return HttpResponseRedirect(reverse(FormplayerMain.urlname, args=[domain]) + '#' + cloudcare_state)
Esempio n. 20
0
 def _track_new_report_events(self):
     track_workflow(
         self.request.user.email,
         "Successfully created a new report in the Report Builder")
     add_event(self.request, [
         "Report Builder",
         "Click On Done On New Report (Successfully)",
         self.report_type,
     ])
Esempio n. 21
0
def register_user(request):
    prefilled_email = request.GET.get('e', '')
    context = get_domain_context()

    if request.user.is_authenticated():
        # Redirect to a page which lets user choose whether or not to create a new account
        domains_for_user = Domain.active_for_user(request.user)
        if len(domains_for_user) == 0:
            return redirect("registration_domain")
        else:
            return redirect("homepage")
    else:
        if request.method == 'POST':
            form = NewWebUserRegistrationForm(request.POST)
            if form.is_valid():
                activate_new_user(form, ip=get_ip(request))
                new_user = authenticate(username=form.cleaned_data['email'],
                                        password=form.cleaned_data['password'])

                track_workflow(new_user.email, "Requested new account")

                login(request, new_user)

                requested_domain = form.cleaned_data['hr_name']
                if form.cleaned_data['create_domain']:
                    try:
                        requested_domain = request_new_domain(
                            request, form, is_new_user=True)
                    except NameUnavailableException:
                        context.update({
                            'current_page': {'page_name': _('Oops!')},
                            'error_msg': _('Project name already taken - please try another'),
                            'show_homepage_link': 1
                        })
                        return render(request, 'error.html', context)

                context.update({
                    'requested_domain': requested_domain,
                    'track_domain_registration': True,
                    'current_page': {'page_name': _('Confirmation Email Sent')},
                })
                return render(request, 'registration/confirmation_sent.html', context)
            context.update({'create_domain': form.cleaned_data['create_domain']})
        else:
            form = NewWebUserRegistrationForm(
                initial={'email': prefilled_email, 'create_domain': True})
            context.update({'create_domain': True})
            meta = get_meta(request)
            track_clicked_signup_on_hubspot(prefilled_email, request.COOKIES, meta)

        context.update({
            'form': form,
            'current_page': {'page_name': _('Create an Account')},
            'hide_password_feedback': settings.ENABLE_DRACONIAN_SECURITY_FEATURES,
            'is_register_user': True,
        })
        return render(request, 'registration/create_new_user.html', context)
Esempio n. 22
0
def confirm_domain(request, guid=None):
    error = None
    # Did we get a guid?
    if guid is None:
        error = _('An account activation key was not provided.  If you think this '
                  'is an error, please contact the system administrator.')

    # Does guid exist in the system?
    else:
        req = RegistrationRequest.get_by_guid(guid)
        if not req:
            error = _('The account activation key "%s" provided is invalid. If you '
                      'think this is an error, please contact the system '
                      'administrator.') % guid

    if error is not None:
        context = {
            'message_body': error,
            'current_page': {'page_name': 'Account Not Activated'},
        }
        return render(request, 'registration/confirmation_error.html', context)

    requested_domain = Domain.get_by_name(req.domain)

    # Has guid already been confirmed?
    if requested_domain.is_active:
        assert(req.confirm_time is not None and req.confirm_ip is not None)
        messages.success(request, 'Your account %s has already been activated. '
            'No further validation is required.' % req.new_user_username)
        return HttpResponseRedirect(reverse("dashboard_default", args=[requested_domain]))

    # Set confirm time and IP; activate domain and new user who is in the
    req.confirm_time = datetime.utcnow()
    req.confirm_ip = get_ip(request)
    req.save()
    requested_domain.is_active = True
    requested_domain.save()
    requesting_user = WebUser.get_by_username(req.new_user_username)

    send_new_request_update_email(requesting_user, get_ip(request), requested_domain.name, is_confirming=True)

    messages.success(request,
            'Your account has been successfully activated.  Thank you for taking '
            'the time to confirm your email address: %s.'
        % (requesting_user.username))
    track_workflow(requesting_user.email, "Confirmed new project")
    track_confirmed_account_on_hubspot.delay(requesting_user)
    url = reverse("dashboard_default", args=[requested_domain])

    # If user already created an app (via prelogin demo), send them there
    apps = get_apps_in_domain(requested_domain.name, include_remote=False)
    if len(apps) == 1:
        app = apps[0]
        if len(app.modules) == 1 and len(app.modules[0].forms) == 1:
            url = reverse('form_source', args=[requested_domain.name, app.id, 0, 0])

    return HttpResponseRedirect(url)
Esempio n. 23
0
    def post(self, request, *args, **kwargs):
        referer_url = request.GET.get('referer', '')
        nextpage = request.POST.get('next')
        form = DomainRegistrationForm(request.POST)
        context = self.get_context_data(form=form)
        if form.is_valid():
            reqs_today = RegistrationRequest.get_requests_today()
            max_req = settings.DOMAIN_MAX_REGISTRATION_REQUESTS_PER_DAY
            if reqs_today >= max_req:
                context.update({
                    'current_page': {
                        'page_name': _('Oops!')
                    },
                    'error_msg':
                    _('Number of domains requested today exceeds limit (%d) - contact Dimagi'
                      ) % max_req,
                    'show_homepage_link':
                    1
                })
                return render(request, 'error.html', context)

            try:
                domain_name = request_new_domain(request,
                                                 form,
                                                 is_new_user=self.is_new_user)
            except NameUnavailableException:
                context.update({
                    'current_page': {
                        'page_name': _('Oops!')
                    },
                    'error_msg':
                    _('Project name already taken - please try another'),
                    'show_homepage_link':
                    1
                })
                return render(request, 'error.html', context)

            if self.is_new_user:
                context.update({
                    'requested_domain': domain_name,
                    'current_page': {
                        'page_name': _('Confirm Account')
                    },
                })
                track_workflow(self.request.user.email, "Created new project")
                return render(request, 'registration/confirmation_sent.html',
                              context)
            else:
                if nextpage:
                    return HttpResponseRedirect(nextpage)
                if referer_url:
                    return redirect(referer_url)
                return HttpResponseRedirect(
                    reverse("domain_homepage", args=[domain_name]))

        return self.render_to_response(context)
Esempio n. 24
0
def download_daily_saved_export(req, domain, export_instance_id):
    with CriticalSection(
        ['export-last-accessed-{}'.format(export_instance_id)]):
        try:
            export_instance = get_properly_wrapped_export_instance(
                export_instance_id)
        except ResourceNotFound:
            raise Http404(_("Export not found"))

        assert domain == export_instance.domain

        if export_instance.export_format == "html":
            if not domain_has_privilege(domain, EXCEL_DASHBOARD):
                raise Http404
        elif export_instance.is_daily_saved_export:
            if not domain_has_privilege(domain, DAILY_SAVED_EXPORT):
                raise Http404

        if not export_instance.filters.is_location_safe_for_user(req):
            return location_restricted_response(req)

        if not can_download_daily_saved_export(export_instance, domain,
                                               req.couch_user):
            raise Http404

        if export_instance.export_format == "html":
            message = "Download Excel Dashboard"
        else:
            message = "Download Saved Export"
        track_workflow(req.couch_user.username,
                       message,
                       properties={
                           'domain': domain,
                           'is_dimagi': req.couch_user.is_dimagi
                       })

        if should_update_export(export_instance.last_accessed):
            try:
                rebuild_saved_export(export_instance_id, manual=False)
            except Exception:
                notify_exception(
                    req,
                    'Failed to rebuild export during download',
                    {
                        'export_instance_id': export_instance_id,
                        'domain': domain,
                    },
                )

        export_instance.last_accessed = datetime.utcnow()
        export_instance.save()

    payload = export_instance.get_payload(stream=True)
    format = Format.from_format(export_instance.export_format)
    return get_download_response(payload, export_instance.file_size, format,
                                 export_instance.filename, req)
Esempio n. 25
0
def _track_build_for_app_preview(domain, couch_user, app_id, message):
    track_workflow(couch_user.username, message, properties={
        'domain': domain,
        'app_id': app_id,
        'is_dimagi': couch_user.is_dimagi,
        'preview_app_enabled': (
            toggles.PREVIEW_APP.enabled(domain) or
            toggles.PREVIEW_APP.enabled(couch_user.username)
        )
    })
Esempio n. 26
0
 def clean_password(self):
     if settings.ENFORCE_SSO_LOGIN and self.is_sso:
         # This field is not used with SSO. A randomly generated
         # password as a fallback is created in SsoBackend.
         return
     try:
         return clean_password(self.cleaned_data.get('password'))
     except forms.ValidationError:
         track_workflow(self.cleaned_data.get('email'), 'Password Failure')
         raise
Esempio n. 27
0
 def rows(self):
     track_workflow(self.request.couch_user.username, "Case List Explorer: Search Performed")
     send_email_to_dev_more(
         self.domain,
         self.request.couch_user.username,
         XpathCaseSearchFilter.get_value(self.request, self.domain),
         self.es_results['hits'].get('total', 0)
     )
     data = (flatten_result(row) for row in self.es_results['hits'].get('hits', []))
     return self._get_rows(data)
Esempio n. 28
0
 def rows(self):
     track_workflow(self.request.couch_user.username,
                    "Case List Explorer: Search Performed")
     send_email_to_dev_more(
         self.domain, self.request.couch_user.username,
         XpathCaseSearchFilter.get_value(self.request, self.domain),
         self.es_results['hits'].get('total', 0))
     data = (flatten_result(row)
             for row in self.es_results['hits'].get('hits', []))
     return self._get_rows(data)
Esempio n. 29
0
 def _track_new_report_events(self):
     track_workflow(
         self.request.user.email,
         "Successfully created a new report in the Report Builder"
     )
     add_event(self.request, [
         "Report Builder",
         "Click On Done On New Report (Successfully)",
         self.report_type,
     ])
Esempio n. 30
0
def _track_build_for_app_preview(domain, couch_user, app_id, message):
    track_workflow(couch_user.username, message, properties={
        'domain': domain,
        'app_id': app_id,
        'is_dimagi': couch_user.is_dimagi,
        'preview_app_enabled': (
            toggles.PREVIEW_APP.enabled(domain) or
            toggles.PREVIEW_APP.enabled(couch_user.username)
        )
    })
Esempio n. 31
0
    def create_domain_link(self, in_data):
        domain_to_link = in_data['downstream_domain']
        try:
            domain_link = link_domains(self.request.couch_user, self.domain, domain_to_link)
        except (DomainDoesNotExist, DomainLinkAlreadyExists, DomainLinkNotAllowed, DomainLinkError) as e:
            return {'success': False, 'message': str(e)}

        track_workflow(self.request.couch_user.username, "Linked domain: domain link created")

        domain_link_view_model = build_domain_link_view_model(domain_link, get_timezone_for_request())
        return {'success': True, 'domain_link': domain_link_view_model}
Esempio n. 32
0
    def delete_domain_link(self, in_data):
        linked_domain = in_data['linked_domain']
        link = DomainLink.objects.filter(linked_domain=linked_domain, master_domain=self.domain).first()
        link.deleted = True
        link.save()

        track_workflow(self.request.couch_user.username, "Linked domain: domain link deleted")

        return {
            'success': True,
        }
Esempio n. 33
0
    def delete_domain_link(self, in_data):
        linked_domain = in_data['linked_domain']
        link = DomainLink.objects.filter(linked_domain=linked_domain, master_domain=self.domain).first()
        link.deleted = True
        link.save()

        track_workflow(self.request.couch_user.username, "Linked domain: domain link deleted")

        return {
            'success': True,
        }
Esempio n. 34
0
 def _create_new_account(self, reg_form):
     activate_new_user(reg_form, ip=get_ip(self.request))
     new_user = authenticate(username=reg_form.cleaned_data['email'],
                             password=reg_form.cleaned_data['password'])
     if 'phone_number' in reg_form.cleaned_data and reg_form.cleaned_data[
             'phone_number']:
         web_user = WebUser.get_by_username(new_user.username)
         web_user.phone_numbers.append(
             reg_form.cleaned_data['phone_number'])
         web_user.save()
     track_workflow(new_user.email, "Requested new account")
     login(self.request, new_user)
Esempio n. 35
0
    def _create_new_account(self, reg_form, additional_hubspot_data=None):
        activate_new_user_via_reg_form(reg_form,
                                       created_by=None,
                                       created_via=USER_CHANGE_VIA_WEB,
                                       ip=get_ip(self.request))
        new_user = authenticate(username=reg_form.cleaned_data['email'],
                                password=reg_form.cleaned_data['password'],
                                request=self.request)
        web_user = WebUser.get_by_username(new_user.username, strict=True)

        if 'phone_number' in reg_form.cleaned_data and reg_form.cleaned_data[
                'phone_number']:
            web_user.phone_numbers.append(
                reg_form.cleaned_data['phone_number'])
            web_user.save()

        if settings.IS_SAAS_ENVIRONMENT:
            email = new_user.email

            # registration analytics
            # only do anything with this in a SAAS environment

            persona = reg_form.cleaned_data['persona']
            persona_other = reg_form.cleaned_data['persona_other']

            track_workflow(email, "Requested New Account", {
                'environment': settings.SERVER_ENVIRONMENT,
            })
            track_workflow(email, "Persona Field Filled Out", {
                'personachoice': persona,
                'personaother': persona_other,
            })

            if not additional_hubspot_data:
                additional_hubspot_data = {}
            additional_hubspot_data.update({
                'buyer_persona':
                persona,
                'buyer_persona_other':
                persona_other,
            })
            track_web_user_registration_hubspot(self.request, web_user,
                                                additional_hubspot_data)
            if not persona or (persona == 'Other' and not persona_other):
                # There shouldn't be many instances of this.
                _assert = soft_assert('@'.join(['bbuczyk', 'dimagi.com']),
                                      exponential_backoff=False)
                _assert(
                    False, "[BAD PERSONA DATA] Persona fields during "
                    "login submitted empty. User: {}".format(email))

        login(self.request, new_user)
Esempio n. 36
0
    def post(self, request, *args, **kwargs):
        referer_url = request.GET.get('referer', '')
        nextpage = request.POST.get('next')
        form = DomainRegistrationForm(request.POST)
        context = self.get_context_data(form=form)
        if not form.is_valid():
            return self.render_to_response(context)

        if settings.RESTRICT_DOMAIN_CREATION and not request.user.is_superuser:
            context.update({
                'current_page': {'page_name': _('Oops!')},
                'error_msg': _('Your organization has requested that project creation be restricted. '
                               'For more information, please speak to your administrator.'),
            })
            return render(request, 'error.html', context)

        reqs_today = RegistrationRequest.get_requests_today()
        max_req = settings.DOMAIN_MAX_REGISTRATION_REQUESTS_PER_DAY
        if reqs_today >= max_req:
            context.update({
                'current_page': {'page_name': _('Oops!')},
                'error_msg': _(
                    'Number of projects requested today exceeds limit (%d) - contact Dimagi'
                ) % max_req,
                'show_homepage_link': 1
            })
            return render(request, 'error.html', context)

        try:
            domain_name = request_new_domain(request, form, is_new_user=self.is_new_user)
        except NameUnavailableException:
            context.update({
                'current_page': {'page_name': _('Oops!')},
                'error_msg': _('Project name already taken - please try another'),
                'show_homepage_link': 1
            })
            return render(request, 'error.html', context)

        if self.is_new_user:
            context.update({
                'requested_domain': domain_name,
                'current_page': {'page_name': _('Confirm Account')},
            })
            track_workflow(self.request.user.email, "Created new project")
            return render(request, 'registration/confirmation_sent.html', context)

        if nextpage:
            return HttpResponseRedirect(nextpage)
        if referer_url:
            return redirect(referer_url)
        return HttpResponseRedirect(reverse("domain_homepage", args=[domain_name]))
Esempio n. 37
0
def download_daily_saved_export(req, domain, export_instance_id):
    with CriticalSection(['export-last-accessed-{}'.format(export_instance_id)]):
        try:
            export_instance = get_properly_wrapped_export_instance(export_instance_id)
        except ResourceNotFound:
            raise Http404(_("Export not found"))

        assert domain == export_instance.domain

        if export_instance.export_format == "html":
            if not domain_has_privilege(domain, EXCEL_DASHBOARD):
                raise Http404
        elif export_instance.is_daily_saved_export:
            if not domain_has_privilege(domain, DAILY_SAVED_EXPORT):
                raise Http404

        if not export_instance.filters.is_location_safe_for_user(req):
            return location_restricted_response(req)

        if not can_download_daily_saved_export(export_instance, domain, req.couch_user):
            raise Http404

        if export_instance.export_format == "html":
            message = "Download Excel Dashboard"
        else:
            message = "Download Saved Export"
        track_workflow(req.couch_user.username, message, properties={
            'domain': domain,
            'is_dimagi': req.couch_user.is_dimagi
        })

        if should_update_export(export_instance.last_accessed):
            try:
                rebuild_saved_export(export_instance_id, manual=False)
            except Exception:
                notify_exception(
                    req,
                    'Failed to rebuild export during download',
                    {
                        'export_instance_id': export_instance_id,
                        'domain': domain,
                    },
                )

        export_instance.last_accessed = datetime.utcnow()
        export_instance.save()

    payload = export_instance.get_payload(stream=True)
    format = Format.from_format(export_instance.export_format)
    return get_download_response(payload, export_instance.file_size, format, export_instance.filename, req)
Esempio n. 38
0
    def _create_new_account(self, reg_form, additional_hubspot_data=None):
        activate_new_user(reg_form, ip=get_ip(self.request))
        new_user = authenticate(
            username=reg_form.cleaned_data['email'],
            password=reg_form.cleaned_data['password']
        )
        web_user = WebUser.get_by_username(new_user.username, strict=True)

        if 'phone_number' in reg_form.cleaned_data and reg_form.cleaned_data['phone_number']:
            web_user.phone_numbers.append(reg_form.cleaned_data['phone_number'])
            web_user.save()

        if settings.IS_SAAS_ENVIRONMENT:
            email = new_user.email

            # registration analytics
            # only do anything with this in a SAAS environment

            persona = reg_form.cleaned_data['persona']
            persona_other = reg_form.cleaned_data['persona_other']

            track_workflow(email, "Requested New Account", {
                'environment': settings.SERVER_ENVIRONMENT,
            })
            track_workflow(email, "Persona Field Filled Out", {
                'personachoice': persona,
                'personaother': persona_other,
            })

            if not additional_hubspot_data:
                additional_hubspot_data = {}
            additional_hubspot_data.update({
                'buyer_persona': persona,
                'buyer_persona_other': persona_other,
            })
            track_web_user_registration_hubspot(
                self.request,
                web_user,
                additional_hubspot_data
            )
            if not persona or (persona == 'Other' and not persona_other):
                # There shouldn't be many instances of this.
                _assert = soft_assert('@'.join(['bbuczyk', 'dimagi.com']), exponential_backoff=False)
                _assert(
                    False,
                    "[BAD PERSONA DATA] Persona fields during "
                    "login submitted empty. User: {}".format(email)
                )

        login(self.request, new_user)
Esempio n. 39
0
def confirm_domain(request, guid=None):
    error = None
    # Did we get a guid?
    if guid is None:
        error = _('An account activation key was not provided.  If you think this '
                  'is an error, please contact the system administrator.')

    # Does guid exist in the system?
    else:
        req = RegistrationRequest.get_by_guid(guid)
        if not req:
            error = _('The account activation key "%s" provided is invalid. If you '
                      'think this is an error, please contact the system '
                      'administrator.') % guid

    if error is not None:
        context = {
            'message_title': _('Account not activated'),
            'message_subtitle': _('Email not yet confirmed'),
            'message_body': error,
        }
        return render(request, 'registration/confirmation_error.html', context)

    requested_domain = Domain.get_by_name(req.domain)

    # Has guid already been confirmed?
    if requested_domain.is_active:
        assert(req.confirm_time is not None and req.confirm_ip is not None)
        messages.success(request, 'Your account %s has already been activated. '
            'No further validation is required.' % req.new_user_username)
        return HttpResponseRedirect(reverse("dashboard_default", args=[requested_domain]))

    # Set confirm time and IP; activate domain and new user who is in the
    req.confirm_time = datetime.utcnow()
    req.confirm_ip = get_ip(request)
    req.save()
    requested_domain.is_active = True
    requested_domain.save()
    requesting_user = WebUser.get_by_username(req.new_user_username)

    send_new_request_update_email(requesting_user, get_ip(request), requested_domain.name, is_confirming=True)

    messages.success(request,
            'Your account has been successfully activated.  Thank you for taking '
            'the time to confirm your email address: %s.'
        % (requesting_user.username))
    track_workflow(requesting_user.email, "Confirmed new project")
    track_confirmed_account_on_hubspot.delay(requesting_user)
    return HttpResponseRedirect(reverse("dashboard_default", args=[requested_domain]))
Esempio n. 40
0
def pull_master_app(request, domain, app_id):
    async_update = request.POST.get('notify') == 'on'
    if async_update:
        update_linked_app_and_notify_task.delay(domain, app_id, request.couch_user.get_id, request.couch_user.email)
        messages.success(request,
                         _('Your request has been submitted. We will notify you via email once completed.'))
    else:
        app = get_current_app(domain, app_id)
        try:
            update_linked_app(app, request.couch_user.get_id)
        except AppLinkError as e:
            messages.error(request, six.text_type(e))
            return HttpResponseRedirect(reverse_util('app_settings', params={}, args=[domain, app_id]))
        messages.success(request, _('Your linked application was successfully updated to the latest version.'))
    track_workflow(request.couch_user.username, "Linked domain: master app pulled")
    return HttpResponseRedirect(reverse_util('app_settings', params={}, args=[domain, app_id]))
Esempio n. 41
0
def default_new_app(request, domain):
    """New Blank Application according to defaults. So that we can link here
    instead of creating a form and posting to the above link, which was getting
    annoying for the Dashboard.
    """
    send_hubspot_form(HUBSPOT_APP_TEMPLATE_FORM_ID, request)
    track_workflow(request.couch_user.username, "User created a new blank application")

    lang = 'en'
    app = Application.new_app(domain, _("Untitled Application"), lang=lang)
    add_ons.init_app(request, app)

    if request.project.secure_submissions:
        app.secure_submissions = True
    clear_app_cache(request, domain)
    app.save()
    return HttpResponseRedirect(reverse('view_app', args=[domain, app._id]))
Esempio n. 42
0
    def update_linked_model(self, in_data):
        model = in_data['model']
        type_ = model['type']
        detail = model['detail']
        detail_obj = wrap_detail(type_, detail) if detail else None

        master_link = get_domain_master_link(self.domain)
        update_model_type(master_link, type_, detail_obj)
        master_link.update_last_pull(type_, self.request.couch_user._id, model_details=detail_obj)

        track_workflow(self.request.couch_user.username, "Linked domain: updated '{}' model".format(type_))

        timezone = get_timezone_for_request()
        return {
            'success': True,
            'last_update': server_to_user_time(master_link.last_pull, timezone)
        }
Esempio n. 43
0
    def update_linked_model(self, in_data):
        model = in_data['model']
        type_ = model['type']
        detail = model['detail']
        detail_obj = wrap_detail(type, detail) if detail else None

        master_link = get_domain_master_link(self.domain)
        update_model_type(master_link, type_, detail_obj)
        master_link.update_last_pull(type_, self.request.couch_user._id, model_details=detail_obj)

        track_workflow(self.request.couch_user.username, "Linked domain: updated '{}' model".format(type_))

        timezone = get_timezone_for_request()
        return {
            'success': True,
            'last_update': server_to_user_time(master_link.last_pull, timezone)
        }
Esempio n. 44
0
def default_new_app(request, domain):
    """New Blank Application according to defaults. So that we can link here
    instead of creating a form and posting to the above link, which was getting
    annoying for the Dashboard.
    """
    send_hubspot_form(HUBSPOT_APP_TEMPLATE_FORM_ID, request)
    track_workflow(request.couch_user.username, "User created a new blank application")

    lang = 'en'
    app = Application.new_app(domain, _("Untitled Application"), lang=lang)
    add_ons.init_app(request, app)

    if request.project.secure_submissions:
        app.secure_submissions = True
    clear_app_cache(request, domain)
    app.save()
    return HttpResponseRedirect(reverse('view_app', args=[domain, app._id]))
Esempio n. 45
0
 def post(self, *args, **kwargs):
     if self.report_form.is_valid():
         if self.report_form.existing_report:
             try:
                 report_configuration = self.report_form.update_report()
             except ValidationError as e:
                 messages.error(self.request, e.message)
                 return self.get(*args, **kwargs)
         else:
             report_configuration = self.report_form.create_report()
             track_workflow(
                 self.request.user.email,
                 "Successfully created a new report in the Report Builder"
             )
         return HttpResponseRedirect(
             reverse(ConfigurableReport.slug, args=[self.domain, report_configuration._id])
         )
     return self.get(*args, **kwargs)
Esempio n. 46
0
    def _process_new_user_data(request, new_web_user, async_signup):
        """
        If available, this makes sure we apply any relevant user data
        :param request: HttpRequest
        :param new_web_user: WebUser
        :param async_signup: AsyncSignupRequest
        """
        if not async_signup:
            if settings.IS_SAAS_ENVIRONMENT:
                track_workflow(
                    new_web_user.username,
                    "Requested New Account via SSO (Bypassed Signup Form)",
                    {
                        'environment': settings.SERVER_ENVIRONMENT,
                    }
                )
            return

        if async_signup.invitation:
            return

        if async_signup.phone_number:
            new_web_user.phone_numbers.append(async_signup.phone_number)
            new_web_user.save()

        if settings.IS_SAAS_ENVIRONMENT:
            track_workflow(
                new_web_user.username,
                "Requested New Account via SSO",
                {
                    'environment': settings.SERVER_ENVIRONMENT,
                }
            )
            if async_signup.persona:
                track_workflow(
                    new_web_user.username,
                    "Persona Field Filled Out via SSO",
                    {
                        'personachoice': async_signup.persona,
                        'personaother': async_signup.persona_other,
                    }
                )
                track_web_user_registration_hubspot(
                    request,
                    new_web_user,
                    async_signup.additional_hubspot_data,
                )
            else:
                track_workflow(
                    new_web_user.username,
                    "New User created through SSO, but Persona info missing"
                )
Esempio n. 47
0
 def dispatch(self, request_type, request, **kwargs):
     if toggles.API_BLACKLIST.enabled_for_request(request):
         msg = ("API access has been temporarily cut off due to too many "
                "requests.  To re-enable, please contact support.")
         raise ImmediateHttpResponse(HttpResponse(
             json.dumps({"error": msg}),
             content_type="application/json",
             status=401))
     if request.user.is_superuser or domain_has_privilege(request.domain, privileges.API_ACCESS):
         if isinstance(self, DomainSpecificResourceMixin):
             track_workflow(request.user.username, "API Request", properties={
                 'domain': request.domain,
                 'is_dimagi': request.user.username.endswith('@dimagi.com'),
             })
         return super(HqBaseResource, self).dispatch(request_type, request, **kwargs)
     else:
         raise ImmediateHttpResponse(HttpResponse(
             json.dumps({"error": "Your current subscription does not have access to this feature"}),
             content_type="application/json",
             status=401))
Esempio n. 48
0
    def _build_query(self, sort=True):
        query = super(CaseListExplorer, self)._build_query()
        query = self._populate_sort(query, sort)
        xpath = XpathCaseSearchFilter.get_value(self.request, self.domain)
        if xpath:
            try:
                query = query.xpath_query(self.domain, xpath)
            except CaseFilterError as e:
                track_workflow(self.request.couch_user.username, "Case List Explorer: Query Error")

                error = "<p>{}.</p>".format(escape(e))
                bad_part = "<p>{} <strong>{}</strong></p>".format(
                    _("The part of your search query that caused this error is: "),
                    escape(e.filter_part)
                ) if e.filter_part else ""
                raise BadRequestError("{}{}".format(error, bad_part))

            if '/' in xpath:
                track_workflow(self.request.couch_user.username, "Case List Explorer: Related case search")

        return query
Esempio n. 49
0
    def _build_query(self, sort=True):
        query = super(CaseListExplorer, self)._build_query()
        query = self._populate_sort(query, sort)
        xpath = XpathCaseSearchFilter.get_value(self.request, self.domain)
        if xpath:
            try:
                query = query.xpath_query(self.domain, xpath)
            except CaseFilterError as e:
                track_workflow(self.request.couch_user.username, "Case List Explorer: Query Error")

                error = "<p>{}.</p>".format(escape(e))
                bad_part = "<p>{} <strong>{}</strong></p>".format(
                    _("The part of your search query that caused this error is: "),
                    escape(e.filter_part)
                ) if e.filter_part else ""
                raise BadRequestError("{}{}".format(error, bad_part))

            if '/' in xpath:
                track_workflow(self.request.couch_user.username, "Case List Explorer: Related case search")

        return query
Esempio n. 50
0
    def post(self, request, *args, **kwargs):
        if self.invite_web_user_form.is_valid():
            # If user exists and has already requested access, just add them to the project
            # Otherwise, send an invitation
            create_invitation = True
            data = self.invite_web_user_form.cleaned_data
            domain_request = DomainRequest.by_email(self.domain, data["email"])
            if domain_request is not None:
                domain_request.is_approved = True
                domain_request.save()
                user = CouchUser.get_by_username(domain_request.email)
                if user is not None:
                    domain_request.send_approval_email()
                    create_invitation = False
                    user.add_as_web_user(self.domain,
                                         role=data["role"],
                                         location_id=data.get(
                                             "supply_point", None),
                                         program_id=data.get("program", None))
                messages.success(request, "%s added." % data["email"])
            else:
                track_workflow(request.couch_user.get_email(),
                               "Sent a project invitation",
                               {"Sent a project invitation": "yes"})
                meta = get_meta(request)
                track_sent_invite_on_hubspot.delay(request.couch_user,
                                                   request.COOKIES, meta)
                messages.success(request,
                                 "Invitation sent to %s" % data["email"])

            if create_invitation:
                data["invited_by"] = request.couch_user.user_id
                data["invited_on"] = datetime.utcnow()
                data["domain"] = self.domain
                invite = Invitation(**data)
                invite.save()
                invite.send_activation_email()
            return HttpResponseRedirect(
                reverse(ListWebUsersView.urlname, args=[self.domain]))
        return self.get(request, *args, **kwargs)
Esempio n. 51
0
    def post(self, request, *args, **kwargs):
        if self.invite_web_user_form.is_valid():
            # If user exists and has already requested access, just add them to the project
            # Otherwise, send an invitation
            create_invitation = True
            data = self.invite_web_user_form.cleaned_data
            domain_request = DomainRequest.by_email(self.domain, data["email"])
            if domain_request is not None:
                domain_request.is_approved = True
                domain_request.save()
                user = CouchUser.get_by_username(domain_request.email)
                if user is not None:
                    domain_request.send_approval_email()
                    create_invitation = False
                    user.add_as_web_user(self.domain, role=data["role"],
                                         location_id=data.get("supply_point", None),
                                         program_id=data.get("program", None))
                messages.success(request, "%s added." % data["email"])
            else:
                track_workflow(request.couch_user.get_email(),
                               "Sent a project invitation",
                               {"Sent a project invitation": "yes"})
                meta = get_meta(request)
                track_sent_invite_on_hubspot.delay(request.couch_user, request.COOKIES, meta)
                messages.success(request, "Invitation sent to %s" % data["email"])

            if create_invitation:
                data["invited_by"] = request.couch_user.user_id
                data["invited_on"] = datetime.utcnow()
                data["domain"] = self.domain
                invite = Invitation(**data)
                invite.save()
                invite.send_activation_email()
            return HttpResponseRedirect(reverse(
                ListWebUsersView.urlname,
                args=[self.domain]
            ))
        return self.get(request, *args, **kwargs)
Esempio n. 52
0
 def export_table(self):
     self._is_exporting = True
     track_workflow(self.request.couch_user.username, "Case List Explorer: Export button clicked")
     return super(CaseListExplorer, self).export_table
Esempio n. 53
0
def register_user(request, domain_type=None):
    domain_type = domain_type or 'commcare'
    if domain_type not in DOMAIN_TYPES:
        raise Http404()

    prefilled_email = request.GET.get('e', '')

    context = get_domain_context(domain_type)

    if request.user.is_authenticated():
        # Redirect to a page which lets user choose whether or not to create a new account
        domains_for_user = Domain.active_for_user(request.user)
        if len(domains_for_user) == 0:
            return redirect("registration_domain", domain_type=domain_type)
        else:
            return redirect("homepage")
    else:
        if request.method == 'POST':
            form = NewWebUserRegistrationForm(request.POST)
            if form.is_valid():
                activate_new_user(form, ip=get_ip(request))
                new_user = authenticate(username=form.cleaned_data['email'],
                                        password=form.cleaned_data['password'])

                meta = {
                    'HTTP_X_FORWARDED_FOR': request.META.get('HTTP_X_FORWARDED_FOR'),
                    'REMOTE_ADDR': request.META.get('REMOTE_ADDR'),
                }  # request.META can't be pickled for use by the task, so we copy the pertinent properties
                track_created_hq_account_on_hubspot.delay(
                    CouchUser.get_by_username(new_user.username),
                    request.COOKIES,
                    meta
                )
                track_workflow(new_user.email, "Requested new account")

                login(request, new_user)

                requested_domain = form.cleaned_data['hr_name']
                if form.cleaned_data['create_domain']:
                    org = None
                    try:
                        requested_domain = request_new_domain(
                            request, form, org, new_user=True, domain_type=domain_type)
                    except NameUnavailableException:
                        context.update({
                            'error_msg': _('Project name already taken - please try another'),
                            'show_homepage_link': 1
                        })
                        return render(request, 'error.html', context)

                context = get_domain_context(form.cleaned_data['domain_type']).update({
                    'alert_message': _("An email has been sent to %s.") % request.user.username,
                    'requested_domain': requested_domain,
                    'track_domain_registration': True,
                })
                return render(request, 'registration/confirmation_sent.html', context)
            context.update({'create_domain': form.cleaned_data['create_domain']})
        else:
            form = NewWebUserRegistrationForm(
                initial={'domain_type': domain_type, 'email': prefilled_email, 'create_domain': True})
            context.update({'create_domain': True})

        context.update({
            'form': form,
            'domain_type': domain_type,
        })
        return render(request, 'registration/create_new_user.html', context)
Esempio n. 54
0
    def __call__(self, request, invitation_id, **kwargs):
        logging.info("Don't use this view in more apps until it gets cleaned up.")
        # add the correct parameters to this instance
        self.request = request
        self.inv_id = invitation_id
        if 'domain' in kwargs:
            self.domain = kwargs['domain']

        if request.GET.get('switch') == 'true':
            logout(request)
            return redirect_to_login(request.path)
        if request.GET.get('create') == 'true':
            logout(request)
            return HttpResponseRedirect(request.path)

        try:
            invitation = Invitation.get(invitation_id)
        except ResourceNotFound:
            messages.error(request, _("Sorry, it looks like your invitation has expired. "
                                      "Please check the invitation link you received and try again, or request a "
                                      "project administrator to send you the invitation again."))
            return HttpResponseRedirect(reverse("login"))
        if invitation.is_accepted:
            messages.error(request, _("Sorry, that invitation has already been used up. "
                                      "If you feel this is a mistake please ask the inviter for "
                                      "another invitation."))
            return HttpResponseRedirect(reverse("login"))

        self.validate_invitation(invitation)

        if invitation.is_expired:
            return HttpResponseRedirect(reverse("no_permissions"))

        # Add zero-width space to username for better line breaking
        username = self.request.user.username.replace("@", "&#x200b;@")
        context = {
            'create_domain': False,
            'formatted_username': username,
            'domain': self.domain,
            'invite_to': self.domain,
            'invite_type': _('Project'),
            'hide_password_feedback': settings.ENABLE_DRACONIAN_SECURITY_FEATURES,
        }
        if request.user.is_authenticated:
            context['current_page'] = {'page_name': _('Project Invitation')}
        else:
            context['current_page'] = {'page_name': _('Project Invitation, Account Required')}
        if request.user.is_authenticated():
            is_invited_user = request.couch_user.username.lower() == invitation.email.lower()
            if self.is_invited(invitation, request.couch_user) and not request.couch_user.is_superuser:
                if is_invited_user:
                    # if this invite was actually for this user, just mark it accepted
                    messages.info(request, _("You are already a member of {entity}.").format(
                        entity=self.inviting_entity))
                    invitation.is_accepted = True
                    invitation.save()
                else:
                    messages.error(request, _("It looks like you are trying to accept an invitation for "
                                             "{invited} but you are already a member of {entity} with the "
                                             "account {current}. Please sign out to accept this invitation "
                                             "as another user.").format(
                                                 entity=self.inviting_entity,
                                                 invited=invitation.email,
                                                 current=request.couch_user.username,
                                             ))
                return HttpResponseRedirect(self.redirect_to_on_success)

            if not is_invited_user:
                messages.error(request, _("The invited user {invited} and your user {current} do not match!").format(
                    invited=invitation.email, current=request.couch_user.username))

            if request.method == "POST":
                couch_user = CouchUser.from_django_user(request.user)
                self._invite(invitation, couch_user)
                track_workflow(request.couch_user.get_email(),
                               "Current user accepted a project invitation",
                               {"Current user accepted a project invitation": "yes"})
                meta = get_meta(request)
                track_existing_user_accepted_invite_on_hubspot.delay(request.couch_user, request.COOKIES, meta)
                return HttpResponseRedirect(self.redirect_to_on_success)
            else:
                mobile_user = CouchUser.from_django_user(request.user).is_commcare_user()
                context.update({
                    'mobile_user': mobile_user,
                    "invited_user": invitation.email if request.couch_user.username != invitation.email else "",
                })
                return render(request, self.template, context)
        else:
            if request.method == "POST":
                form = WebUserInvitationForm(request.POST)
                if form.is_valid():
                    # create the new user
                    user = activate_new_user(form, domain=invitation.domain)
                    user.save()
                    messages.success(request, _("User account for %s created!") % form.cleaned_data["email"])
                    self._invite(invitation, user)
                    authenticated = authenticate(username=form.cleaned_data["email"],
                                                 password=form.cleaned_data["password"])
                    if authenticated is not None and authenticated.is_active:
                        login(request, authenticated)
                    track_workflow(request.POST['email'],
                                   "New User Accepted a project invitation",
                                   {"New User Accepted a project invitation": "yes"})
                    meta = get_meta(request)
                    track_new_user_accepted_invite_on_hubspot.delay(user, request.COOKIES, meta)
                    return HttpResponseRedirect(reverse("domain_homepage", args=[invitation.domain]))
            else:
                if CouchUser.get_by_username(invitation.email):
                    return HttpResponseRedirect(reverse("login") + '?next=' +
                        reverse('domain_accept_invitation', args=[invitation.domain, invitation.get_id]))
                form = WebUserInvitationForm(initial={
                    'email': invitation.email,
                    'hr_name': invitation.domain,
                    'create_domain': False,
                })

        context.update({"form": form})
        return render(request, self.template, context)
Esempio n. 55
0
def edit_module_attr(request, domain, app_id, module_unique_id, attr):
    """
    Called to edit any (supported) module attribute, given by attr
    """
    attributes = {
        "all": None,
        "auto_select_case": None,
        "case_list": ('case_list-show', 'case_list-label'),
        "case_list-menu_item_media_audio": None,
        "case_list-menu_item_media_image": None,
        'case_list-menu_item_use_default_image_for_all': None,
        'case_list-menu_item_use_default_audio_for_all': None,
        "case_list_form_id": None,
        "case_list_form_label": None,
        "case_list_form_media_audio": None,
        "case_list_form_media_image": None,
        'case_list_form_use_default_image_for_all': None,
        'case_list_form_use_default_audio_for_all': None,
        "case_list_post_form_workflow": None,
        "case_type": None,
        'comment': None,
        "display_separately": None,
        "has_schedule": None,
        "media_audio": None,
        "media_image": None,
        "module_filter": None,
        "name": None,
        "name_enum": None,
        "parent_module": None,
        "put_in_root": None,
        "root_module_id": None,
        "source_module_id": None,
        "task_list": ('task_list-show', 'task_list-label'),
        "excl_form_ids": None,
        "display_style": None,
        "custom_icon_form": None,
        "custom_icon_text_body": None,
        "custom_icon_xpath": None,
        "use_default_image_for_all": None,
        "use_default_audio_for_all": None,
    }

    if attr not in attributes:
        return HttpResponseBadRequest()

    def should_edit(attribute):
        if attribute == attr:
            return True
        if 'all' == attr:
            if attributes[attribute]:
                for param in attributes[attribute]:
                    if not request.POST.get(param):
                        return False
                return True
            else:
                return request.POST.get(attribute) is not None

    app = get_app(domain, app_id)

    try:
        module = app.get_module_by_unique_id(module_unique_id)
    except ModuleNotFoundException:
        # temporary fallback
        module = app.get_module(module_unique_id)

    lang = request.COOKIES.get('lang', app.langs[0])
    resp = {'update': {}, 'corrections': {}}
    if should_edit("custom_icon_form"):
        error_message = handle_custom_icon_edits(request, module, lang)
        if error_message:
            return json_response(
                {'message': error_message},
                status_code=400
            )

    if should_edit("name_enum"):
        name_enum = json.loads(request.POST.get("name_enum"))
        module.name_enum = [MappingItem(i) for i in name_enum]

    if should_edit("case_type"):
        case_type = request.POST.get("case_type", None)
        if case_type == USERCASE_TYPE and not isinstance(module, AdvancedModule):
            return HttpResponseBadRequest('"{}" is a reserved case type'.format(USERCASE_TYPE))
        elif case_type and not is_valid_case_type(case_type, module):
            return HttpResponseBadRequest("case type is improperly formatted")
        else:
            old_case_type = module["case_type"]
            module["case_type"] = case_type

            # rename other reference to the old case type
            all_advanced_modules = []
            modules_with_old_case_type_exist = False
            for mod in app.modules:
                if isinstance(mod, AdvancedModule):
                    all_advanced_modules.append(mod)

                modules_with_old_case_type_exist |= mod.case_type == old_case_type
            for mod in all_advanced_modules:
                for form in mod.forms:
                    for action in form.actions.get_load_update_actions():
                        if action.case_type == old_case_type and action.details_module == module_unique_id:
                            action.case_type = case_type

                    if mod.unique_id == module_unique_id or not modules_with_old_case_type_exist:
                        for action in form.actions.get_open_actions():
                            if action.case_type == old_case_type:
                                action.case_type = case_type

    if should_edit("put_in_root"):
        module["put_in_root"] = json.loads(request.POST.get("put_in_root"))
    if should_edit("display_style"):
        module["display_style"] = request.POST.get("display_style")
    if should_edit("source_module_id"):
        module["source_module_id"] = request.POST.get("source_module_id")
    if should_edit("display_separately"):
        module["display_separately"] = json.loads(request.POST.get("display_separately"))
    if should_edit("parent_module"):
        parent_module = request.POST.get("parent_module")
        module.parent_select.module_id = parent_module
        if module_case_hierarchy_has_circular_reference(module):
            return HttpResponseBadRequest(_("The case hierarchy contains a circular reference."))
    if should_edit("auto_select_case"):
        module["auto_select_case"] = request.POST.get("auto_select_case") == 'true'

    if app.enable_module_filtering and should_edit('module_filter'):
        module['module_filter'] = request.POST.get('module_filter')

    if should_edit('case_list_form_id'):
        module.case_list_form.form_id = request.POST.get('case_list_form_id')
    if should_edit('case_list_form_label'):
        module.case_list_form.label[lang] = request.POST.get('case_list_form_label')
    if should_edit('case_list_post_form_workflow'):
        module.case_list_form.post_form_workflow = request.POST.get('case_list_post_form_workflow')

    if should_edit("name"):
        name = request.POST.get("name", None)
        module["name"][lang] = name
        resp['update'] = {'.variable-module_name': trans(module.name, [lang], use_delim=False)}
    if should_edit('comment'):
        module.comment = request.POST.get('comment')
    for SLUG in ('case_list', 'task_list'):
        show = '{SLUG}-show'.format(SLUG=SLUG)
        label = '{SLUG}-label'.format(SLUG=SLUG)
        if request.POST.get(show) == 'true' and (request.POST.get(label) == ''):
            # Show item, but empty label, was just getting ignored
            return HttpResponseBadRequest("A label is required for {SLUG}".format(SLUG=SLUG))
        if should_edit(SLUG):
            module[SLUG].show = json.loads(request.POST[show])
            module[SLUG].label[lang] = request.POST[label]

    if should_edit("root_module_id"):
        old_root = module['root_module_id']
        if not request.POST.get("root_module_id"):
            module["root_module_id"] = None
        else:
            module["root_module_id"] = request.POST.get("root_module_id")
        if not old_root and module['root_module_id']:
            track_workflow(request.couch_user.username, "User associated module with a parent")
        elif old_root and not module['root_module_id']:
            track_workflow(request.couch_user.username, "User orphaned a child module")

    if should_edit('excl_form_ids') and isinstance(module, ShadowModule):
        excl = request.POST.getlist('excl_form_ids')
        excl.remove('0')  # Placeholder value to make sure excl_form_ids is POSTed when no forms are excluded
        module.excluded_form_ids = excl

    handle_media_edits(request, module, should_edit, resp, lang)
    handle_media_edits(request, module.case_list_form, should_edit, resp, lang, prefix='case_list_form_')
    handle_media_edits(request, module.case_list, should_edit, resp, lang, prefix='case_list-menu_item_')


    app.save(resp)
    resp['case_list-show'] = module.requires_case_details()
    return HttpResponse(json.dumps(resp))
Esempio n. 56
0
 def rows(self):
     track_workflow(self.request.couch_user.username, "Case List Explorer: Search Performed")
     data = (flatten_result(row) for row in self.es_results['hits'].get('hits', []))
     return self._get_rows(data)
Esempio n. 57
0
 def clean_password(self):
     try:
         return clean_password(self.cleaned_data.get('password'))
     except forms.ValidationError:
         track_workflow(self.cleaned_data.get('email'), 'Password Failure')
         raise
Esempio n. 58
0
    def __call__(self, request, invitation_id, **kwargs):
        logging.warning("Don't use this view in more apps until it gets cleaned up.")
        # add the correct parameters to this instance
        self.request = request
        self.inv_id = invitation_id
        if "domain" in kwargs:
            self.domain = kwargs["domain"]

        if request.GET.get("switch") == "true":
            logout(request)
            return redirect_to_login(request.path)
        if request.GET.get("create") == "true":
            logout(request)
            return HttpResponseRedirect(request.path)

        try:
            invitation = Invitation.get(invitation_id)
        except ResourceNotFound:
            messages.error(
                request,
                _(
                    "Sorry, it looks like your invitation has expired. "
                    "Please check the invitation link you received and try again, or request a "
                    "project administrator to send you the invitation again."
                ),
            )
            return HttpResponseRedirect(reverse("login"))
        if invitation.is_accepted:
            messages.error(
                request,
                _(
                    "Sorry, that invitation has already been used up. "
                    "If you feel this is a mistake please ask the inviter for "
                    "another invitation."
                ),
            )
            return HttpResponseRedirect(reverse("login"))

        self.validate_invitation(invitation)

        if invitation.is_expired:
            return HttpResponseRedirect(reverse("no_permissions"))

        context = self.added_context()
        if request.user.is_authenticated():
            is_invited_user = request.couch_user.username.lower() == invitation.email.lower()
            if self.is_invited(invitation, request.couch_user) and not request.couch_user.is_superuser:
                if is_invited_user:
                    # if this invite was actually for this user, just mark it accepted
                    messages.info(
                        request, _("You are already a member of {entity}.").format(entity=self.inviting_entity)
                    )
                    invitation.is_accepted = True
                    invitation.save()
                else:
                    messages.error(
                        request,
                        _(
                            "It looks like you are trying to accept an invitation for "
                            "{invited} but you are already a member of {entity} with the "
                            "account {current}. Please sign out to accept this invitation "
                            "as another user."
                        ).format(
                            entity=self.inviting_entity, invited=invitation.email, current=request.couch_user.username
                        ),
                    )
                return HttpResponseRedirect(self.redirect_to_on_success)

            if not is_invited_user:
                messages.error(
                    request,
                    _("The invited user {invited} and your user {current} do not match!").format(
                        invited=invitation.email, current=request.couch_user.username
                    ),
                )

            if request.method == "POST":
                couch_user = CouchUser.from_django_user(request.user)
                self._invite(invitation, couch_user)
                track_workflow(
                    request.couch_user.get_email(),
                    "Current user accepted a project invitation",
                    {"Current user accepted a project invitation": "yes"},
                )
                meta = get_meta(request)
                track_existing_user_accepted_invite_on_hubspot.delay(request.couch_user, request.COOKIES, meta)
                return HttpResponseRedirect(self.redirect_to_on_success)
            else:
                mobile_user = CouchUser.from_django_user(request.user).is_commcare_user()
                context.update(
                    {
                        "mobile_user": mobile_user,
                        "invited_user": invitation.email if request.couch_user.username != invitation.email else "",
                    }
                )
                return render(request, self.template, context)
        else:
            if request.method == "POST":
                form = NewWebUserRegistrationForm(request.POST)
                if form.is_valid():
                    # create the new user
                    user = activate_new_user(form)
                    user.save()
                    messages.success(request, _("User account for %s created!") % form.cleaned_data["email"])
                    self._invite(invitation, user)
                    authenticated = authenticate(
                        username=form.cleaned_data["email"], password=form.cleaned_data["password"]
                    )
                    if authenticated is not None and authenticated.is_active:
                        login(request, authenticated)
                    track_workflow(
                        request.POST["email"],
                        "New User Accepted a project invitation",
                        {"New User Accepted a project invitation": "yes"},
                    )
                    meta = get_meta(request)
                    track_new_user_accepted_invite_on_hubspot.delay(user, request.COOKIES, meta)
                    return HttpResponseRedirect(reverse("domain_homepage", args=[invitation.domain]))
            else:
                if CouchUser.get_by_username(invitation.email):
                    return HttpResponseRedirect(
                        reverse("login")
                        + "?next="
                        + reverse("domain_accept_invitation", args=[invitation.domain, invitation.get_id])
                    )
                domain = Domain.get_by_name(invitation.domain)
                form = NewWebUserRegistrationForm(
                    initial={
                        "email": invitation.email,
                        "hr_name": domain.display_name() if domain else invitation.domain,
                        "create_domain": False,
                    }
                )

        context.update({"form": form})
        return render(request, self.template, context)
Esempio n. 59
0
def confirm_domain(request, guid=''):
    with CriticalSection(['confirm_domain_' + guid]):
        error = None
        # Did we get a guid?
        if not guid:
            error = _('An account activation key was not provided.  If you think this '
                      'is an error, please contact the system administrator.')

        # Does guid exist in the system?
        else:
            req = RegistrationRequest.get_by_guid(guid)
            if not req:
                error = _('The account activation key "%s" provided is invalid. If you '
                          'think this is an error, please contact the system '
                          'administrator.') % guid

        if error is not None:
            context = {
                'message_body': error,
                'current_page': {'page_name': 'Account Not Activated'},
            }
            return render(request, 'registration/confirmation_error.html', context)

        requested_domain = Domain.get_by_name(req.domain)
        view_name = "dashboard_default"
        view_args = [requested_domain.name]
        if not domain_has_apps(req.domain):
            if False and settings.IS_SAAS_ENVIRONMENT and domain_is_on_trial(req.domain):
                view_name = "app_from_template"
                view_args.append("appcues")
            else:
                view_name = "default_new_app"

        # Has guid already been confirmed?
        if requested_domain.is_active:
            assert(req.confirm_time is not None and req.confirm_ip is not None)
            messages.success(request, 'Your account %s has already been activated. '
                'No further validation is required.' % req.new_user_username)
            return HttpResponseRedirect(reverse(view_name, args=view_args))

        # Set confirm time and IP; activate domain and new user who is in the
        req.confirm_time = datetime.utcnow()
        req.confirm_ip = get_ip(request)
        req.save()
        requested_domain.is_active = True
        requested_domain.save()
        requesting_user = WebUser.get_by_username(req.new_user_username)

        send_new_request_update_email(requesting_user, get_ip(request), requested_domain.name, is_confirming=True)

        messages.success(request,
                'Your account has been successfully activated.  Thank you for taking '
                'the time to confirm your email address: %s.'
            % (requesting_user.username))
        track_workflow(requesting_user.email, "Confirmed new project")
        track_confirmed_account_on_hubspot_v2.delay(requesting_user)
        request.session['CONFIRM'] = True

        if settings.IS_SAAS_ENVIRONMENT:
            # For AppCues v3, land new user in Web Apps
            view_name = get_cloudcare_urlname(requested_domain.name)
        return HttpResponseRedirect(reverse(view_name, args=view_args))