楼主从12年毕业大部分时间一直从事于通讯网关的开发,刚刚学那会连C#是啥都不知道,就直接入手网关开发,前前后后到现在也算是弄了5、6个通讯协议,后来看到北风之神的socket框架和supersocket也是研究了很久,就在想着去自己搭建一个通讯网关框架。
这个框架原形当然是微软的高性能服务器框架,其中封装了一些业务逻辑等处理。
1 /// <summary> 2 /// 服务接口 3 /// </summary> 4 public interface IServer 5 { 6 string Name { get; } 7 void Start(int port); 8 void Start(EndPoint localPoint); 9 void Stop();10 }
/// <summary> /// 请求接口 /// </summary> public interface IRequestInfo { /// <summary> /// 唯一编号 /// </summary> string Key { get; set; } }
每种协议都有特定的格式,这个类就就是按特定命令格式生成的请求
1 /// <summary> 2 /// 消息过滤器 3 /// </summary> 4 /// <typeparam name="TRequestInfo">请求接口</typeparam> 5 public interface IReceiveFilter<TRequestInfo> 6 where TRequestInfo : IRequestInfo 7 { 8 /// <summary> 9 /// 消息解析10 /// </summary>11 /// <param name="message"></param>12 /// <returns></returns>13 List<TRequestInfo> Filter(ref byte[] message);14 }
消息的过滤器,处理tcp连接中的粘包断包等问题
1 /// <summary> 2 /// 网关接口 3 /// </summary> 4 /// <typeparam name="TRequestInfo">请求数据</typeparam> 5 /// <typeparam name="TReceiveFilter">消息过滤器</typeparam> 6 /// <typeparam name="TCommandFactory">命令工厂</typeparam> 7 public interface IGater<TRequestInfo, TReceiveFilter, out TCommandFactory> 8 where TRequestInfo : IRequestInfo 9 where TReceiveFilter : IReceiveFilter<TRequestInfo>10 {11 /// <summary>12 /// 配置13 /// </summary>14 BaseConfig Config { get; }15 /// <summary>16 /// 命令工厂17 /// </summary>18 TCommandFactory CommandFactory { get; }19 /// <summary>20 /// 服务程序21 /// </summary>22 TcpServer<TReceiveFilter, TRequestInfo> Server { get; }23 }
网关接口层
1 /// <summary> 2 /// 基础网关 3 /// </summary> 4 /// <typeparam name="TRequestInfo">请求数据接口</typeparam> 5 /// <typeparam name="TCommand">客户端命令接口</typeparam> 6 /// <typeparam name="TReceiveFilter">消息过滤器接口</typeparam> 7 /// <typeparam name="TCommandFactory">客户端命令解析工厂</typeparam> 8 public abstract class BaseGate<TRequestInfo, TCommand, TReceiveFilter, TCommandFactory> : IGater<TRequestInfo, TReceiveFilter, TCommandFactory> 9 where TRequestInfo : IRequestInfo10 where TCommand : ICommand<TRequestInfo>11 where TReceiveFilter : IReceiveFilter<TRequestInfo>, new()12 where TCommandFactory : ICommandFactory<TRequestInfo, TCommand>13 {14 /// <summary>15 /// 配置16 /// </summary>17 public BaseConfig Config { get; PRivate set; }18 /// <summary>19 /// 命令工厂20 /// </summary>21 public TCommandFactory CommandFactory { get; private set; }22 /// <summary>23 /// 服务24 /// </summary>25 public TcpServer<TReceiveFilter, TRequestInfo> Server { get; private set; }26 27 /// <summary>28 /// 构造函数29 /// </summary>30 /// <param name="server">socekt服务</param>31 /// <param name="commandFactory">命令工厂</param>32 /// <param name="config">服务配置</param>33 /// <param name="clientEvent">客户端事件处理</param>34 protected BaseGate(TcpServer<TReceiveFilter, TRequestInfo> server, TCommandFactory commandFactory, BaseConfig config, IClientEvent clientEvent)35 {36 CommandFactory = commandFactory;37 Server = server;38 Config = config;39 server.ClientOnClosed += clientEvent.ClientOnClosed;40 server.ClientOnConnected += clientEvent.ClientOnConnected;41 server.ReceiveNewData += ReceiveNewData;42 }43 44 /// <summary>45 /// 新数据处理46 /// </summary>47 /// <param name="request"></param>48 private void ReceiveNewData(TRequestInfo request)49 {50 var item = CommandFactory.CreateCommand(request);51 if (item != null)52 {53 item.ExcuteCommand(request);54 }55 }56 57 /// <summary>58 /// 初始化网关59 /// </summary>60 public void Init()61 {62 63 Server.Init(Config.MaxClientCounts, Config.BufferSize);64 Server.InitFilter(new TReceiveFilter());65 }66 /// <summary>67 /// 启动网关68 /// </summary>69 public void Start()70 {71 Server.Start(Config.Port);72 }73 }
网关的基本实现
1 /// <summary> 2 /// 客户端连接处理接口 3 /// </summary> 4 public interface IClientEvent 5 { 6 /// <summary> 7 /// 新连接 8 /// </summary> 9 /// <param name="sender"></param>10 /// <param name="e"></param>11 void ClientOnConnected(object sender, ClientEventArgs e);12 /// <summary>13 /// 连接断开14 /// </summary>15 /// <param name="sender"></param>16 /// <param name="e"></param>17 void ClientOnClosed(object sender, ClientEventArgs e);18 }
这个是客户端的连接处理,是根据requestinfo中key来标识唯一id,也可以在网关中实现,我是单独摘开的,因为可能架构多个服务器的话,多种协议
这里其实是封装了命令的处理,提供工厂接口以及命令接口,根据request请求生成
1 /// <summary> 2 /// 命令接口 3 /// </summary> 4 /// <typeparam name="TRequestInfo">请求接口</typeparam> 5 public interface ICommand<in TRequestInfo> 6 where TRequestInfo : IRequestInfo 7 { 8 /// <summary> 9 /// 客户端标识10 /// </summary>11 string Key { get; set; }12 /// <summary>13 /// 执行命令14 /// </summary>15 /// <param name="request"></param>16 void ExcuteCommand(TRequestInfo request);17 }
1 /// <summary> 2 /// 客户端命令工厂 3 /// </summary> 4 /// <typeparam name="TRequestInfo">请求接口</typeparam> 5 /// <typeparam name="TCommand">命令接口</typeparam> 6 public interface ICommandFactory<in TRequestInfo, out TCommand> 7 where TRequestInfo : IRequestInfo 8 where TCommand : ICommand<TRequestInfo> 9 {10 /// <summary>11 /// 构造命令12 /// </summary>13 /// <param name="request"></param>14 /// <returns></returns>15 TCommand CreateCommand(TRequestInfo request);16 }
大家只要继承上面的接口,基本就可以实现了。
这是下载地址,大家都看看,顺便给点意见
http://pan.baidu.com/s/1dDIOkyH
新闻热点
疑难解答