WCF - 例項管理



WCF 用於將一組訊息(客戶端請求)繫結到服務例項的技術稱為例項管理。WCF 支援三種類型的例項啟用,本章將對此進行討論。

每次呼叫服務

每次呼叫服務是 WCF 的預設例項啟用模式。當 WCF 服務配置為每次呼叫服務時,將在客戶端呼叫或請求進行的持續時間內建立一個 CLR 物件。CLR 代表公共語言執行時,它包含 WCF 中的服務例項。

在每次呼叫服務中,每個客戶端請求都會獲得一個新的專用服務例項,並且與其他型別的例項啟用相比,其記憶體消耗更少。

為了指示 WCF 服務充當每次呼叫服務,需要將 InstanceContextMode 屬性設定為 InstanceContextMode.PerCall。InstanceContextMode 屬性屬於 ServiceBehavior 屬性。因此,可以按如下方式配置每次呼叫服務:

[ServiceContract]
interface IMyContract
{...}
[ServiceBehavior (InstanceContextMode = InstanceContextMode.PerCall)]
class MyService : IMyContract
{...} 

此處,服務表示為 IMyContract。下圖顯示了每次呼叫服務例項啟用的過程。

Wcf Instance Management Per Call Service

實現每次呼叫服務

[DataContract]
class Param {....}

[ServiceContract]
interface IMyContract {
   [OperationContract]
   void MyMethod(Param objectIdentifier);
}
class MyPerCallService : IMyContract, IDisposable {
   public void MyMethod(Param objectIdentifier) {
      GetState(objectIdentifier); 
      DoWork();
      SaveState(objectIdentifier);
   }
   
   void GetState(Param objectIdentifier) {....}
   void DoWork() {....}
   void SaveState(Param objectIdentifier) {....}
   public void Dispose() {....}
}

此處,Param 是為上述示例發明的偽型別引數。

每次會話服務

在此 WCF 啟用模式下,在兩個實體(即客戶端和特定服務例項)之間維護一個私有或我們可以稱之為機密的會話。每次會話服務也稱為私有會話服務,它提供一個新的服務例項,該例項專門用於每個客戶端請求,並且獨立於與該會話感知服務相關的所有其他例項。

要啟動每次會話服務,需要將 InstanceContextMode 屬性設定為 PerSession。在此,服務例項在整個會話持續時間內都保留在記憶體中。

此啟用模式存在可擴充套件性問題,因為配置的服務無法支援除少數(或可能最多幾百個)之外的任何其他未完成的客戶端,因為每個專用服務例項都會產生成本。

可以按如下方式配置每次會話服務:

[ServiceBehavior (InstanceContextMode = InstanceContextMode.PerSession)]
class MyService : IMyContract
{...}

每次會話服務的過程如下圖所示:

Wcf Instance Management Per Session Service

以下程式碼顯示了一個合同和服務,這些合同和服務配置為使用私有會話。輸出表明客戶端確實獲得了專用服務例項。

服務程式碼

[ServiceContract(Session = true)]
interface IMyContract {
   [OperationContract]
   void MyMethod();
}

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession)]
class MyService : IMyContract, IDisposable {
   int m_Counter = 0; MyService() {Console.WriteLine("MyService.MyService()"); }
   
   public void MyMethod() {
      m_Counter++;
      Console.WriteLine("Counter = " + m_Counter);
   }
   public void Dispose() { 
      Console.WriteLine("MyService.Dispose()"); 
   }
}

客戶端程式碼

MyContractProxy proxy = new MyContractProxy(); proxy.MyMethod(); proxy.MyMethod(); 
proxy.Close();

輸出

MyService.MyService() Counter = 1 Counter = 2 MyService.Dispose()

單例服務

在此 WCF 啟用模式下,所有相互獨立的客戶端請求都連線到同一個眾所周知的單個例項,而不管它們與服務端點的連線如何。僅當主機關閉時,單例服務才會被處置。

此服務僅在主機建立時建立一次。如果主機未提供任何單例例項,則服務將返回 NULL。當每個方法呼叫的工作量很少並且後臺沒有掛起的操作時,此啟用模式效果最佳。

需要將 InstanceContextMode 屬性設定為 InstanceContextMode.Single 以啟動此單例服務。

因此,可以按如下方式配置單例服務:

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]
class MySingleton : ...
{...}

單例服務的過程如下圖所示:

Wcf Instance Management Singleton Service

以下程式碼用於初始化和託管單例例項。

服務程式碼

[ServiceContract]
interface IMyContract {
   [OperationContract]
   void MyMethod( );
}
[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]
class MySingleton : IMyContract {
   int m_Counter = 0;
   
   public int Counter {
      get {
         return m_Counter;
      }
      set {
         m_Counter = value;
      }
   }
   public void MyMethod( ) {
      m_Counter++;
      Trace.WriteLine("Counter = " + Counter);
   }
}

主機程式碼

MySingleton singleton = new MySingleton( );
singleton.Counter = 42;
ServiceHost host = new ServiceHost(singleton);
host.Open( );

//Do some blocking calls then
host.Close( );

客戶端程式碼

MyContractClient proxy = new MyContractClient( );
proxy.MyMethod( );
proxy.Close( );

輸出

Counter = 43
廣告

© . All rights reserved.