Exemple #1
0
    def save(self, *args, **kwargs):
        if self.shouldCreate():
            #runs only if they have propose permission
            if self.initiator.has_perm(self.app_name + '.add_' + self.action_codename):
                if hasattr(self, 'proposal'):
                    self.proposal.status = Proposal.PROPOSED
                else:
                    self.proposal = Proposal.objects.create(status=Proposal.PROPOSED, author=self.initiator)
                super(ConstitutionAction, self).save(*args, **kwargs)

                if not self.is_bundled:
                    action = self
                    #if they have execute permission, skip all policies
                    if action.initiator.has_perm(action.app_name + '.can_execute_' + action.action_codename):
                        action.execute()
                    else:
                        for policy in ConstitutionPolicy.objects.filter(community=self.community):
                          if filter_policy(policy, action):

                              initialize_policy(policy, action)

                              check_result = check_policy(policy, action)
                              if check_result == Proposal.PASSED:
                                  pass_policy(policy, action)
                              elif check_result == Proposal.FAILED:
                                  fail_policy(policy, action)
                              else:
                                  notify_policy(policy, action)
            else:
                self.proposal = Proposal.objects.create(status=Proposal.FAILED, author=self.initiator)
        else:
            if not self.pk: # Runs only when object is new
                self.proposal = Proposal.objects.create(status=Proposal.FAILED, author=self.initiator)
            super(ConstitutionAction, self).save(*args, **kwargs)
Exemple #2
0
    def save(self, *args, **kwargs):
        logger.info('entered save')
        if not self.pk:
            logger.info('is pk')
            #runs only if they have propose permission
            if self.initiator.has_perm(self.app_name + '.add_' +
                                       self.action_codename):
                logger.info('has propose permission')
                p = Proposal.objects.create(status=Proposal.PROPOSED,
                                            author=self.initiator)
                self.proposal = p

                super(PlatformAction, self).save(*args, **kwargs)

                if not self.is_bundled:
                    action = self
                    #if they have execute permission, skip all policies
                    if action.initiator.has_perm(action.app_name +
                                                 '.can_execute_' +
                                                 action.action_codename):
                        logger.info('has execute permission')
                        action.execute()
                    else:
                        for policy in PlatformPolicy.objects.filter(
                                community=self.community):

                            logger.info('save: policy checking')
                            if filter_policy(policy, action):

                                initialize_policy(policy, action)

                                check_result = check_policy(policy, action)
                                if check_result == Proposal.PASSED:
                                    logger.info('passed (save)')
                                    pass_policy(policy, action)
                                elif check_result == Proposal.FAILED:
                                    logger.info('failed (save)')
                                    fail_policy(policy, action)
                                else:
                                    logger.info('notify (save)')
                                    notify_policy(policy, action)
            else:
                logger.info('does not have propose permission')
                p = Proposal.objects.create(status=Proposal.FAILED,
                                            author=self.initiator)
                self.proposal = p
        else:
            super(PlatformAction, self).save(*args, **kwargs)
Exemple #3
0
def after_constitutionaction_bundle_save(sender, instance, **kwargs):
    action = instance
    if action.initiator.has_perm(action.app_name + '.add_' + action.action_codename):
        #if they have execute permission, skip all policies
        if action.initiator.has_perm(action.app_name + '.can_execute_' + action.action_codename):
            action.execute()
        else:
            for policy in ConstitutionPolicy.objects.filter(community=action.community):
                if filter_policy(policy, action):

                    initialize_policy(policy, action)

                    check_result = check_policy(policy, action)
                    if check_result == Proposal.PASSED:
                      pass_policy(policy, action)
                    elif check_result == Proposal.FAILED:
                      fail_policy(policy, action)
                    else:
                      notify_policy(policy, action)
Exemple #4
0
def action(request):
    json_data = json.loads(request.body)
    logger.info('RECEIVED ACTION')
    logger.info(json_data)
    action_type = json_data.get('type')

    if action_type == "url_verification":
        challenge = json_data.get('challenge')
        return HttpResponse(challenge)

    elif action_type == "event_callback":
        event = json_data.get('event')
        team_id = json_data.get('team_id')
        community = SlackCommunity.objects.get(team_id=team_id)
        admin_user = SlackUser.objects.filter(is_community_admin=True)[0]

        new_api_action = None
        policy_kit_action = False

        if event.get('type') == "channel_rename":
            if not is_policykit_action(community, event['channel']['name'], 'name', SlackRenameConversation.ACTION):
                new_api_action = SlackRenameConversation()
                new_api_action.community = community
                new_api_action.name = event['channel']['name']
                new_api_action.channel = event['channel']['id']

                u,_ = SlackUser.objects.get_or_create(username=event['user'],
                                                    community=community)
                new_api_action.initiator = u
                prev_names = new_api_action.get_channel_info()
                new_api_action.prev_name = prev_names[0]

        elif event.get('type') == 'message' and event.get('subtype') == None:
            if not is_policykit_action(community, event['text'], 'text', SlackPostMessage.ACTION):
                new_api_action = SlackPostMessage()
                new_api_action.community = community
                new_api_action.text = event['text']
                new_api_action.channel = event['channel']
                new_api_action.time_stamp = event['ts']

                u,_ = SlackUser.objects.get_or_create(username=event['user'], community=community)

                new_api_action.initiator = u

        elif event.get('type') == "member_joined_channel":
            if not is_policykit_action(community, event['channel'], 'channel', SlackJoinConversation.ACTION):
                new_api_action = SlackJoinConversation()
                new_api_action.community = community
                if event.get('inviter'):
                    u,_ = SlackUser.objects.get_or_create(username=event['inviter'],
                                                          community=community)
                    new_api_action.initiator = u
                else:
                    u,_ = SlackUser.objects.get_or_create(username=event['user'],
                                                          community=community)
                    new_api_action.initiator = u
                new_api_action.users = event.get('user')
                new_api_action.channel = event['channel']


        elif event.get('type') == 'pin_added':
            if not is_policykit_action(community, event['channel_id'], 'channel', SlackPinMessage.ACTION):
                new_api_action = SlackPinMessage()
                new_api_action.community = community

                u,_ = SlackUser.objects.get_or_create(username=event['user'],
                                                      community=community)
                new_api_action.initiator = u
                new_api_action.channel = event['channel_id']
                new_api_action.timestamp = event['item']['message']['ts']

        if new_api_action.initiator.has_perm('slackintegration.add_' + new_api_action.action_codename):
            if new_api_action and not policy_kit_action:
                #if they have execute permission, skip all policies
                if new_api_action.initiator.has_perm('slackintegration.can_execute_' + new_api_action.action_codename):
                    new_api_action.execute()
                else:
                    for policy in PlatformPolicy.objects.filter(community=new_api_action.community):
                      if filter_policy(policy, new_api_action):
                          if not new_api_action.pk:
                              new_api_action.community_origin = True
                              new_api_action.is_bundled = False
                              new_api_action.save()
                          initialize_policy(policy, new_api_action)
                          cond_result = check_policy(policy, new_api_action)
                          if cond_result == Proposal.PROPOSED or cond_result == Proposal.FAILED:
                              new_api_action.revert()
        else:
            p = Proposal.objects.create(status=Proposal.FAILED,
                                        author=new_api_action.initiator)
            new_api_action.proposal = p

        if event.get('type') == 'reaction_added':
            ts = event['item']['ts']
            action = None
            action_res = PlatformAction.objects.filter(community_post=ts)
            if action_res.exists():
                action = action_res[0]

                if event['reaction'] == '+1' or event['reaction'] == '-1':
                    if event['reaction'] == '+1':
                        value = True
                    elif event['reaction'] == '-1':
                        value = False

                    user,_ = SlackUser.objects.get_or_create(username=event['user'],
                                                            community=action.community)
                    uv = BooleanVote.objects.filter(proposal=action.proposal,
                                                                 user=user)
                    if uv.exists():
                        uv = uv[0]
                        uv.boolean_value = value
                        uv.save()
                    else:
                        uv = BooleanVote.objects.create(proposal=action.proposal, user=user, boolean_value=value)

            if action == None:
                action_res = PlatformActionBundle.objects.filter(community_post=ts)
                if action_res.exists():
                    action = action_res[0]

                    bundled_actions = list(action.bundled_actions.all())

                    if event['reaction'] in NUMBERS_TEXT.keys():
                        num = NUMBERS_TEXT[event['reaction']]
                        voted_action = bundled_actions[num]

                        user,_ = SlackUser.objects.get_or_create(username=event['user'],
                                                               community=voted_action.community)
                        uv = NumberVote.objects.filter(proposal=voted_action.proposal,
                                                                 user=user)
                        if uv.exists():
                            uv = uv[0]
                            uv.number_value = 1
                            uv.save()
                        else:
                            uv = NumberVote.objects.create(proposal=voted_action.proposal, user=user, number_value=1)

    return HttpResponse("")
