コード例 #1
0
def send_messages(sender, instance, created, **kwargs):
    """When there is a message in a conversation we need to send it to any subscribed participants."""
    message = instance
    conversation = message.conversation

    topic = 'conversations:message'

    for subscription in ChannelSubscription.objects.recent().filter(
            user__in=conversation.participants.all()).distinct():

        payload = ConversationMessageSerializer(
            message, context={
                'request': MockRequest(user=subscription.user)
            }).data
        send_in_channel(subscription.reply_channel, topic, payload)

        if created and message.is_thread_reply(
        ) and subscription.user != message.author:
            payload = ConversationMessageSerializer(
                message.thread,
                context={
                    'request': MockRequest(user=subscription.user)
                }).data
            send_in_channel(subscription.reply_channel, topic, payload)

    # Send push notification and conversation updates when a message is created, but not when it is modified
    if not created:
        return

    tasks.notify_message_push_subscribers(message)

    # Send conversations object to participants after sending a message
    # (important for unread_message_count)
    # Exclude the author because their seen_up_to status gets updated,
    # so they will receive the `send_conversation_update` message
    topic = 'conversations:conversation'

    # Can be skipped for thread replies, as they don't alter the conversations object
    if message.is_thread_reply():
        return

    for subscription in ChannelSubscription.objects.recent()\
            .filter(user__in=conversation.participants.all())\
            .exclude(user=message.author).distinct():
        participant = conversation.conversationparticipant_set.get(
            user=subscription.user)
        payload = ConversationSerializer(
            participant,
            context={
                'request': MockRequest(user=subscription.user)
            }).data
        send_in_channel(subscription.reply_channel, topic, payload)
コード例 #2
0
ファイル: receivers.py プロジェクト: amengsk/karrot-backend
def send_reaction_update(sender, instance, **kwargs):
    reaction = instance
    message = reaction.message
    conversation = message.conversation

    topic = 'conversations:message'

    for subscription in ChannelSubscription.objects.recent() \
            .filter(user__in=conversation.participants.all()).distinct():
        payload = ConversationMessageSerializer(message, context={'request': MockRequest(user=subscription.user)}).data
        send_in_channel(subscription.reply_channel, topic, payload)
コード例 #3
0
ファイル: receivers.py プロジェクト: amengsk/karrot-backend
def send_thread_update(sender, instance, created, **kwargs):
    # Update thread object for user after updating their participation
    # (important for seen_up_to and unread_message_count)

    # Saves a few unnecessary messages if we only send on modify
    if created:
        return

    thread = instance.thread

    topic = 'conversations:message'
    payload = ConversationMessageSerializer(thread, context={'request': MockRequest(user=instance.user)}).data

    for subscription in ChannelSubscription.objects.recent().filter(user=instance.user):
        send_in_channel(subscription.reply_channel, topic, payload)
コード例 #4
0
ファイル: api.py プロジェクト: yohn-dezmon/karrot-backend
    def list(self, request, *args, **kwargs):
        queryset = self.get_queryset() \
            .exclude(conversation__latest_message_id=None) \
            .annotate_unread_message_count() \
            .annotate(conversation_latest_message_id=F('conversation__latest_message_id')) \
            .select_related(
                'conversation',
                'conversation__latest_message',
                'conversation__target_type',
             ) \
            .prefetch_related(
                'conversation__latest_message__reactions',
                'conversation__participants',
             ) \
            .order_by('-conversation__latest_message_id')
        queryset = self.filter_queryset(queryset)

        participations = self.paginate_queryset(queryset)
        conversations = [p.conversation for p in participations]

        messages = [
            c.latest_message for c in conversations
            if c.latest_message is not None
        ]

        # Prefetch related objects per target type
        pickup_ct = ContentType.objects.get_for_model(PickupDate)
        pickup_conversations = [
            item for item in conversations if item.target_type == pickup_ct
        ]
        pickups = PickupDate.objects. \
            filter(id__in=[c.target_id for c in pickup_conversations]). \
            prefetch_related('pickupdatecollector_set', 'feedback_given_by')

        applications_ct = ContentType.objects.get_for_model(Application)
        application_conversations = [
            item for item in conversations
            if item.target_type == applications_ct
        ]
        applications = Application.objects. \
            filter(id__in=[c.target_id for c in application_conversations]). \
            select_related('user')

        issues_ct = ContentType.objects.get_for_model(Issue)
        issue_conversations = [
            item for item in conversations if item.target_type == issues_ct
        ]
        issues = Issue.objects. \
            filter(id__in=[c.target_id for c in issue_conversations]). \
            prefetch_for_serializer(user=request.user)

        # Applicant does not have access to group member profiles, so we attach reduced user profiles
        my_applications = [a for a in applications if a.user == request.user]

        def get_conversation(application):
            return next(c for c in application_conversations
                        if c.target_id == application.id)

        users = get_user_model().objects. \
            filter(conversationparticipant__conversation__in=[get_conversation(a) for a in my_applications]). \
            exclude(id=request.user.id)

        context = self.get_serializer_context()
        serializer = self.get_serializer(participations, many=True)
        message_serializer = ConversationMessageSerializer(messages,
                                                           many=True,
                                                           context=context)
        pickups_serializer = PickupDateSerializer(pickups,
                                                  many=True,
                                                  context=context)
        application_serializer = ApplicationSerializer(applications,
                                                       many=True,
                                                       context=context)
        issue_serializer = IssueSerializer(issues, many=True, context=context)
        user_serializer = UserInfoSerializer(users, many=True, context=context)
        meta, _ = ConversationMeta.objects.get_or_create(user=request.user)
        meta_serializer = ConversationMetaSerializer(
            meta, context=self.get_serializer_context())

        return self.get_paginated_response({
            'conversations':
            serializer.data,
            'messages':
            message_serializer.data,
            'pickups':
            pickups_serializer.data,
            'applications':
            application_serializer.data,
            'issues':
            issue_serializer.data,
            'users_info':
            user_serializer.data,
            'meta':
            meta_serializer.data,
        })