chat_record.py 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201
  1. # coding=utf-8
  2. """
  3. @project: MaxKB
  4. @Author:虎虎
  5. @file: chat_record.py
  6. @date:2025/6/23 11:16
  7. @desc:
  8. """
  9. from typing import Dict
  10. from django.db import transaction
  11. from django.db.models import QuerySet
  12. from django.utils.translation import gettext_lazy as _, gettext
  13. from rest_framework import serializers
  14. from application.models import VoteChoices, ChatRecord, Chat, ApplicationAccessToken, VoteReasonChoices
  15. from application.serializers.application_chat import ChatCountSerializer
  16. from application.serializers.application_chat_record import ChatRecordSerializerModel, \
  17. ApplicationChatRecordQuerySerializers
  18. from common.db.search import page_search
  19. from common.exception.app_exception import AppApiException
  20. from common.utils.lock import RedisLock
  21. class VoteRequest(serializers.Serializer):
  22. vote_status = serializers.ChoiceField(choices=VoteChoices.choices,
  23. label=_("Bidding Status"))
  24. vote_reason = serializers.ChoiceField(choices=VoteReasonChoices.choices, label=_("Vote Reason"), required=False,
  25. allow_null=True)
  26. vote_other_content = serializers.CharField(required=False, allow_blank=True, label=_("Vote other content"))
  27. class HistoryChatModel(serializers.ModelSerializer):
  28. class Meta:
  29. model = Chat
  30. fields = ['id',
  31. 'application_id',
  32. 'abstract',
  33. 'create_time',
  34. 'update_time']
  35. class VoteSerializer(serializers.Serializer):
  36. chat_id = serializers.UUIDField(required=True, label=_("Conversation ID"))
  37. chat_record_id = serializers.UUIDField(required=True,
  38. label=_("Conversation record id"))
  39. @transaction.atomic
  40. def vote(self, instance: Dict, with_valid=True):
  41. if with_valid:
  42. self.is_valid(raise_exception=True)
  43. VoteRequest(data=instance).is_valid(raise_exception=True)
  44. rlock = RedisLock()
  45. if not rlock.try_lock(self.data.get('chat_record_id')):
  46. raise AppApiException(500,
  47. gettext(
  48. "Voting on the current session minutes, please do not send repeated requests"))
  49. try:
  50. chat_record_details_model = QuerySet(ChatRecord).get(id=self.data.get('chat_record_id'),
  51. chat_id=self.data.get('chat_id'))
  52. if chat_record_details_model is None:
  53. raise AppApiException(500, gettext("Non-existent conversation chat_record_id"))
  54. vote_status = instance.get("vote_status")
  55. # 未投票状态,可以进行投票
  56. if chat_record_details_model.vote_status == VoteChoices.UN_VOTE:
  57. # 投票时获取字段
  58. vote_reason = instance.get("vote_reason")
  59. vote_other_content = instance.get("vote_other_content") or ''
  60. if vote_status == VoteChoices.STAR:
  61. # 点赞
  62. chat_record_details_model.vote_status = VoteChoices.STAR
  63. chat_record_details_model.vote_reason = vote_reason
  64. chat_record_details_model.vote_other_content = vote_other_content
  65. if vote_status == VoteChoices.TRAMPLE:
  66. # 点踩
  67. chat_record_details_model.vote_status = VoteChoices.TRAMPLE
  68. chat_record_details_model.vote_reason = vote_reason
  69. chat_record_details_model.vote_other_content = vote_other_content
  70. chat_record_details_model.save()
  71. # 已投票状态
  72. else:
  73. if vote_status == VoteChoices.UN_VOTE:
  74. # 取消点赞
  75. chat_record_details_model.vote_status = VoteChoices.UN_VOTE
  76. chat_record_details_model.vote_reason = None
  77. chat_record_details_model.vote_other_content = ''
  78. chat_record_details_model.save()
  79. else:
  80. raise AppApiException(500, gettext("Already voted, please cancel first and then vote again"))
  81. finally:
  82. rlock.un_lock(self.data.get('chat_record_id'))
  83. ChatCountSerializer(data={'chat_id': self.data.get('chat_id')}).update_chat()
  84. return True
  85. class HistoricalConversationSerializer(serializers.Serializer):
  86. application_id = serializers.UUIDField(required=True, label=_('Application ID'))
  87. chat_user_id = serializers.UUIDField(required=True, label=_('Chat User ID'))
  88. def get_queryset(self):
  89. chat_user_id = self.data.get('chat_user_id')
  90. application_id = self.data.get("application_id")
  91. return QuerySet(Chat).filter(application_id=application_id, chat_user_id=chat_user_id,
  92. is_deleted=False).order_by('-update_time', 'id')
  93. def list(self):
  94. self.is_valid(raise_exception=True)
  95. queryset = self.get_queryset()
  96. return [HistoryChatModel(r).data for r in queryset]
  97. def page(self, current_page, page_size):
  98. self.is_valid(raise_exception=True)
  99. return page_search(current_page, page_size, self.get_queryset(), lambda r: HistoryChatModel(r).data)
  100. class EditAbstractSerializer(serializers.Serializer):
  101. abstract = serializers.CharField(required=True, label=_('Abstract'))
  102. class HistoricalConversationOperateSerializer(serializers.Serializer):
  103. application_id = serializers.UUIDField(required=True, label=_('Application ID'))
  104. chat_user_id = serializers.UUIDField(required=True, label=_('Chat User ID'))
  105. chat_id = serializers.UUIDField(required=True, label=_('Chat ID'))
  106. def is_valid(self, *, raise_exception=False):
  107. super().is_valid(raise_exception=True)
  108. e = QuerySet(Chat).filter(id=self.data.get('chat_id'), application_id=self.data.get('application_id'),
  109. chat_user_id=self.data.get('chat_user_id')).exists()
  110. if not e:
  111. raise AppApiException(500, _('Chat is not exist'))
  112. def edit_abstract(self, instance, with_valid=True):
  113. if with_valid:
  114. self.is_valid(raise_exception=True)
  115. EditAbstractSerializer(data=instance).is_valid(raise_exception=True)
  116. QuerySet(Chat).filter(id=self.data.get('chat_id'), application_id=self.data.get('application_id'),
  117. chat_user_id=self.data.get('chat_user_id')).update(abstract=instance.get('abstract'))
  118. return True
  119. def logic_delete(self, with_valid=True):
  120. if with_valid:
  121. self.is_valid(raise_exception=True)
  122. QuerySet(Chat).filter(id=self.data.get('chat_id'), application_id=self.data.get('application_id'),
  123. chat_user_id=self.data.get('chat_user_id')).update(is_deleted=True)
  124. return True
  125. class Clear(serializers.Serializer):
  126. application_id = serializers.UUIDField(required=True, label=_('Application ID'))
  127. chat_user_id = serializers.UUIDField(required=True, label=_('Chat User ID'))
  128. def batch_logic_delete(self, with_valid=True):
  129. if with_valid:
  130. self.is_valid(raise_exception=True)
  131. QuerySet(Chat).filter(application_id=self.data.get('application_id'),
  132. chat_user_id=self.data.get('chat_user_id')).update(is_deleted=True)
  133. return True
  134. class HistoricalConversationRecordSerializer(serializers.Serializer):
  135. application_id = serializers.UUIDField(required=True, label=_('Application ID'))
  136. chat_id = serializers.UUIDField(required=True, label=_('Chat ID'))
  137. chat_user_id = serializers.UUIDField(required=True, label=_('Chat User ID'))
  138. def is_valid(self, *, raise_exception=False):
  139. super().is_valid(raise_exception=True)
  140. chat_user_id = self.data.get('chat_user_id')
  141. application_id = self.data.get("application_id")
  142. chat_id = self.data.get('chat_id')
  143. chat_exist = QuerySet(Chat).filter(application_id=application_id, chat_user_id=chat_user_id,
  144. id=chat_id).exists()
  145. if not chat_exist:
  146. raise AppApiException(500, _('Non-existent chatID'))
  147. def get_queryset(self):
  148. chat_id = self.data.get('chat_id')
  149. return QuerySet(ChatRecord).filter(chat_id=chat_id).order_by('-create_time')
  150. def list(self):
  151. self.is_valid(raise_exception=True)
  152. queryset = self.get_queryset()
  153. return [ChatRecordSerializerModel(r).data for r in queryset]
  154. def page(self, current_page, page_size):
  155. self.is_valid(raise_exception=True)
  156. application_access_token = QuerySet(ApplicationAccessToken).filter(
  157. application_id=self.data.get('application_id')).first()
  158. show_source = False
  159. show_exec = False
  160. if application_access_token is not None:
  161. show_exec = application_access_token.show_exec
  162. show_source = application_access_token.show_source
  163. return ApplicationChatRecordQuerySerializers(
  164. data={'application_id': self.data.get('application_id'), 'chat_id': self.data.get('chat_id')}).page(
  165. current_page, page_size, show_source=show_source, show_exec=show_exec)