Exemple #5
0
def reddit_listener_actions():

    for community in RedditCommunity.objects.all():
        actions = []

        res = community.make_call('r/policykit/about/unmoderated')

        call_type = 'api/submit'

        for item in res['data']['children']:
            data = item['data']

            if not is_policykit_action(community, data['name'], call_type,
                                       data['title'], 'title'):

                post_exists = RedditMakePost.objects.filter(name=data['name'])

                if not post_exists.exists():
                    logger.info('make new action')

                    new_api_action = RedditMakePost()
                    new_api_action.community = community
                    new_api_action.text = data['selftext']
                    new_api_action.title = data['title']
                    new_api_action.name = data['name']

                    u, _ = RedditUser.objects.get_or_create(
                        username=data['author'], community=community)
                    new_api_action.initiator = u
                    actions.append(new_api_action)

        for action in actions:
            for policy in PlatformPolicy.objects.filter(
                    community=action.community):
                if filter_policy(policy, action):
                    if not action.pk:
                        action.community_origin = True
                        action.is_bundled = False
                        action.save()
                        logger.info('action saved')
                    cond_result = check_policy(policy, action)
                    logger.info(cond_result)
                    if cond_result == Proposal.PROPOSED or cond_result == Proposal.FAILED:
                        logger.info('revert')
                        action.revert()

        # look for votes

        proposed_actions = PlatformAction.objects.filter(
            community=community,
            proposal__status=Proposal.PROPOSED,
            community_post__isnull=False)

        for proposed_action in proposed_actions:

            id = proposed_action.community_post.split('_')[1]

            call = 'r/policykit/comments/' + id + '.json'
            res = community.make_call(call)
            replies = res[1]['data']['children']

            for reply in replies:
                data = reply['data']

                text = data['body']

                logger.info(text)

                val = None
                if '\\-1' in text:
                    val = False
                elif '\\+1' in text:
                    val = True

                if val != None:
                    username = data['author']
                    u = RedditUser.objects.filter(username=username,
                                                  community=community)

                    if u.exists():
                        u = u[0]
                        bool_vote = BooleanVote.objects.filter(
                            proposal=proposed_action.proposal, user=u)
                        if bool_vote.exists():
                            vote = bool_vote[0]
                            if vote.boolean_value != val:
                                vote.boolean_value = val
                                vote.save()
                        else:
                            b = BooleanVote.objects.create(
                                proposal=proposed_action.proposal,
                                user=u,
                                boolean_value=val)
                            logger.info('created vote')
