Exemplo n.º 1
0
    def catch_triggers(cls, entity, trigger_type, channel):
        if isinstance(entity, Msg):
            contact = entity.contact
            start_msg = entity
        elif isinstance(entity, Call) or isinstance(entity, IVRCall):
            contact = entity.contact
            start_msg = Msg(org=entity.org, contact=contact, channel=entity.channel, created_on=timezone.now(), id=0)
        elif isinstance(entity, Contact):
            contact = entity
            start_msg = Msg(org=entity.org, contact=contact, channel=channel, created_on=timezone.now(), id=0)
        else:
            raise ValueError("Entity must be of type msg, call or contact")

        triggers = Trigger.get_triggers_of_type(entity.org, trigger_type)

        if trigger_type == Trigger.TYPE_FOLLOW:
            triggers = triggers.filter(channel=channel)

        # is there a match for a group specific trigger?
        group_ids = contact.user_groups.values_list('pk', flat=True)
        group_triggers = triggers.filter(groups__in=group_ids).order_by('groups__name')

        # if we match with a group restriction, that takes precedence
        if group_triggers:
            triggers = group_triggers

        # otherwise, restrict to triggers that don't filter by group
        else:
            triggers = triggers.filter(groups=None)

        # only fire the first matching trigger
        if triggers:
            triggers[0].flow.start([], [contact], start_msg=start_msg, restart_participants=True)

        return bool(triggers)
Exemplo n.º 2
0
    def catch_triggers(cls,
                       entity,
                       trigger_type,
                       channel,
                       referrer_id=None,
                       extra=None):
        if isinstance(entity, Msg):
            contact = entity.contact
            start_msg = entity
        elif isinstance(entity, ChannelEvent) or isinstance(entity, IVRCall):
            contact = entity.contact
            start_msg = Msg(org=entity.org,
                            contact=contact,
                            channel=entity.channel,
                            created_on=timezone.now(),
                            id=0)
        elif isinstance(entity, Contact):
            contact = entity
            start_msg = Msg(org=entity.org,
                            contact=contact,
                            channel=channel,
                            created_on=timezone.now(),
                            id=0)
        else:  # pragma: needs cover
            raise ValueError("Entity must be of type msg, call or contact")

        triggers = Trigger.get_triggers_of_type(entity.org, trigger_type)

        if trigger_type in [
                Trigger.TYPE_FOLLOW, Trigger.TYPE_NEW_CONVERSATION,
                Trigger.TYPE_REFERRAL
        ]:
            triggers = triggers.filter(
                models.Q(channel=channel) | models.Q(channel=None))

        if referrer_id is not None:
            triggers = triggers.filter(referrer_id=referrer_id)

        # is there a match for a group specific trigger?
        group_ids = contact.user_groups.values_list('pk', flat=True)
        group_triggers = triggers.filter(
            groups__in=group_ids).order_by('groups__name')

        # if we match with a group restriction, that takes precedence
        if group_triggers:
            triggers = group_triggers

        # otherwise, restrict to triggers that don't filter by group
        else:
            triggers = triggers.filter(groups=None)

        # only fire the first matching trigger
        if triggers:
            contact.ensure_unstopped()
            triggers[0].flow.start([], [contact],
                                   start_msg=start_msg,
                                   restart_participants=True,
                                   extra=extra)

        return bool(triggers)
Exemplo n.º 3
0
    def catch_triggers(cls, entity, trigger_type, channel):
        if isinstance(entity, Msg):
            contact = entity.contact
            start_msg = entity
        elif isinstance(entity, Call) or isinstance(entity, IVRCall):
            contact = entity.contact
            start_msg = Msg(contact=contact, channel=entity.channel, created_on=timezone.now(), id=0)
        elif isinstance(entity, Contact):
            contact = entity
            start_msg = Msg(contact=contact, channel=channel, created_on=timezone.now(), id=0)
        else:
            raise ValueError("Entity must be of type msg, call or contact")

        triggers = Trigger.get_triggers_of_type(entity.org, trigger_type)

        if trigger_type == Trigger.TYPE_FOLLOW:
            triggers = triggers.filter(channel=channel)

        for trigger in triggers:
            trigger.flow.start([], [contact], start_msg=start_msg, restart_participants=True)

        return bool(triggers)
