2009-09-01 57 views
14

我已經給出了一個用Java編寫的Web服務,我無法對其進行任何更改。它要求用戶通過基本身份驗證進行身份驗證才能訪問任何方法。在.NET中與此服務交互的建議方式是使用安裝了WSE 3.0的Visual Studio 2005。使用WCF無法使用基本身份驗證調用Web服務

這是一個問題,因爲該項目已經使用Visual Studio 2008(針對.NET 2.0)。我可以在VS2005中做到這一點,但是我不想將這個項目與VS2005聯繫起來,或者通過在VS2005中創建一個程序集並將其包含在VS2008解決方案中來實現(不管將來如何改變程序集)。我認爲這些選項中的任何一個都會讓新開發人員變得複雜,因爲他們強迫他們安裝WSE 3.0,並且使該項目未來能夠在.NET 3.5中使用2008和功能......也就是說,我真的相信使用WCF是要走的路。

我一直在尋找到使用WCF對於這一點,但我不能確定如何讓WCF服務,以瞭解它需要與每個請求一起發送認證報頭。當我嘗試對Web服務執行任何操作時,出現401錯誤。

這是我的代碼如下所示:

WebHttpBinding webBinding = new WebHttpBinding(); 
ChannelFactory<MyService> factory = 
    new ChannelFactory<MyService>(webBinding, new EndpointAddress("http://127.0.0.1:80/Service/Service/")); 
factory.Endpoint.Behaviors.Add(new WebHttpBehavior()); 
factory.Credentials.UserName.UserName = "username"; 
factory.Credentials.UserName.Password = "password"; 

MyService proxy = factory.CreateChannel(); 
proxy.postSubmission(_postSubmission); 

這將運行,並拋出以下異常:

The HTTP request is unauthorized with client authentication scheme 'Anonymous'. The authentication header received from the server was 'Basic realm=realm'.

這有一個內部異常:

The remote server returned an error: (401) Unauthorized.

任何想法可能會導致這個問題將不勝感激。

回答

26

第一個問題:這是一個基於SOAP或REST的Java服務你想打電話?

眼下,用「的WebHttpBinding」,您使用的是基於REST的方法。如果Java服務是SOAP服務,那麼您需要將綁定更改爲「basicHttpBinding」。

IF它是一個基於SOAP服務,你應該試試這個:

BasicHttpBinding binding = new BasicHttpBinding(); 

binding.SendTimeout = TimeSpan.FromSeconds(25); 

binding.Security.Mode = BasicHttpSecurityMode.Transport; 
binding.Security.Transport.ClientCredentialType = 
           HttpClientCredentialType.Basic; 

EndpointAddress address = new EndpointAddress(your-url-here); 

ChannelFactory<MyService> factory = 
      new ChannelFactory<MyService>(binding, address); 

MyService proxy = factory.CreateChannel(); 

proxy.ClientCredentials.UserName.UserName = "username"; 
proxy.ClientCredentials.UserName.Password = "password"; 

我用這個用各種網絡服務和它的作品 - 大部分時間。

如果不工作,你必須找到更多關於什麼的Java Web服務期望,以及如何到相關的信息發送給它。

馬克

+0

馬克,你能告訴我如何編寫代碼和配置,如果它是REST基於Java的服務? – rajibdotnet 2012-12-04 15:19:19

+2

在我鍵入代理後,屬性ClientCredentials完全不顯示。 – rajibdotnet 2012-12-04 15:29:47

+1

@rajibdotnet:好的,問題中的代碼基本上就是你需要調用基於REST的服務....如果這沒有幫助:請**問你自己的問題**所以人們可以回答... – 2012-12-04 15:32:08

3

我會加入到這個問題,以及基於我剛剛經歷了類似的問題。我用VS自動生成配置/代理 - 但它創建的配置實際上並不工作。

雖然它有安全模式=「運輸」正確設置,它沒有clientCredentialType =「基本」集。我補充說,我的配置,它仍然無法正常工作。然後我實際上刪除的工具,因爲我接觸的服務創建的郵件安全僅僅是SSL +基礎:

<message clientCredentialType="UserName" algorithmSuite="Default" /> 

瞧 - 它的工作。

我不確定爲什麼這會產生影響,考慮到元素沒有指定消息級別的安全性......但它確實如此。

6

首先在你的app.config或web.config中放入以下內容。 (不需要改變這個,你通過環境移動):

<system.serviceModel> 
     <bindings> 
      <basicHttpBinding> 
       <binding name="BasicHttpBinding_IConfigService"> 
        <security mode="TransportCredentialOnly"> 
         <transport clientCredentialType="Basic"/> 
        </security> 
       </binding> 
      </basicHttpBinding> 
     </bindings> 
     <client> 
      <endpoint address="http://localhost:55283/ConfigService.svc" 
       binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IConfigService" 
       contract="IConfigService" name="BasicHttpBinding_IService" /> 
     </client> 
    </system.serviceModel> 

變更合同屬性相應的的Namespace.Interface名。 注意安全模式= TransportCredentialOnly

現在以編程方式更改端點和憑據傳遞,使用下面的代碼:

  var myBinding = new BasicHttpBinding("BasicHttpBinding_IConfigService"); 
      var myEndpoint = new EndpointAddress("http://yourbaseurl/configservice.svc"); 
      var myChannelFactory = new ChannelFactory<IConfigService>(myBinding, myEndpoint); 

      var credentialBehaviour = myChannelFactory.Endpoint.Behaviors.Find<ClientCredentials>(); 
      credentialBehaviour.UserName.UserName = @"username"; 
      credentialBehaviour.UserName.Password = @"password"; 

      IConfigService client = null; 

      try 
      { 
       client = myChannelFactory.CreateChannel(); 
       var brands = client.YourServiceFunctionName(); 
       ((ICommunicationObject)client).Close(); 
      } 
      catch (Exception ex) 
      { 
       if (client != null) 
       { 
        ((ICommunicationObject)client).Abort(); 
       } 
      } 
+0

我不明白如何將該credentialBehavior應用於該頻道?它看起來就像您找到<>客戶端憑據並將其應用於新的Var credentialBehavior。然後設置該變量的用戶名和密碼......如果我沒有弄錯,那與綁定沒有任何關係,或者 – SoftwareSavant 2015-06-25 19:39:03

相關問題