SuperSocket学习进展 下载本文

内置的命令行协议

内置的命令行协议(接受自定义,分隔符为“:”,“,”): 命令行协议定义了每个请求必须以回车换行结尾 \。

由于 SuperSocket 中内置的命令行协议用空格来分割请求的Key和参,因此当客户端发送如下数据到服务器端时:

\

SuperSocket 服务器将会收到一个 StringRequestInfo 实例,这个实例的属性为:

Key: \

Body: \

Parameters: [\

SuperSocket 提供了一些通用的协议解析工具, 你可以用他们简单而且快速的实现你自己的通信协议

\一个协议使用两个字符 \作为结束符

“CountSpliterReceiveFilter”:有些协议定义了像这样格式的请求

\每个请求有7个由 '#' 分隔的部分. 这种协议的实现非常简单:

“FixedSizeReceiveFilter”:在这种协议之中, 所有请求的大小都是相同的。如果你的每个请求都是有9个字符组成的字符串,如\你应该做的事就是想如下代码这样实现一个接收过滤器(ReceiveFilter):

“BeginEndMarkReceiveFilter”:在这类协议的每个请求之中 都有固定的开始和结束标记。例如, 我有个协议,它的所有消息都遵循这种格式 \。因此,在这种情况下, \是开始标记, \是结束标记,于是你的接受过滤器可以定义成这样:

“FixedHeaderReceiveFilter”:这种协议将一个请求定义为两大部分, 第一部分定义了包含第二部分长度等等基础信息. 我们通常称第一部分为头部.

例如, 我们有一个这样的协议: 头部包含 6 个字节, 前 4 个字节用于存储请求的名字, 后两个字节用于代表请求体的长度:

你需要基于类FixedHeaderReceiveFilter实现你自己的接收过滤器.

然后你就可以使用接收或者自己定义的接收过滤器工厂来在 SuperSocket 中启用该协议. 在.NET中的反射也可以实现从对象的外部来了解对象(或程序集)内部结构的功能,哪怕你不知道这个对象(或程序集)是个什么东西,另外.NET中的反射还可以运态创建出对象并执行它其中的方法。

这一块的内容负责让自定义的协议开始工作:

通信协议用于将接收到的二进制数据转化成您的应用程序可以理解的请求。 SuperSocket提供了一个内置的通信协议“命令行协议”定义每个请求都必须以回车换行\结尾。

但是一些应用程序无法使用命令行协议由于不同的原因。 这种情况下,你需要使用下面的工具来实现你的自定义协议: * RequestInfo * ReceiveFilter * ReceiveFilterFactory * AppServer and AppSession

请求(RequestInfo)

请求类型 StringRequestInfo 用在 SuperSocket 命令行协议中。

你也可以根据你的应用程序的需要来定义你自己的请求类型。 例如, 如果所有请求都包含 DeviceID 信息,你可以在RequestInfo类里为它定义一个属性

SuperSocket 还提供了另外一个请求类 \用于二进制协议:

接收过滤器(ReceiveFilter)

接收过滤器(ReceiveFilter)用于将接收到的二进制数据转化成请求实例(RequestInfo)。 实现一个接收过滤器(ReceiveFilter), 你需要实现接口 IReceiveFilter:

public interface IReceiveFilter where TRequestInfo : IRequestInfo {

///

/// Filters received data of the specific session into request info. ///

///

/// ///

/// ///

TRequestInfo Filter(byte[] readBuffer, int offset, int length, bool toBeCopied, out int rest);

///

/// Gets the size of the left buffer. ///

///

/// 接收过滤器已缓存数据的长度 ///

int LeftBufferSize { get; }

///

/// Gets the next receive filter. ///

IReceiveFilter NextReceiveFilter { get; }

///

/// Resets this instance to initial state.重置这个实例到初始化状态 ///

void Reset(); }

TRequestInfo: 类型参数 \是你要在程序中使用的请求类型(RequestInfo); LeftBufferSize: 该接收过滤器已缓存数据的长度;

NextReceiveFilter: 当下一块数据收到时,用于处理数据的接收过滤器实例; Reset(): 重设接收过滤器实例到初始状态;

Filter(....): 该方法将会在 SuperSocket 收到一块二进制数据时被执行,接收到的数据在 readBuffer 中从 offset 开始, 长度为 length 的部分。

TRequestInfo Filter(byte[] readBuffer, int offset, int length, bool toBeCopied, out int rest);

readBuffer: 接收缓冲区, 接收到的数据存放在此数组里 offset: 接收到的数据在接收缓冲区的起始位置 length: 本轮接收到的数据的长度

toBeCopied: 表示当你想缓存接收到的数据时,是否需要为接收到的数据重新创建一个备份而不是直接使用接收缓冲区

rest: 这是一个输出参数, 它应该被设置为当解析到一个为正的请求后,接收缓冲区还剩余多少数据未被解析

这儿有很多种情况需要你处理:

当你在接收缓冲区中找到一条完整的请求时,你必须返回一个你的请求类型的实例. 当你在接收缓冲区中没有找到一个完整的请求时, 你需要返回 NULL.

当你在接收缓冲区中找到一条完整的请求, 但接收到的数据并不仅仅包含一个请求时,设置剩余数据的长度到输出变量 \将会检查这个输出参数 \如果它大于 0, 此 Filter 方法 将会被再次执行, 参数 \和 \会被调整为合适的值.