Example #1
0
    def setUp(self):
        self.clear_cache()

        self.superuser = User.objects.create_superuser(username="******", email="*****@*****.**", password="******")

        # some orgs
        self.unicef = self.create_org("UNICEF", timezone="Asia/Kabul", subdomain="unicef")
        self.nyaruka = self.create_org("Nyaruka", timezone="Africa/Kigali", subdomain="nyaruka")

        # some admins for those orgs
        self.admin = self.create_admin(self.unicef, "Richard", "*****@*****.**")
        self.eric = self.create_admin(self.nyaruka, "Eric", "*****@*****.**")

        # some regions
        self.region1 = self.create_region(self.unicef, name="Kandahar", uuid='G-001')
        self.region2 = self.create_region(self.unicef, name="Khost", uuid='G-002')
        self.region3 = self.create_region(self.unicef, name="Kunar", uuid='G-003')
        self.region4 = self.create_region(self.nyaruka, name="Kigali", uuid='G-004')

        # some users in those regions
        self.user1 = self.create_user(self.unicef, "Sam Sims", "*****@*****.**", regions=[self.region1])
        self.user2 = self.create_user(self.unicef, "Sue", "*****@*****.**", regions=[self.region2, self.region3])
        self.user3 = self.create_user(self.nyaruka, "Nic", "*****@*****.**", regions=[self.region4])

        # some reporting groups
        self.group1 = self.create_group(self.unicef, name="Farmers", uuid='G-005')
        self.group2 = self.create_group(self.unicef, name="Teachers", uuid='G-006')
        self.group3 = self.create_group(self.unicef, name="Doctors", uuid='G-007')
        self.group4 = self.create_group(self.nyaruka, name="Programmers", uuid='G-008')

        # some contacts
        self.contact1 = self.create_contact(self.unicef, "Ann", 'tel:1234', self.region1, self.group1, 'C-001')
        self.contact2 = self.create_contact(self.unicef, "Bob", 'tel:2345', self.region1, self.group1, 'C-002')
        self.contact3 = self.create_contact(self.unicef, "Cat", 'tel:3456', self.region1, self.group2, 'C-003')
        self.contact4 = self.create_contact(self.unicef, "Dan", 'twitter:danny', self.region2, self.group2, 'C-004')
        self.contact5 = self.create_contact(self.unicef, "Eve", 'twitter:evee', self.region3, self.group3, 'C-005')
        self.contact6 = self.create_contact(self.nyaruka, "Norbert", 'twitter:n7', self.region4, self.group4, 'C-006')

        # a poll with some questions
        self.poll1 = Poll.create(self.unicef, "Farm Poll", 'F-001')
        self.poll1_question1 = Question.create(self.poll1, "Number of sheep", 'N', 1, 'RS-001')
        self.poll1_question2 = Question.create(self.poll1, "How is the weather?", 'O', 2, 'RS-002')

        # and a poll for the other org
        self.poll2 = Poll.create(self.nyaruka, "Code Poll", 'F-002')
        self.poll2_question1 = Question.create(self.poll2, "Number of bugs", 'N', 1, 'RS-003')
Example #2
0
    def __init__(self, *args, **kwargs):
        self.user = kwargs.pop('user')
        org = self.user.get_org()

        super(BaselineTermForm, self).__init__(*args, **kwargs)

        if org:
            polls = Poll.get_all(org).order_by('name')
            self.fields['baseline_poll'].queryset = polls
            self.fields['follow_up_poll'].queryset = polls
Example #3
0
    def __init__(self, *args, **kwargs):
        org = kwargs.pop('org')

        super(SpoofDataForm, self).__init__(*args, **kwargs)

        if org:
            contacts = Contact.get_all(org).order_by('name')
            self.fields['contacts'].queryset = contacts
            questions = Question.objects.filter(poll__in=Poll.get_all(org))
            self.fields['baseline_question'].queryset = questions
            self.fields['follow_up_question'].queryset = questions
Example #4
0
def fetch_org_runs(org_id):
    """
    Fetches new and modified flow runs for the given org and creates/updates
    poll responses.
    """
    from tracpro.orgs_ext.constants import TaskType
    from tracpro.polls.models import Poll, PollRun, Response

    org = Org.objects.get(pk=org_id)

    client = org.get_temba_client()
    redis_connection = get_redis_connection()
    last_time_key = LAST_FETCHED_RUN_TIME_KEY % org.pk
    last_time = redis_connection.get(last_time_key)

    if last_time is not None:
        last_time = parse_iso8601(last_time)
    else:
        newest_runs = Response.objects.filter(pollrun__poll__org=org).order_by("-created_on")
        newest_runs = newest_runs.exclude(pollrun__pollrun_type=PollRun.TYPE_SPOOFED)
        newest_run = newest_runs.first()
        last_time = newest_run.created_on if newest_run else None

    until = timezone.now()

    total_runs = 0
    for poll in Poll.get_all(org):
        poll_runs = client.get_runs(flows=[poll.flow_uuid], after=last_time, before=until)
        total_runs += len(poll_runs)

        # convert flow runs into poll responses
        for run in poll_runs:
            try:
                Response.from_run(org, run, poll=poll)
            except ValueError as e:
                logger.error("Unable to save run #%d due to error: %s" % (run.id, e.message))
                continue

    logger.info(
        "Fetched %d new and updated runs for org #%d (since=%s)"
        % (total_runs, org.id, format_iso8601(last_time) if last_time else "Never")
    )

    task_result = dict(time=datetime_to_ms(timezone.now()), counts=dict(fetched=total_runs))
    org.set_task_result(TaskType.fetch_runs, task_result)

    redis_connection.set(last_time_key, format_iso8601(until))
