簡體   English   中英

如何在非自托管的WCF服務庫中執行初始化?

[英]How can I perform initialisation in a WCF service library that isn't self-hosted?

我已經創建了一個WCF服務庫,其中包含一個簡單的“hello world”測試服務和一個正確配置的App.config文件,因此當我啟動客戶端應用程序時,WCF服務是通過Visual Studio的內置主機啟動的。 現在的服務與我的客戶端中的外部配置一起正常工作。

我需要運行一些初始化代碼來設置DI,數據訪問,日志記錄等。我已經編寫了一個可以做到這一點的控制台主機,並且服務本身最終將部署為Windows服務,但我想使用內置的-in host,這樣我就不必在開發過程中手動重啟服務。

有沒有什么方法可以掛鈎庫中的一些代碼,以便在啟動時調用?

我發現了另一個關於使用自定義ServiceHostFactory執行引導的問題 ,該引導是通過*.svc文件設置的。 *.svc文件是WCF服務應用程序的一部分,不能由WCF服務直接使用。 我想堅持使用服務庫來實現服務和最終生產托管的一些靈活性,但是使用WCF服務應用程序將以適合開發的方式完成工作(並且可能很容易丟棄使用備用配置集進入IIS進行生產托管)。 所以我想我只需要創建一個WCF服務應用程序,它充當服務庫中服務的主機,並執行所需的初始化。

我首先創建了一個新的WCF服務應用程序,刪除了VS創建的默認服務文件,並添加了對現有服務庫和其他依賴項的引用。

在服務應用程序的Web.Config文件中,在<configSections>..</configSections>部分(需要是<configuration>標記之后的第一個節點)下,我為服務添加了<system.serviceModel>部分。庫(可以從服務庫中的App.config文件中提取並編輯以適應)。

例如:

<system.serviceModel>
  <services>
    <service behaviorConfiguration="MyServiceBehavior" name="BelfryImages.QueryService.Implementation.HelloWorld">
      <endpoint address="HelloWorld" binding="wsHttpBinding" name="HelloWorld" contract="BelfryImages.QueryService.Contracts.IHelloWorld" />
    </service>
  </services>

  <behaviors>
    <serviceBehaviors>
      <behavior name="MyServiceBehavior">
        <serviceMetadata httpGetEnabled="true" />
        <serviceDebug includeExceptionDetailInFaults="true" />
      </behavior>
    </serviceBehaviors>
  </behaviors>

  <bindings>
  </bindings>
</system.serviceModel>

請注意, BelfryImages.QueryService.Implementation.HelloWorld是服務契約(接口) BelfryImages.QueryService.Contracts.IHelloWorld的服務實現(實現類)的BelfryImages.QueryService.Contracts.IHelloWorld 我實際上有兩個單獨的組件; BelfryImages.QueryService.Contracts.dll是WCF服務庫。

我向服務應用程序添加了一個新的空白.svc文件,命名為匹配端點,例如HelloWorld.svc 通常,將WCF服務添加到WCF服務應用程序會生成.svc文件和.cs隱藏文件,其中包含服務的實現。 我手動添加了沒有代碼隱藏的.svc文件,並將其指向服務庫實現:

<%@ ServiceHost Language="C#" Debug="true" Service="BelfryImages.QueryService.Implementation.HelloWorld" %>

在第一次將客戶端的服務URL從http://localhost:XXXXX/QueryService/HelloWorld更改為http://localhost:XXXXX/HelloWorld.svc/HelloWorld之后,這可用作VS托管服務庫的替代品http://localhost:XXXXX/HelloWorld.svc/HelloWorld

然后,我創建了ServiceHostFactory來執行服務的初始化。 我找到了一篇MSDN文章( 托管和使用WCF服務 ),解釋了如何執行此操作 (清單5-6和5-7) - 為了我的目的,我只添加了一個更簡單的通用CustomHostFactory類:

public class CustomHostFactory
    : ServiceHostFactory
{
    protected override ServiceHost CreateServiceHost(Type serviceType, Uri[] baseAddresses)
    {
        // perform initialisation:
        ...

        var serviceHost = base.CreateServiceHost(serviceType, baseAddresses);
        return serviceHost;
    }
}

然后通過添加Factory屬性將其綁定到.svc文件中的服務:

<%@ ServiceHost Language="C#" Debug="true" Service="BelfryImages.QueryService.Implementation.HelloWorld" Factory="BelfryImages.WcfService.CustomHostFactory" %>

CreateServiceHost()覆蓋頂部的初始化是在照常創建服務之前執行的。 這似乎只發生在每個服務一次,而不是每次調用一次服務,但是會有多個服務的開銷。 這可能是通過使用靜態標志或類似的一次性。 目前似乎工作正常。

是否可以在實現服務的類的靜態構造函數中使用初始化代碼?

public class WCFService : IWCFService
{
    static WCFService()
    {
        // do initializing here
    }

}

此代碼將在對服務進行第一次調用時執行。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM