From 7373cb15d43a046a8d610e953dfa459ea0609db2 Mon Sep 17 00:00:00 2001 From: Ali Asadi Date: Tue, 21 Jul 2026 16:08:37 +0330 Subject: [PATCH] debug none sender uuid --- apps/chat/integrations/mattermost/client.py | 8 ++++++- apps/chat/services/message.py | 25 +++++++++------------ apps/chat/tests/test_conversation_close.py | 2 +- apps/chat/tests/test_messages.py | 18 +++++++-------- 4 files changed, 28 insertions(+), 25 deletions(-) diff --git a/apps/chat/integrations/mattermost/client.py b/apps/chat/integrations/mattermost/client.py index 8f5724a..3afb81c 100644 --- a/apps/chat/integrations/mattermost/client.py +++ b/apps/chat/integrations/mattermost/client.py @@ -156,9 +156,14 @@ class MattermostClient: return channel_id - def post_message(self, channel_id: str, message: str) -> str: + def post_message(self, channel_id: str, message: str, sender_uuid: UUID) -> str: """ Post a message to the given channel using the admin token. + + Every post is authored by the single service account, not the real + sender — there are no per-user tokens. `sender_uuid` is stamped into + the post's `props` so it can be recovered later in `get_posts()`; + Mattermost's own `user_id` on the post is always the service account. Returns the opaque mattermost_post_id string. """ try: @@ -166,6 +171,7 @@ class MattermostClient: options={ "channel_id": channel_id, "message": message, + "props": {"sender_uuid": str(sender_uuid)}, } ) return post["id"] diff --git a/apps/chat/services/message.py b/apps/chat/services/message.py index 2a75337..a074228 100644 --- a/apps/chat/services/message.py +++ b/apps/chat/services/message.py @@ -7,7 +7,7 @@ from apps.chat.events.publishers.push import PushPublisher from apps.chat.events.publishers.websocket import WebSocketPublisher from apps.chat.exceptions import ConversationClosedError from apps.chat.integrations.mattermost.client import MattermostClient -from apps.chat.models import Conversation, ConversationStatus, MattermostAccountMapping +from apps.chat.models import Conversation, ConversationStatus from apps.chat.services.account import AccountService from apps.chat.services.storage import StorageService @@ -62,7 +62,9 @@ class MessageService: else: mm_message = text or "" - post_id = self._mm.post_message(conversation.mattermost_channel_id, mm_message) + post_id = self._mm.post_message( + conversation.mattermost_channel_id, mm_message, sender_uuid + ) event = MessageSentEvent( chat_uuid=conversation_uuid, @@ -99,19 +101,14 @@ class MessageService: since=since, ) - mm_user_ids = {p["user_id"] for p in raw_posts if p.get("user_id")} - mappings = { - m.mattermost_user_id: m.user_uuid - for m in MattermostAccountMapping.objects.filter( - mattermost_user_id__in=mm_user_ids - ) - } if mm_user_ids else {} + return [self._normalize_post(p) for p in raw_posts] - return [self._normalize_post(p, mappings) for p in raw_posts] - - def _normalize_post(self, post: dict, mappings: dict) -> dict: - mm_uid = post.get("user_id") - sender_uuid = mappings.get(mm_uid) + def _normalize_post(self, post: dict) -> dict: + sender_uuid_raw = (post.get("props") or {}).get("sender_uuid") + try: + sender_uuid = UUID(sender_uuid_raw) if sender_uuid_raw else None + except ValueError: + sender_uuid = None msg = post.get("message", "") created_ms = post.get("create_at") created_at = ( diff --git a/apps/chat/tests/test_conversation_close.py b/apps/chat/tests/test_conversation_close.py index 4092c29..0f3de6d 100644 --- a/apps/chat/tests/test_conversation_close.py +++ b/apps/chat/tests/test_conversation_close.py @@ -109,4 +109,4 @@ def test_send_message_after_reopen_succeeds(): result = svc.send(conv.uuid, sender_uuid, "text", text="hello again") assert result["post_id"] == "post-1" - mm_client.post_message.assert_called_once_with("ch-close", "hello again") + mm_client.post_message.assert_called_once_with("ch-close", "hello again", sender_uuid) diff --git a/apps/chat/tests/test_messages.py b/apps/chat/tests/test_messages.py index d0126c4..9877dd5 100644 --- a/apps/chat/tests/test_messages.py +++ b/apps/chat/tests/test_messages.py @@ -3,7 +3,7 @@ from unittest.mock import Mock import pytest -from apps.chat.models import Conversation, MattermostAccountMapping +from apps.chat.models import Conversation from apps.chat.services.message import MessageService @@ -36,7 +36,7 @@ def test_send_text_message(): result = svc.send(conv.uuid, sender_uuid, "text", text="Hello world") - mm_client.post_message.assert_called_once_with("ch-send-text", "Hello world") + mm_client.post_message.assert_called_once_with("ch-send-text", "Hello world", sender_uuid) storage.get_download_url.assert_not_called() ws_publisher.publish.assert_called_once() @@ -62,7 +62,9 @@ def test_send_image_message(): result = svc.send(conv.uuid, sender_uuid, "image", object_key=object_key) storage.get_download_url.assert_called_once_with(object_key) - mm_client.post_message.assert_called_once_with("ch-send-image", f"image:{object_key}") + mm_client.post_message.assert_called_once_with( + "ch-send-image", f"image:{object_key}", sender_uuid + ) assert result["url"] == download_url assert result["message_type"] == "image" @@ -71,11 +73,7 @@ def test_send_image_message(): def test_list_messages_normalized(): conv = Conversation.objects.create(mattermost_channel_id="ch-list") sender_uuid = uuid.uuid4() - mm_user_id = "mm-user-xyz" - - MattermostAccountMapping.objects.create( - user_uuid=sender_uuid, mattermost_user_id=mm_user_id - ) + mm_user_id = "mm-service-bot" # every post is authored by the service account object_key = "voice/def456/clip.ogg" raw_posts = [ @@ -83,12 +81,14 @@ def test_list_messages_normalized(): "id": "p1", "user_id": mm_user_id, "message": "First message", + "props": {"sender_uuid": str(sender_uuid)}, "create_at": 1700000000000, }, { "id": "p2", "user_id": mm_user_id, "message": f"voice:{object_key}", + "props": {"sender_uuid": str(sender_uuid)}, "create_at": 1700000001000, }, { @@ -130,7 +130,7 @@ def test_list_messages_normalized(): system_msg = messages[2] assert system_msg["post_id"] == "sys1" - assert system_msg["sender_uuid"] == sender_uuid + assert system_msg["sender_uuid"] is None assert system_msg["mattermost_message_type"] == "system_add_to_channel" -- 2.45.3