zoukankan      html  css  js  c++  java
  • ESFramework网络通信框架介绍之(5)――消息分派器IMessageDispatcher

      从2004年7月开始,就一直从事N层C/S架构的服务端的开发,时至今日,慢慢的积累了一些开发经验,ESFramework网络通信框架体系便是这些经验的总结。ESFramework网络通信框架这是一套完全可复用的、灵活的、单纯的、支持N层C/S架构的网络通信框架,内置了对Tcp和Udp协议的支持。ESFramework网络通信框架不仅仅提供了一个基础的C/S框架和大量C/S应用中常用的组件,而且在ESFramework网络通信框架框架之上,引入的一个扩展层--ESFramework网络通信框架扩展层,专门用于解决的与具体应用相关的领域问题。

    一.ESFramework网络通信框架与消息分派器

    (本文原作于2006.03.14,第一次修正于2006.06.06,修正后适用于ESFramework V0.3+)

        本来Tcp/udp组件是系统与外界交换消息的唯一进出口,而Tcp组件或Udp组件与我们系统唯一的联系是通过消息分派器IMessageDispatcher,如此一来,就相当于ESFramework规定了消息分派器是我们应用与外界交换消息的进出口。IMessageDispatcher是与协议无关、宿主无关的组件,即,它即可以在使用于TCP协议也可使用于Udp协议,如果使用Remoting的方式通信也可以使用IMessageDispatcher来分派消息;它即可以用在服务端也可以用于客户端,这样的高可复用性使得基于不同底层(如Tcp/Udp、服务端/客户端)构建的上层应用具有高度的统一性,同时使得ESFramework网络通信框架的整个架构更加清晰、学习曲线更平滑。


        IMessageDispatcher保证接收到的每个消息和发送出去的每个消息都能被所有的HookSpy
    截获。另外,消息分派器可能需要验证接收到的每个消息格式是否正确、消息是否合法、消息是否符合特定规格等。下面是消息分派器组件的组成:
        
       
        消息分派器IMessageDispatcher定义如下:
       

        public interface IMessageDispatcher
        {
            IEsbLogger           EsbLogger{
    set ;}        
            INetMessageHook       NetMessageHook{
    set ;}//可为EsbNetMessageHook
            IGatewayMessageSpy GatewayMessageSpy{set;}
            IInnerMessageSpy   InnerMessageSpy{
    set;}    

            IContractHelper       ContractHelper{
    set ;}//必须设置
            INakeDispatcher    NakeDispatcher{set ;} //必须设置

            NetMessage DispatchMessage(NetMessage reqMsg) ;
            
            
    /// <summary>
            
    /// 如所有的SingleMessage在发送之前必须经过IMessageDispatcher的Hook链和Spy
            
    /// </summary>        
            NetMessage BeforeSendMessage(NetMessage msg) ;

            
    event CbNetMessage MessageReceived ;
        }    

        从IMessageDispatcher的组件结构图和接口的定义可以看出,IMessageDispatcher保证了将接受到的消息按照规定的顺序经过各个Spy、Hook、消息处理器等组件。任何消息不得例外。即使是系统内部生成的消息(如发给客户端的通知),也必须经过IMessageDispatcher的BeforeSendMessage后才可安全的发送出去。
        IMessageDispatcher的实现如下所示:

        public class MessageDispatcher :IMessageDispatcher
        {
            
    #region property
            
    #region Logger
            
    private IEsbLogger esbLogger = new EmptyEsbLogger() ;
            
    public  IEsbLogger EsbLogger
            {
                
    set
                {
                    
    if(value != null)
                    {
                        
    this.esbLogger = value ;
                    }
                }
            }
            
    #endregion

            
    #region NakeDispatcher    
            
    private INakeDispatcher nakeDispatcher ;
            
    public  INakeDispatcher NakeDispatcher
            {
                
    set
                {
                    
    this.nakeDispatcher = value ;
                }
            }
            
    #endregion                

            
    #region NetMessageHook
            
    private INetMessageHook netMessageHook = new EmptyNetMessageHook() ;
            
    public  INetMessageHook NetMessageHook 
            {
                
    set
                {
                    
    this.netMessageHook = value ;
                }
            }
            
    #endregion

            
    #region InnerMessageSpy        
            
    private IInnerMessageSpy innerMessageSpy = new EmptyInnerMessageSpy() ;
            
    public  IInnerMessageSpy InnerMessageSpy
            {
                
    set
                {
                    
    if(value != null)
                    {
                        
    this.innerMessageSpy = value ;
                    }

                }
            }
            
    #endregion
            
            
    #region GatewayMessageSpy    
            
    private IGatewayMessageSpy gatewayMessageSpy = new EmptyGatewayNetMessageSpy() ;
            
    public  IGatewayMessageSpy GatewayMessageSpy
            {
                
    set
                {
                    
    if(value != null)
                    {
                        
    this.gatewayMessageSpy = value ;
                    }
                }
            }
            
    #endregion

            
    #region ContractHelper
            
    private IContractHelper contractHelper = null ;
            
    public  IContractHelper ContractHelper
            {
                
    set
                {
                    
    this.contractHelper = value ;
                }
            }
            
    #endregion

            
    public event CbNetMessage MessageReceived;
            
    #endregion

            
    #region IMessageDispatcher 成员    

            
    public NetMessage DispatchMessage(NetMessage reqMsg)
            {
                
    try
                {
                    
    if(this.MessageReceived != null)
                    {
                        
    this.MessageReceived(reqMsg) ;
                    }

                    
    this.gatewayMessageSpy.SpyReceivedMsg(reqMsg) ;

                    NetMessage msgHooked 
    = this.netMessageHook.CaptureReceivedMsg(reqMsg) ;

                    
                    
    this.innerMessageSpy.SpyReceivedMsg(msgHooked) ;                
                    NetMessage resMsg 
    = this.nakeDispatcher.DispatchMessage(msgHooked) ;
                    
    if(reqMsg == null)
                    {
                        
    return null ;
                    }
                    
                    
    return this.BeforeSendMessage(resMsg) ;
                }
                
    catch(Exception ee)
                {
                    
    this.esbLogger.Log(ee.GetType().ToString() ,ee.Message ,"ESFramework.Network.MessageDispatcher.DispatchMessage" ,ErrorLevel.High) ;
                    
    return this.contractHelper.GetResponseByServiceResultType(reqMsg ,ServiceResultType.HandleFailure) ;                    
                }
            }

            
    public NetMessage BeforeSendMessage(NetMessage msg)
            {
                
    this.innerMessageSpy.SpyToBeSendedMsg(msg) ;
                NetMessage msgHooked 
    = this.netMessageHook.CaptureBeforeSendMsg(msg) ;
                
    this.gatewayMessageSpy.SpyToBeSendedMsg(msgHooked) ;

                
    return msgHooked ;            
            }


            
    #endregion
        }


        我们看到,IMessageDispatcher内部使用了INakeDispatcher组件,INakeDispatcher的职责比较单纯,它针对需要分派的消息调用IDataDealerFactory创建对应的处理器,然后将消息交给处理器处理后,将结果返回。其接口定义如下:

        public interface INakeDispatcher
        {
            NetMessage DispatchMessage(NetMessage msg) ;
        }

        INakeDispatcher的实现也非常简单:

        public class NakeDispatcher :INakeDispatcher
        {
            
    #region DataDealerFactory
            
    private IDataDealerFactory dataDealerFactory = null ; 
            
    public  IDataDealerFactory DataDealerFactory
            {
                
    set
                {
                    
    this.dataDealerFactory = value ;
                }
            }
            
    #endregion
            
            
    #region ContractHelper
            
    private IContractHelper contractHelper = null ; 
            
    public  IContractHelper ContractHelper
            {
                
    set
                {
                    
    this.contractHelper = value ;
                }
            }
            
    #endregion     

            
    #region INakeDispatcher 成员

            
    public NetMessage DispatchMessage(NetMessage msg)
            {
                IDataDealer dealer 
    = this.dataDealerFactory.CreateDealer(msg.Header.ServiceKey ,msg.Header.TypeKey) ;
                
    if(dealer == null)
                {
                    
    return this.contractHelper.GetResponseByServiceResultType(msg ,ServiceResultType.ServiceIsNotExist) ;
                }

                
    return dealer.DealRequestMessage(msg) ;
            }

            
    #endregion
        }

        通常,在客户端使用IMessageDispatcher组件时,我们不需要使用GatewayMessageSpy和InnerMessageSpy,如果是这样,那么我们只要不为MessageDispatcher的GatewayMessageSpy属性和InnerMessageSpy属性注入对象就可以了。

    上一篇:ESFramework网络通信框架介绍之(4)――消息拦截器INetMessageHook

    转到  :ESFramework 可复用的网络通信框架(序)
     

     

    版权声明:本文为博主原创文章,未经博主允许不得转载。

  • 相关阅读:
    txtbox取Calendar值
    【Spread Sheet 应用(一)】去掉原有功能键及添加功能键
    【SQLSERVER】存储过程基础
    【SQLSERVER】在存储过程中调用存储过程
    ASP.NET跨页面传值技巧(VB.NET篇)
    【EXCEL】IF...ELSE语句
    VB单元测试
    【VB.NET】窗体之间传值
    【Spread Sheet 应用(二)】常用属性设置
    【SQLSERCER】创建、改变、删除索引
  • 原文地址:https://www.cnblogs.com/zhuweisky/p/349616.html
Copyright © 2011-2022 走看看