<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12

      WCF從理論到實(shí)踐(8):事件廣播

      上文討論了WCF中三種消息交換模式,one-way,request/reply,duplex。前兩項(xiàng)比較簡(jiǎn)單,無(wú)需多言,duplex相對(duì)比較復(fù)雜,上文只是實(shí)現(xiàn)了簡(jiǎn)單的回調(diào),在真正應(yīng)用的時(shí)候,還有許多值得注意之處,本文就結(jié)合一個(gè)實(shí)際的應(yīng)用例子來(lái)談?wù)撓耫uplex的具體應(yīng)用和非常值得我們注意的地方。

      本文的出發(fā)點(diǎn)

      通過(guò)閱讀本文,您能理解以下知識(shí):

      1. 如何實(shí)現(xiàn)一個(gè)基于duplex的事件廣播
      2. 解析在實(shí)現(xiàn)duplex事件廣播中的幾個(gè)問(wèn)題
      3. 初步探討一下異步

      本文適合的讀者

      本文屬于中等難度的文章,需要有WCF消息交換和windows應(yīng)用程序開(kāi)發(fā)相關(guān)的基礎(chǔ)知識(shí),有關(guān)WCF消息交換,請(qǐng)閱讀http://www.rzrgm.cn/jillzhang/archive/2008/02/17/1071521.html

      如何實(shí)現(xiàn)一個(gè)基于duplex的事件廣播

      在討論如何實(shí)現(xiàn)之前,先看一下本文的范例所要實(shí)現(xiàn)的功能是什么?本文的范例實(shí)現(xiàn)了一個(gè)簡(jiǎn)單的分布式任務(wù)管理系統(tǒng),簡(jiǎn)單的說(shuō),它是在服務(wù)端(Server Point)執(zhí)行任務(wù)(Job),并且將任務(wù)的信息呈現(xiàn)給客戶端。它有如下特征:

      1. 通過(guò)調(diào)用服務(wù)端的Accept(),客戶端能連接上服務(wù)端,并保持會(huì)話。
      2. 客戶端在啟動(dòng)的時(shí)候,可以通過(guò)遠(yuǎn)程調(diào)用GetJobs()來(lái)獲取當(dāng)前服務(wù)端中全部的任務(wù),并將這些任務(wù)在客戶端窗體中用列表控件呈現(xiàn)出來(lái)
      3. 客戶端能通過(guò)調(diào)用AddJob()向服務(wù)端添加任務(wù),當(dāng)服務(wù)端完成添加操作之后,引發(fā)添加完成的事件,并向全部的客戶端廣播該事件
      4. 當(dāng)客戶端服務(wù)端發(fā)來(lái)的添加新任務(wù)事件廣播的時(shí)候,客戶端將新增任務(wù)添加到列表控件加以呈現(xiàn)
      5. 客戶端可以命令服務(wù)端執(zhí)行具體某個(gè)任務(wù),當(dāng)任務(wù)在開(kāi)始執(zhí)行和執(zhí)行結(jié)束后,服務(wù)端都會(huì)像全部客戶端廣播任務(wù)的執(zhí)行情況,并且任務(wù)的執(zhí)行和事件的廣播異步執(zhí)行
      6. 客戶端收到廣播后,便可以更新任務(wù)信息。

      和以前文章不同,本文先給出最后實(shí)現(xiàn)的效果

      如何您要了解該范例得具體設(shè)計(jì)和實(shí)現(xiàn),可以下載下面的文件進(jìn)行分析:
      范例最終實(shí)現(xiàn):/Files/jillzhang/Jillzhang.Event.rar
      我這里只列出范例中項(xiàng)目列表

      項(xiàng)目名稱(chēng)

      項(xiàng)目描述

      Jillzhang.Event.Core

      該項(xiàng)目用于定義WCF的契約,主要包括IServer服務(wù)契約,ICallback用于回調(diào)的服務(wù)契約,Job數(shù)據(jù)契約

      Jillzhang.Event.Service

      服務(wù)端的具體實(shí)現(xiàn),其中Server實(shí)現(xiàn)了一個(gè)有廣播事件能力的服務(wù)契約

      Jillzhang.Event.Host

      服務(wù)的宿主程序,一個(gè)ConsoleApplication

      Jillzhang.Event.Client

      客戶端實(shí)現(xiàn),用于消費(fèi)服務(wù)端。

      Jillzhang.Event.Client2

      和Jillzhang.Event.Client是一個(gè)實(shí)現(xiàn),但為了驗(yàn)證廣播,可與Jillzhang.Event.Client同時(shí)消費(fèi)服務(wù)端

       

      解析在實(shí)現(xiàn)duplex事件廣播中的幾個(gè)問(wèn)題

      1) Duplex模式對(duì)服務(wù)行為ConcurrencyMode的要求

      我們知道ConcurrencyMode是控制服務(wù)并發(fā)的,默認(rèn)情況下ConCurrendMode的值為Single,它設(shè)置服務(wù)運(yùn)行在單線程下,當(dāng)上一個(gè)請(qǐng)求未完成之前,服務(wù)是不接受下一個(gè)請(qǐng)求的。而duplex在進(jìn)行回調(diào)的時(shí)候,如果回調(diào)方法沒(méi)有被設(shè)置為 One-Way的交換模式,服務(wù)端是會(huì)等待客戶端對(duì)回調(diào)的響應(yīng)的,這可不是一件好事情,因?yàn)榉?wù)端并不能保證客戶端能正常地執(zhí)行回調(diào)并返回?cái)?shù)據(jù)。更多的情況下,我們期望回調(diào)在發(fā)出后能立即返回,方法有兩個(gè):a)將回調(diào)方法設(shè)置為One-Way交換模式 b)采用多線程。經(jīng)過(guò)我的測(cè)試,當(dāng)回調(diào)方法被設(shè)置了one-way模式后,將ConcurrencyMode設(shè)置為Single是可以實(shí)現(xiàn)duplex雙向通訊的。 要第二種方法也非常簡(jiǎn)單,只需要將ConcurrencyMode設(shè)置為Mutiple.此時(shí)即使回調(diào)方法不是one-way模式,也是可以完成duplex的。值得說(shuō)明一下的是ConcurrencyMode還有中性的屬性:ConcurrencyMode.Reentrant,說(shuō)句心里話,我不喜歡這個(gè)不倫不類(lèi)的家伙,他能實(shí)現(xiàn)在單線程下同時(shí)接受多個(gè)請(qǐng)求,但有利必有弊,這個(gè)家伙不能保證請(qǐng)求事務(wù)的完整性,使用的時(shí)候應(yīng)該謹(jǐn)慎。

      2)InstanceContextMode = InstanceContextMode.PerSession卻為何能實(shí)現(xiàn)廣播?

      如果將InstanceContextMode設(shè)置為PerSession,我們知道服務(wù)端對(duì)象是針對(duì)每一個(gè)會(huì)話的,也就是說(shuō)每個(gè)會(huì)話會(huì)產(chǎn)生一個(gè)對(duì)象實(shí)例,這樣如果要實(shí)現(xiàn)廣播,我們必須將當(dāng)前服務(wù)包含的會(huì)話信息用一個(gè)列表對(duì)象記錄下來(lái),廣播的時(shí)候,我們遍歷會(huì)話列表,進(jìn)行逐個(gè)回調(diào)。本示例中巧妙的利用了Event可包括多個(gè)委托實(shí)例的特征,一個(gè)靜態(tài)的Event對(duì)象針對(duì)每個(gè)會(huì)話創(chuàng)建一個(gè)委托實(shí)例便可以完成上述的要求。遍歷回調(diào)的方法便可以編寫(xiě)如下:  

              private void BroadcastEvent(CallbackEventArg e, ServerEventHanlder temp)
              
      {         
                  
      if (OnStatusChanged != null
      )
                  
      {
                      
      foreach (ServerEventHanlder handler in
       temp.GetInvocationList())
                      
      {
                          handler.BeginInvoke(
      this, e, new AsyncCallback(EndAsync), null
      );
                      }

                  }

              }

      3)困擾了我半天的問(wèn)題

      上篇文章中,已經(jīng)對(duì)duplex有了初步的認(rèn)識(shí),本以為本文的范例實(shí)現(xiàn)會(huì)很順利呢,可有一個(gè)問(wèn)題卻困擾了我半天,在回調(diào)的時(shí)候非常不穩(wěn)定,有時(shí)能回調(diào)4.5次,有時(shí)1,2次之后,再回調(diào)卻沒(méi)了響應(yīng),開(kāi)始百思不得其解,因?yàn)殚_(kāi)始幾次可成功回調(diào),為何會(huì)不穩(wěn)定呢?經(jīng)過(guò)好一番嘗試,也沒(méi)能解決,回調(diào)沒(méi)有響應(yīng),肯定是客戶端與服務(wù)端失去了連接,會(huì)話過(guò)期就會(huì)造成雙方通訊連接的中斷,經(jīng)過(guò)分析,我的系統(tǒng)是這樣的

      會(huì)不會(huì)在Accept后Do()方法前的過(guò)程中會(huì)話過(guò)期了呢?后來(lái)經(jīng)過(guò)驗(yàn)證,的確是此處的問(wèn)題,解決方法是通過(guò)設(shè)置操作契約的IsTerminating來(lái)實(shí)現(xiàn)會(huì)話的維護(hù),當(dāng)一個(gè)操作契約的IsTerminating被設(shè)置為false的時(shí)候,該操作不會(huì)導(dǎo)致會(huì)話的中斷,將IServer設(shè)計(jì)如下便解決了我的問(wèn)題 :

      using System;
      using System.Collections.Generic;
      using System.Linq;
      using System.Text;
      using System.ServiceModel;

      namespace Jillzhang.Event.Core
      {
          [ServiceContract(SessionMode 
      = SessionMode.Required, CallbackContract = typeof(ICallback))]
          
      public interface IServer
          
      {
              [OperationContract(IsOneWay 
      = true, IsInitiating = true, IsTerminating = false)]
              
      void Accept();        

              [OperationContract(IsOneWay
      =true,IsInitiating=false,IsTerminating=false)]
              
      void Do(string jobName);

              [OperationContract(IsOneWay 
      = true, IsInitiating = false, IsTerminating = false)]
              
      void AddJob(Job job);

              [OperationContract(IsOneWay
      =false,IsInitiating=false,IsTerminating=false)]
              List
      <Job> GetJobs();
          }

      }


      初步探討一下異步

      進(jìn)程間通訊是一件很耗時(shí)的事情,如果同步執(zhí)行會(huì)造成線程的阻塞,如果是在服務(wù)端,會(huì)降低服務(wù)的處理能力(這種說(shuō)法可能有些問(wèn)題,我會(huì)進(jìn)一步求證,估計(jì)保留,經(jīng)過(guò)查證多線程在服務(wù)端的好處在于提供對(duì)單個(gè)請(qǐng)求用多個(gè)線程處理的能力,從而防止完成一個(gè)請(qǐng)求之前,無(wú)法接受新的請(qǐng)求),如果是在客戶端,會(huì)給用戶帶來(lái)不好的體驗(yàn)。下面就分別探討一下如何實(shí)現(xiàn)服務(wù)端和客戶端的異步。

      在服務(wù)端,一個(gè)事件的異步可以通過(guò)delegate的BeginInvoke和EndInvoke來(lái)實(shí)現(xiàn),具體方法可以參見(jiàn)示例項(xiàng)目Jillzhang.Event.Service中的Server對(duì)象的方法BroadcastEvent方法的實(shí)現(xiàn)

      而在客戶端,我們可以起多個(gè)線程,當(dāng)然最方便快捷的辦法就是使用BackGroundWorker后臺(tái)線程來(lái)處理耗時(shí)比較長(zhǎng)的操作了,具體實(shí)現(xiàn)也可以參考Jillzhang.Event.Client項(xiàng)目中的Form1.cs實(shí)現(xiàn)。

      本文的參考資料

      1. http://www.rzrgm.cn/wayfarer/archive/2007/03/08/667865.html
      2. http://www.rzrgm.cn/caishiqi/archive/2007/10/05/914671.html
      3. http://msdn.microsoft.com/msdnmag/issues/06/10/wcfessentials/default.aspx

      本文中的范例 

      范例最終實(shí)現(xiàn):/Files/jillzhang/Jillzhang.Event.rar
       

      原來(lái)的示例代碼中,采用的Binding為NetTcpBinding,有朋友問(wèn)用WsDualHttpBinding的時(shí)候出現(xiàn)異常,也作了一個(gè)示例
      /Files/jillzhang/Jillzhang.Event_WsDualHttpBinding.rar

      posted @ 2008-02-24 12:06  Robin Zhang  閱讀(15825)  評(píng)論(29)    收藏  舉報(bào)
      主站蜘蛛池模板: 日韩精品人妻中文字幕| 日本伊人色综合网| 国产精品高清视亚洲乱码| 中文日韩在线一区二区| 婷婷四虎东京热无码群交双飞视频 | 日本一区二区三区专线| 最近中文字幕完整版2019| 国产精品久久精品| 国产精品福利中文字幕| 黄网站色视频免费观看| 亚洲欧洲一区二区三区久久| 亚洲欧洲日产国码久在线| 毛片一区二区在线看| 国产一区二区三区色噜噜| 亚洲高清成人av在线| 久本草在线中文字幕亚洲| 国产爆乳无码视频在线观看3| gogogo高清在线观看视频中文 | 亚洲男人在线天堂| 国产在线欧美日韩精品一区| 景德镇市| 熟女一区| 亚洲中文字幕无码专区| 精品超清无码视频在线观看| 国内偷自第一区二区三区| 亚洲熟妇色xxxxx亚洲| 日本久久99成人网站| 国产成人精品亚洲日本语言| 亚洲 日本 欧洲 欧美 视频| 亚洲国产精品视频一二区| 国产成人精品无码免费看夜聊软件| 激情五月天一区二区三区| 少妇高潮喷潮久久久影院| 中文成人无字幕乱码精品区| 国产一区在线观看不卡| 熟女系列丰满熟妇AV| 国产乱人伦真实精品视频| 综合色一色综合久久网| 久久精品无码一区二区三区| 成 人 色 网 站免费观看| 亚洲另类激情专区小说婷婷久|