2016-06-21 61 views
1

我正面臨着WCF和命名空間的一些問題。情況是這樣的:我的webservice(我們稱之爲「WS-A」)應該作爲另一個(更復雜的)web服務(「WS-B」)的代理。 WS-A爲我們開發的應用程序公開了更簡單的接口,因此它簡單地「隱藏」了一些我們不想在我們的應用程序中結束的業務邏輯。我們獲得了WS-B的WSDL和XSD模式,並使用svcutil將它們導入到C#中。顯然它繼承了WS-B的命名空間(http://ws.source.com)。對於WS-A,我們使用一些其他名稱空間(http://ws.example.com)。一些數據結構必須在兩個Web服務之間共享,但我無法重用相同的數據合同。 AFAIK WCF要求數據和服務合約的名稱空間是「靜態的」,並且不能在運行時決定。有沒有辦法與WCF做到這一點,或者我應該改變我的策略?在不同命名空間中共享數據合同

編輯:這裏是一個例子,試圖澄清我需要什麼。

 
            Namespace A  V  Namespace B 
           +--------------+ | +--------------+ 
           |    | | |    | 
      Application >-------+ Webservice A +-------+ Webservice B | 
           |    | | |    | 
           +--------------+ | +--------------+ 

應用程序調用WS-A的操作「GiveMeData」,該操作使用名稱空間A,如其WSDL中所述。響應所包含的類別「數據」,這實際上是使用命名空間B.

[DataContract(Namespace="http://namespaceB")] 
public class Data { 
...  
} 

所以響應將數據綁定到錯誤的命名空間從WS-B中得到的數據結構的引用。

+0

您是否考慮將共享數據合同移動到可以在服務之間共享的獨立程序集中?您可以在代碼中設置命名空間 - 例如'[DataContract(Namespace =「http://some.namespace.com/」)''。 – Tim

+0

問題是共享XSD命名空間而不是程序集命名空間之間的數據契約。我有一個對象,我想從/到/兩個名稱空間的序列化。 –

+0

如果我正確理解你的問題,我會改變這種策略。您可能會從不緊密耦合的數據合同中受益。 (當你每次簽訂合同B時都想改變合同A?) 我會使用單獨的名稱空間,但可能會通過繼承通用接口或類似工具來在WCF之外共享數據合同。 – Guran

回答

2

所以你想減少系統中重複代碼的數量,以及可能跳過一些似乎毫無意義的對象深層複製操作?

對問題的評論表明這是一個壞主意,我同意。無論您或後端Web服務是否需要更改合同(即使只是一點點),無論如何您都無法或將最終收到兩個數據聯繫人類。

相反,即使結構相同,也應該保留兩個POCO類定義,並用類似http://automapper.org的方式管理克隆/複製過程。這樣,您可以利用映射器中的一些轉換緩存,並保持代碼清潔。

如果您堅持在代理服務的兩端使用相同的POCO,您可能只想使用後端POCO進行編碼。但是,在序列化響應之後(在進入線程之前)以及在反序列化請求之前(在它變成POCO之前),您需要在WCF管道中操作消息。前者有點破解,您可以考慮它就像使用正則表達式替換名稱空間中的響應來重新編寫信息一樣,當你控制序列化的響應流時,這不是太難,但是你不控制發送到你的代理服務的東西,所以正則表達式來處理請求將會成比例地變得更加複雜,並且很容易出錯。看看這個WCF自定義消息編碼器的例子:https://social.msdn.microsoft.com/Forums/en-US/0da33309-ec07-47d6-8ddb-15290a80977f/wcf-hook-in-after-serialization?forum=wcf

該答案的作者有一些關於這個主題的其他博客文章,有不同的方法。 ,完成你的願望的代碼變得非常奇怪,真的很快。

+0

我對數據合同變化不大:我相當有信心:如果這些變化不是向後兼容的話,它們會打破數百個政府電子支付系統的客戶。但是如果他們破壞了某些東西(我們都知道政府的系統是天生的),我*必須*儘快更新我的代碼,以避免重複的代碼/類將幫助我實現可維護性(DRY原則)。 這就是說,我也同意重複的POCO是我得到的最好的選擇,automapper實際上是一個非常好的工具,可以幫助我的代碼保持整潔,所以謝謝。 ;) –