diff --git a/Realtime/Conversation/LCIMConversation.cs b/Realtime/Conversation/LCIMConversation.cs
index 2e40ddc..d6346a3 100644
--- a/Realtime/Conversation/LCIMConversation.cs
+++ b/Realtime/Conversation/LCIMConversation.cs
@@ -237,8 +237,11 @@ namespace LeanCloud.Realtime {
///
///
public async Task Join() {
- LCIMPartiallySuccessResult result = await AddMembers(new string[] { Client.Id });
- if (!result.IsSuccess) {
+ LCIMPartiallySuccessResult result = await Client.ConversationController.AddMembers(Id,
+ new string[] { Client.Id });
+ if (result.IsSuccess) {
+ ids.UnionWith(result.SuccessfulClientIdList);
+ } else {
LCIMOperationFailure error = result.FailureList[0];
throw new LCException(error.Code, error.Reason);
}
diff --git a/Realtime/Internal/Controller/LCIMConversationController.cs b/Realtime/Internal/Controller/LCIMConversationController.cs
index cf33ca9..6b3e38f 100644
--- a/Realtime/Internal/Controller/LCIMConversationController.cs
+++ b/Realtime/Internal/Controller/LCIMConversationController.cs
@@ -563,6 +563,48 @@ namespace LeanCloud.Realtime.Internal.Controller {
#region 消息处理
internal override async Task OnNotification(GenericCommand notification) {
+ if (notification.Cmd == CommandType.Conv) {
+ await OnConversation(notification);
+ } else if (notification.Cmd == CommandType.Unread) {
+ await OnUnread(notification);
+ }
+ }
+
+ private async Task OnUnread(GenericCommand notification) {
+ UnreadCommand unread = notification.UnreadMessage;
+
+ IEnumerable convIds = unread.Convs
+ .Select(conv => conv.Cid);
+ Dictionary conversationDict = (await Client.GetConversationList(convIds))
+ .ToDictionary(item => item.Id);
+ ReadOnlyCollection conversations = unread.Convs.Select(conv => {
+ // 设置对话中的未读数据
+ LCIMConversation conversation = conversationDict[conv.Cid];
+ conversation.Unread = conv.Unread;
+ if (conv.HasData || conv.HasBinaryMsg) {
+ // 如果有消息,则反序列化
+ LCIMMessage message = null;
+ if (conv.HasBinaryMsg) {
+ // 二进制消息
+ byte[] bytes = conv.BinaryMsg.ToByteArray();
+ message = LCIMBinaryMessage.Deserialize(bytes);
+ } else {
+ // 类型消息
+ message = LCIMTypedMessage.Deserialize(conv.Data);
+ }
+ // 填充消息数据
+ message.ConversationId = conv.Cid;
+ message.Id = conv.Mid;
+ message.FromClientId = conv.From;
+ message.SentTimestamp = conv.Timestamp;
+ conversation.LastMessage = message;
+ }
+ return conversation;
+ }).ToList().AsReadOnly();
+ Client.OnUnreadMessagesCountUpdated?.Invoke(conversations);
+ }
+
+ private async Task OnConversation(GenericCommand notification) {
ConvCommand convMessage = notification.ConvMessage;
switch (notification.Op) {
case OpType.Joined:
diff --git a/Realtime/Internal/Controller/LCIMMessageController.cs b/Realtime/Internal/Controller/LCIMMessageController.cs
index 830328f..8378080 100644
--- a/Realtime/Internal/Controller/LCIMMessageController.cs
+++ b/Realtime/Internal/Controller/LCIMMessageController.cs
@@ -223,40 +223,20 @@ namespace LeanCloud.Realtime.Internal.Controller {
#region 消息处理
internal override async Task OnNotification(GenericCommand notification) {
- if (notification.Cmd == CommandType.Patch) {
- await OnMessagePatched(notification);
- } else if (notification.Cmd == CommandType.Direct) {
+ if (notification.Cmd == CommandType.Direct) {
await OnMessaage(notification);
+ } else if (notification.Cmd == CommandType.Patch) {
+ await OnMessagePatched(notification);
+ } else if (notification.Cmd == CommandType.Rcp) {
+ await OnMessageReceipt(notification);
}
}
- private async Task OnMessagePatched(GenericCommand notification) {
- PatchCommand patchMessage = notification.PatchMessage;
- foreach (PatchItem patch in patchMessage.Patches) {
- // 获取对话
- LCIMConversation conversation = await Client.GetOrQueryConversation(patch.Cid);
- LCIMMessage message;
- if (patch.HasBinaryMsg) {
- byte[] bytes = patch.BinaryMsg.ToByteArray();
- message = LCIMBinaryMessage.Deserialize(bytes);
- } else {
- message = LCIMTypedMessage.Deserialize(patch.Data);
- }
- message.ConversationId = patch.Cid;
- message.Id = patch.Mid;
- message.FromClientId = patch.From;
- message.SentTimestamp = patch.Timestamp;
- message.PatchedTimestamp = patch.PatchTimestamp;
- if (message is LCIMRecalledMessage recalledMessage) {
- // 消息撤回
- Client.OnMessageRecalled?.Invoke(conversation, recalledMessage);
- } else {
- // 消息修改
- Client.OnMessageUpdated?.Invoke(conversation, message);
- }
- }
- }
-
+ ///
+ /// 接收消息事件
+ ///
+ ///
+ ///
private async Task OnMessaage(GenericCommand notification) {
DirectCommand direct = notification.DirectMessage;
// 反序列化消息
@@ -289,6 +269,58 @@ namespace LeanCloud.Realtime.Internal.Controller {
Client.OnMessage?.Invoke(conversation, message);
}
+ ///
+ /// 消息被修改事件
+ ///
+ ///
+ ///
+ private async Task OnMessagePatched(GenericCommand notification) {
+ PatchCommand patchMessage = notification.PatchMessage;
+ foreach (PatchItem patch in patchMessage.Patches) {
+ // 获取对话
+ LCIMConversation conversation = await Client.GetOrQueryConversation(patch.Cid);
+ LCIMMessage message;
+ if (patch.HasBinaryMsg) {
+ byte[] bytes = patch.BinaryMsg.ToByteArray();
+ message = LCIMBinaryMessage.Deserialize(bytes);
+ } else {
+ message = LCIMTypedMessage.Deserialize(patch.Data);
+ }
+ message.ConversationId = patch.Cid;
+ message.Id = patch.Mid;
+ message.FromClientId = patch.From;
+ message.SentTimestamp = patch.Timestamp;
+ message.PatchedTimestamp = patch.PatchTimestamp;
+ if (message is LCIMRecalledMessage recalledMessage) {
+ // 消息撤回
+ Client.OnMessageRecalled?.Invoke(conversation, recalledMessage);
+ } else {
+ // 消息修改
+ Client.OnMessageUpdated?.Invoke(conversation, message);
+ }
+ }
+ }
+
+ ///
+ /// 消息回执事件
+ ///
+ ///
+ ///
+ private async Task OnMessageReceipt(GenericCommand notification) {
+ RcpCommand rcp = notification.RcpMessage;
+ string convId = rcp.Cid;
+ string msgId = rcp.Id;
+ long timestamp = rcp.T;
+ bool isRead = rcp.Read;
+ string fromId = rcp.From;
+ LCIMConversation conversation = await Client.GetOrQueryConversation(convId);
+ if (isRead) {
+ Client.OnMessageRead?.Invoke(conversation, msgId);
+ } else {
+ Client.OnMessageDelivered?.Invoke(conversation, msgId);
+ }
+ }
+
#endregion
}
}
diff --git a/Realtime/Internal/Controller/LCIMRcpController.cs b/Realtime/Internal/Controller/LCIMRcpController.cs
deleted file mode 100644
index 7760117..0000000
--- a/Realtime/Internal/Controller/LCIMRcpController.cs
+++ /dev/null
@@ -1,29 +0,0 @@
-using System.Threading.Tasks;
-using LeanCloud.Realtime.Protocol;
-
-namespace LeanCloud.Realtime.Internal.Controller {
- internal class LCIMRcpController : LCIMController {
- internal LCIMRcpController(LCIMClient client) : base(client) {
-
- }
-
- #region 消息处理
-
- internal override async Task OnNotification(GenericCommand notification) {
- RcpCommand rcp = notification.RcpMessage;
- string convId = rcp.Cid;
- string msgId = rcp.Id;
- long timestamp = rcp.T;
- bool isRead = rcp.Read;
- string fromId = rcp.From;
- LCIMConversation conversation = await Client.GetOrQueryConversation(convId);
- if (isRead) {
- Client.OnMessageRead?.Invoke(conversation, msgId);
- } else {
- Client.OnMessageDelivered?.Invoke(conversation, msgId);
- }
- }
-
- #endregion
- }
-}
diff --git a/Realtime/Internal/Controller/LCIMUnreadController.cs b/Realtime/Internal/Controller/LCIMUnreadController.cs
deleted file mode 100644
index aab34dc..0000000
--- a/Realtime/Internal/Controller/LCIMUnreadController.cs
+++ /dev/null
@@ -1,51 +0,0 @@
-using System.Linq;
-using System.Threading.Tasks;
-using System.Collections.Generic;
-using System.Collections.ObjectModel;
-using LeanCloud.Realtime.Protocol;
-
-namespace LeanCloud.Realtime.Internal.Controller {
- internal class LCIMUnreadController : LCIMController {
- internal LCIMUnreadController(LCIMClient client) : base(client) {
-
- }
-
- #region 消息处理
-
- internal override async Task OnNotification(GenericCommand notification) {
- UnreadCommand unread = notification.UnreadMessage;
-
- IEnumerable convIds = unread.Convs
- .Select(conv => conv.Cid);
- Dictionary conversationDict = (await Client.GetConversationList(convIds))
- .ToDictionary(item => item.Id);
- ReadOnlyCollection conversations = unread.Convs.Select(conv => {
- // 设置对话中的未读数据
- LCIMConversation conversation = conversationDict[conv.Cid];
- conversation.Unread = conv.Unread;
- if (conv.HasData || conv.HasBinaryMsg) {
- // 如果有消息,则反序列化
- LCIMMessage message = null;
- if (conv.HasBinaryMsg) {
- // 二进制消息
- byte[] bytes = conv.BinaryMsg.ToByteArray();
- message = LCIMBinaryMessage.Deserialize(bytes);
- } else {
- // 类型消息
- message = LCIMTypedMessage.Deserialize(conv.Data);
- }
- // 填充消息数据
- message.ConversationId = conv.Cid;
- message.Id = conv.Mid;
- message.FromClientId = conv.From;
- message.SentTimestamp = conv.Timestamp;
- conversation.LastMessage = message;
- }
- return conversation;
- }).ToList().AsReadOnly();
- Client.OnUnreadMessagesCountUpdated?.Invoke(conversations);
- }
-
- #endregion
- }
-}
diff --git a/Realtime/LCIMClient.cs b/Realtime/LCIMClient.cs
index a5e7c24..8c2f3d1 100644
--- a/Realtime/LCIMClient.cs
+++ b/Realtime/LCIMClient.cs
@@ -231,10 +231,6 @@ namespace LeanCloud.Realtime {
get; private set;
}
- internal LCIMUnreadController UnreadController {
- get; private set;
- }
-
internal LCIMGoAwayController GoAwayController {
get; private set;
}
@@ -243,10 +239,6 @@ namespace LeanCloud.Realtime {
get; private set;
}
- internal LCIMRcpController RcpController {
- get; private set;
- }
-
#region 接口
public LCIMClient(string clientId,
@@ -289,9 +281,7 @@ namespace LeanCloud.Realtime {
SessionController = new LCIMSessionController(this);
ConversationController = new LCIMConversationController(this);
MessageController = new LCIMMessageController(this);
- UnreadController = new LCIMUnreadController(this);
GoAwayController = new LCIMGoAwayController(this);
- RcpController = new LCIMRcpController(this);
Connection = new LCConnection(Id) {
OnNotification = OnConnectionNotification,
@@ -446,21 +436,17 @@ namespace LeanCloud.Realtime {
_ = SessionController.OnNotification(notification);
break;
case CommandType.Conv:
+ case CommandType.Unread:
_ = ConversationController.OnNotification(notification);
break;
case CommandType.Direct:
case CommandType.Patch:
+ case CommandType.Rcp:
_ = MessageController.OnNotification(notification);
break;
- case CommandType.Unread:
- _ = UnreadController.OnNotification(notification);
- break;
case CommandType.Goaway:
_ = GoAwayController.OnNotification(notification);
break;
- case CommandType.Rcp:
- _ = RcpController.OnNotification(notification);
- break;
default:
break;
}
diff --git a/Test/Realtime.Test/Message.cs b/Test/Realtime.Test/Message.cs
index 47d2494..c721a41 100644
--- a/Test/Realtime.Test/Message.cs
+++ b/Test/Realtime.Test/Message.cs
@@ -1,12 +1,14 @@
using NUnit.Framework;
-using System.Collections.ObjectModel;
+using System;
+using System.Threading;
using System.Threading.Tasks;
+using System.Collections.Generic;
using LeanCloud;
using LeanCloud.Common;
using LeanCloud.Storage;
using LeanCloud.Realtime;
-using static NUnit.Framework.TestContext;
+using static System.Console;
namespace Realtime.Test {
public class Message {
@@ -34,25 +36,16 @@ namespace Realtime.Test {
}
[Test]
- [Order(0)]
public async Task Send() {
- TaskCompletionSource