Exemplo n.º 4
0
def advance_stuck_runs(apps, schema_editor):

    # this data migration is not forward-compatible
    from temba.flows.models import Flow, FlowStep, FlowRun, RuleSet
    from temba.msgs.models import Msg

    flows = Flow.objects.filter(flow_type='F', version_number=5)

    if flows:
        print "%d version 5 flows" % len(flows)

        for flow in flows:

            # looking for flows that start with a passive ruleset
            ruleset = RuleSet.objects.filter(uuid=flow.entry_uuid,
                                             flow=flow).first()

            if ruleset and not ruleset.is_pause():

                # now see if there are any active steps at our current flow
                steps = FlowStep.objects.filter(
                    run__is_active=True,
                    step_uuid=ruleset.uuid,
                    rule_value=None,
                    left_on=None).select_related('contact')

                if steps:
                    print '\nAdvancing %d steps for %s:%s' % (
                        len(steps), flow.org.name, flow.name)
                    for idx, step in enumerate(steps):

                        if (idx + 1) % 100 == 0:
                            print '\n\n *** Step %d of %d\n\n' % (idx + 1,
                                                                  len(steps))

                        # force them to be handled again
                        msg = Msg(contact=step.contact, text='', id=0)
                        Flow.handle_destination(ruleset, step, step.run, msg)
Exemplo n.º 5
0
    def catch_triggers(cls,
                       entity,
                       trigger_type,
                       channel,
                       referrer_id=None,
                       extra=None):
        if isinstance(entity, Msg):
            contact = entity.contact
            start_msg = entity
        elif isinstance(entity, ChannelEvent) or isinstance(entity, IVRCall):
            contact = entity.contact
            start_msg = Msg(org=entity.org,
                            contact=contact,
                            channel=entity.channel,
                            created_on=timezone.now(),
                            id=0)
        elif isinstance(entity, Contact):
            contact = entity
            start_msg = Msg(org=entity.org,
                            contact=contact,
                            channel=channel,
                            created_on=timezone.now(),
                            id=0)
        else:  # pragma: needs cover
            raise ValueError("Entity must be of type msg, call or contact")

        triggers = Trigger.get_triggers_of_type(entity.org, trigger_type)

        if trigger_type in [
                Trigger.TYPE_FOLLOW, Trigger.TYPE_NEW_CONVERSATION,
                Trigger.TYPE_REFERRAL
        ]:
            triggers = triggers.filter(
                models.Q(channel=channel) | models.Q(channel=None))

        if referrer_id is not None:
            all_referrer_triggers = triggers
            triggers = triggers.filter(
                models.Q(referrer_id__iexact=referrer_id)
                | models.Q(referrer_id=''))

            # if we catch more than one trigger with a referrer_id, ignore the catchall
            if len(triggers) > 1:
                triggers = triggers.exclude(referrer_id='')

            if not triggers:
                #Now check if can use regex expression
                tmp_triggers = all_referrer_triggers.filter(
                    models.Q(referrer_id__contains="regex"))
                import re
                for trigger in tmp_triggers:
                    prog = re.compile(trigger.referrer_id.split('_')[1])
                    if re.match(prog, referrer_id):
                        triggers = tmp_triggers.filter(
                            models.Q(referrer_id__iexact=trigger.referrer_id))
                        ############ Save last referrer id response from contact ###############
                        contact.add_field_to_contact(
                            label=ContactField.REFERRER_LABEL,
                            field=ContactField.REFERRER_FIELD,
                            value=referrer_id,
                            org=entity.org)
                        break

        # is there a match for a group specific trigger?
        group_ids = contact.user_groups.values_list('pk', flat=True)
        group_triggers = triggers.filter(
            groups__in=group_ids).order_by('groups__name')

        # if we match with a group restriction, that takes precedence
        if group_triggers:
            triggers = group_triggers

        # otherwise, restrict to triggers that don't filter by group
        else:
            triggers = triggers.filter(groups=None)

        # only fire the first matching trigger
        if triggers:
            contact.ensure_unstopped()
            triggers[0].flow.start([], [contact],
                                   start_msg=start_msg,
                                   restart_participants=True,
                                   extra=extra)

        return bool(triggers)