Exemple #6
0
def discord_listener_actions():
    for community in DiscordCommunity.objects.all():
        actions = []

        req = urllib.request.Request(
            'https://discordapp.com/api/guilds/%s/channels' %
            community.team_id)
        req.add_header("Content-Type", "application/x-www-form-urlencoded")
        req.add_header('Authorization', 'Bot %s' % DISCORD_BOT_TOKEN)
        req.add_header(
            "User-Agent", "Mozilla/5.0"
        )  # yes, this is strange. discord requires it when using urllib for some weird reason
        resp = urllib.request.urlopen(req)
        channels = json.loads(resp.read().decode('utf-8'))

        for channel in channels:
            channel_id = channel['id']

            # Post Message
            call_type = ('channels/%s/messages' % channel_id)

            req = urllib.request.Request(
                'https://discordapp.com/api/channels/%s/messages' % channel_id)
            req.add_header("Content-Type", "application/x-www-form-urlencoded")
            req.add_header('Authorization', 'Bot %s' % DISCORD_BOT_TOKEN)
            req.add_header(
                "User-Agent", "Mozilla/5.0"
            )  # yes, this is strange. discord requires it when using urllib for some weird reason
            resp = urllib.request.urlopen(req)
            messages = json.loads(resp.read().decode('utf-8'))

            for message in messages:
                if not is_policykit_action(community, message['id'], 'id',
                                           call_type):
                    post_exists = DiscordPostMessage.objects.filter(
                        id=message['id'])
                    if not post_exists.exists():
                        new_api_action = DiscordPostMessage()
                        new_api_action.community = community
                        new_api_action.text = message['content']
                        new_api_action.channel = message['channel_id']
                        new_api_action.id = message['id']

                        u, _ = DiscordUser.objects.get_or_create(
                            username=message['author']['id'],
                            community=community)
                        new_api_action.initiator = u
                        actions.append(new_api_action)

            # Rename Channel
            call_type = ('channels/%s' % channel_id)

            if not is_policykit_action(community, channel['name'], 'name',
                                       call_type):
                new_api_action = DiscordRenameChannel()
                new_api_action.community = community
                new_api_action.name = channel['name']
                new_api_action.channel = channel['id']

                actions.append(new_api_action)

        for action in actions:
            for policy in PlatformPolicy.objects.filter(
                    community=action.community):
                if filter_policy(policy, action):
                    if not action.pk:
                        action.community_origin = True
                        action.is_bundled = False
                        action.save()
                    check_result = check_policy(policy, action)
                    if check_result == Proposal.PROPOSED or check_result == Proposal.FAILED:
                        action.revert()

        # Boolean voting

        proposed_actions = PlatformAction.objects.filter(
            community=community,
            proposal_status=Proposal.PROPOSED,
            community_post__isnull=False)

        for proposed_action in proposed_actions:
            channel_id = proposed_action.channel
            message_id = proposed_action.id

            for reaction in [
                    EMOJI_LIKE_ENCODED, EMOJI_DISLIKE_ENCODED,
                    EMOJI_ZERO_ENCODED, EMOJI_ONE_ENCODED, EMOJI_TWO_ENCODED,
                    EMOJI_THREE_ENCODED, EMOJI_FOUR_ENCODED,
                    EMOJI_FIVE_ENCODED, EMOJI_SIX_ENCODED, EMOJI_SEVEN_ENCODED,
                    EMOJI_EIGHT_ENCODED, EMOJI_NINE_ENCODED
            ]:
                call = ('channels/%s/messages/%s/reactions/%s' %
                        (channel_id, message_id, reaction))
                users_with_reaction = community.make_call(call)

                for user in users_with_reaction:
                    u = DiscordUser.objects.filter(username=user.id,
                                                   community=community)

                    if u.exists():
                        u = u[0]

                        # Check for Boolean votes
                        if reaction in [
                                EMOJI_LIKE_ENCODED, EMOJI_DISLIKE_ENCODED
                        ]:
                            bool_vote = BooleanVote.objects.filter(
                                proposal=proposed_action.proposal, user=u)

                            if reaction == EMOJI_LIKE_ENCODED:
                                val = True
                            else:
                                val = False

                            if bool_vote.exists():
                                vote = bool_vote[0]
                                if vote.boolean_value != val:
                                    vote.boolean_value = val
                                    vote.save()
                            else:
                                b = BooleanVote.objects.create(
                                    proposal=proposed_action.proposal,
                                    user=u,
                                    boolean_value=val)