如何从套接字读取整个消息以重建对象

本文关键字:消息 重建 对象 套接字 读取 | 更新日期: 2023-09-27 18:12:59

我正在发送一个消息,基本上是一个序列化到xml对象(SerializedXMLMessageObject)从服务器到客户端。

我试图读取整个消息并将其累积到MemoryStream中,然后才能对其进行反序列化。我遇到的问题是,它永远不会进入下面这个if-else的"else"部分。当它完成读取后,将跳转到else语句的结束括号。

两个问题:

  1. 我如何从套接字读取整个消息并保持与服务器的连接?是否有一种简单的方法来修复下面的代码,或者我必须提供某种分隔符?

  2. 我在哪里可以找到在c#中通过套接字发送xml序列化对象的例子?我遇到的每个例子都展示了如何发送一个简单的字符串。

编辑1:期望连接保持打开状态。也就是说,客户端与服务器保持连接。

private void callback(IAsyncResult result)
 {
   byte[] data = (byte[])result.AsyncState;
            try
            {
                int read = socket.EndReceive(result);
                if (read > 0)
                {
                    _memoryStream.Write(data, 0, read);
                    socket.BeginReceive(data, 0, 255, SocketFlags.None, new AsyncCallback(callback), data);
                }
                else
                {
                    SerializedXMLMessageObject msg = DeserializeFromXml<SerializedXMLMessageObject >(_memoryStream.ToArray());
                }             
            }
            catch (ObjectDisposedException)
            {
                socket.Close();
            }
        }

如何从套接字读取整个消息以重建对象

接受了建议,意识到了自己的问题。

从发送端我计算要发送的消息大小:

 byte[] data = ObjectToByteArray(SerializedXMLMessageObject);
 byte[] head = BitConverter.GetBytes(data.Length);
 byte[] total = new byte[data.Length + head.Length];
 head.CopyTo(total, 0);
 data.CopyTo(total, head.Length);
socket.Send(...)

在接收端,我将其转换为StateObject,提取消息大小并读取,直到完成。

stateObject.TotalMessageSize = BitConverter.ToInt32(stateObject.buffer, 0);

……

 if (state.received < state.expected)           
 {
  handler.BeginReceive(state.buffer, 0, StateObject.bufferSize,
                            SocketFlags.None, callback, stateobject);
 }