Example #5
0
    def handle(self, *args, **options):
        org_id = int(args[0]) if args else None
        if not org_id:
            raise CommandError("Most provide valid org id")

        try:
            org = Org.objects.get(pk=org_id)
        except Org.DoesNotExist:
            raise CommandError("No such org with id %d" % org_id)

        minutes, hours, days = options['minutes'], options['hours'], options[
            'days']

        if not (minutes or hours or days):
            raise CommandError(
                "Must provide at least one of --minutes --hours or --days")

        since = timezone.now() - relativedelta(
            minutes=minutes, hours=hours, days=days)

        self.stdout.write('Fetching responses for org %s since %s...' %
                          (org.name, since.strftime('%b %d, %Y %H:%M')))

        client = org.get_temba_client()

        polls_by_flow_uuids = {p.flow_uuid: p for p in Poll.get_all(org)}

        runs = client.get_runs(flows=polls_by_flow_uuids.keys(), after=since)

        self.stdout.write("Fetched %d runs for org %s" % (len(runs), org.id))

        created = 0
        updated = 0
        for run in runs:
            poll = polls_by_flow_uuids[run.flow]
            try:
                response = Response.from_run(org, run, poll=poll)
            except ValueError, e:
                self.stderr.write("Unable to save run #%d due to error: %s" %
                                  (run.id, e.message))
                continue

            if getattr(response, 'is_new', False):
                created += 1
            else:
                updated += 1
Example #6
0
    def handle(self, *args, **options):
        org_id = int(args[0]) if args else None
        if not org_id:
            raise CommandError("Most provide valid org id")

        try:
            org = Org.objects.get(pk=org_id)
        except Org.DoesNotExist:
            raise CommandError("No such org with id %d" % org_id)

        minutes, hours, days = options['minutes'], options['hours'], options['days']

        if not (minutes or hours or days):
            raise CommandError("Must provide at least one of --minutes --hours or --days")

        since = timezone.now() - relativedelta(minutes=minutes, hours=hours, days=days)

        self.stdout.write('Fetching responses for org %s since %s...' % (org.name, since.strftime('%b %d, %Y %H:%M')))

        client = org.get_temba_client()

        polls_by_flow_uuids = {p.flow_uuid: p for p in Poll.get_all(org)}

        runs = client.get_runs(flows=polls_by_flow_uuids.keys(), after=since)

        self.stdout.write("Fetched %d runs for org %s" % (len(runs), org.id))

        created = 0
        updated = 0
        for run in runs:
            if run.flow not in polls_by_flow_uuids:
                continue  # Response is for a Poll not tracked for this org.

            poll = polls_by_flow_uuids[run.flow]
            try:
                response = Response.from_run(org, run, poll=poll)
            except ValueError as e:
                self.stderr.write("Unable to save run #%d due to error: %s" % (run.id, e.message))
                continue

            if getattr(response, 'is_new', False):
                created += 1
            else:
                updated += 1

        self.stdout.write("Created %d new responses and updated %d existing responses" % (created, updated))
Example #7
0
    def get_context_data(self, **kwargs):
        context = super(HomeView, self).get_context_data(**kwargs)
        context['polls'] = Poll.get_all(self.request.org).order_by('name')

        # Loop through all baseline terms, until we find one with data
        for baselineterm in BaselineTerm.objects.all().order_by('-end_date'):
            data_found = baselineterm.check_for_data(self.request.data_regions)
            if data_found:
                answers_dict, baseline_dict, all_regions, date_list = chart_baseline(
                    baselineterm=baselineterm, regions=self.request.data_regions, region_selected=0)
                context['all_regions'] = all_regions
                context['date_list'] = date_list
                context['baseline_dict'] = baseline_dict
                context['answers_dict'] = answers_dict
                context['baselineterm'] = baselineterm
                break  # Found our baseline chart with data, send it back to the view

        return context
Example #8
0
    def get_context_data(self, **kwargs):
        context = super(HomeView, self).get_context_data(**kwargs)
        context['polls'] = Poll.get_all(self.request.org).order_by('name')
        # Loop through all baseline terms, until we find one with data
        baselineterms = BaselineTerm.get_all(self.request.org).order_by('-end_date')
        for baselineterm in baselineterms:
            data_found = baselineterm.check_for_data(self.request.data_regions)
            if data_found:
                (follow_up_list, baseline_list, all_regions, date_list,
                 baseline_mean, baseline_std, follow_up_mean, follow_up_std,
                 baseline_response_rate, follow_up_response_rate) = chart_baseline(
                    baselineterm=baselineterm, regions=self.request.data_regions, region_selected=None)
                context['all_regions'] = all_regions
                context['date_list'] = date_list
                context['baseline_list'] = baseline_list
                context['follow_up_list'] = follow_up_list
                context['baselineterm'] = baselineterm
                break  # Found our baseline chart with data, send it back to the view

        # Return top 5 baseline terms only
        context['baselineterms'] = baselineterms[0:5]

        return context
Example #9
0
 def get_context_data(self, **kwargs):
     context = super(HomeView, self).get_context_data(**kwargs)
     context['polls'] = Poll.get_all(self.request.org).order_by('name')
     return context