程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> .NET網頁編程 >> 關於.NET >> WCF安全系列(二) - netTCPBinding綁定之Transport安全模式

WCF安全系列(二) - netTCPBinding綁定之Transport安全模式

編輯:關於.NET

一、netTCPBinding.1

1、安全模式 – None.2

2、安全模式 - Transport.4

2.1.客戶端驗證:Windows.4

2.2.客戶端驗證:None.5

2.2.1.獲得和安裝證書...6

2.2.2.服務端代碼...6

2.2.3.客戶端代碼...6

2.2.4.測試...7

2.3.客戶端驗證:Certificate.8

2.3.1.獲得和安裝證書...9

2.3.2.服務端代碼...9

2.3.3.客戶端代碼...9

2.3.4.測試...10

2.3.5.證書映射到windows用戶...10

一、netTCPBinding

此綁定使用TCP傳輸協議,不具交互性,只適用於 WCF 到 WCF 的通信。

此綁定的傳輸安全性的實現:

l 安全模式Message

這種模式WCF中都一樣,都是使用WS-*通過對SOAP消息本身進行加密、簽名等 等的處理來保證安全性。Message模式不依賴於傳輸協議。服務端需要指定服務 端證書,用來加密服務端和客戶端相互傳送的消息。

l Transport – 客戶端windows驗證

使用windows security保證消息的安全,使用windows credential進行身份 驗證。

這種方式不需要服務端證書。

至於windows security的實現安全的原理我還不明白,這部分尚待了解。

l Transport – 客戶端其他驗證方式

使用TLS over TCP實現傳輸安全性,需要服務端證書。

一般大家對SSL比較熟悉,對TLS可能要陌生些,其實可以說TLS協議可以看作 跟SSL協議後續版本。1994年,netscape為了在internet上進行安全的數據傳輸 ,開發了的SSL協議,後來標准化組織把SSL標准化了,稍作修改改名叫TLS,在 一般的使用意義上,這兩個協議差別不大,就是在保證消息完整性的散列算法上 使用了不同的算法。

TLS over TCP 直接建立在TCP協議上,通過傳輸層TCP協議實現安全性。

netTCPBinding綁定是直接使用TCP協議,不走HTTP,所以不能使用IIS宿主。 這部分的測試實例采用自宿主的服務端console應用,基於代碼的方式。

測試環境

l 服務端:

服務器名:win2008

操作系統:Windows server 2008

開發環境:visual studio 2008

運行環境:.net framework 3.5

Web服務器: IIS 7.0

浏覽器:IE 7.0

l 客戶端:

服務端機器同時充當測試客戶端機器,同時准備了一台win2003的機器做測試 客戶端:

計算機名:win2003base2

操作系統:Windows server 2003

運行環境:.net framework 3.5

浏覽器:IE 7.0

共用測試WCF服務類

所有測試都是用同樣的服務端contract和實現這個contract的service:

[ServiceContract(Namespace = "http://chnking.com")]
public interface IGetIdentity
{
  [OperationContract]
  string Get(string ClientIdentity);
}
public class GetIdentity : IGetIdentity
{
  public string Get(string ClientIdentity)
  {
    return ("服務端Identity 是'" + ServiceSecurityContext.Current.PrimaryIdentity.Name +
      "'\n\r客戶端Identity是 '" + ClientIdentity + "'");
  }
}

代碼很簡單,一個contract提供了一個Get方法,接收一個string參數,返回 一個string參數。在後面的測試中,客戶端把客戶端安全上下文的Identity發送 到服務端,服務端返回服務端安全上下文的Identity給客戶端。

1、安全模式 – None

這部分的測試代碼:NetTcpBinding_None.rar

netTCPBinding綁定默認的安全模式是Transport,提供傳輸層的安全性,但 是也提供None安全模式的選擇,None安全模式不提供任何安全性和身份驗證。

這種方式的安全性:

完整性 不提供 保密性 不提供 服務端身份身份驗證 不提供 客戶端身份驗證 無,並忽略客戶端驗證的其他方式設置,固定為None

本例采用全代碼方式,不使用配置文件。

服務端代碼:

internal static void Main()
{
  NetTcpBinding myBinding = new NetTcpBinding();
  myBinding.Security.Mode = SecurityMode.None;
  myBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.None;
  Uri baseAddress = new Uri ("net.tcp://localhost:8056/WCFService/");
  myServiceHost = new ServiceHost(typeof(GetIdentity), baseAddress);
  ServiceEndpoint myServiceEndpoint = myServiceHost.AddServiceEndpoint
    (typeof(IGetIdentity), myBinding, "GetIdentity");
  ServiceMetadataBehavior behavior = new ServiceMetadataBehavior ();
  behavior.HttpGetEnabled = true;
  behavior.HttpGetUrl = new Uri ("http://localhost:8057/mex");
  myServiceHost.Description.Behaviors.Add(behavior);
  myServiceHost.Open();
  Console.WriteLine("Service started!");
  Console.ReadLine();
  myServiceHost.Close();
}

客戶端代碼:

static void Main(string[] args)
{
  NetTcpBinding myBinding = new NetTcpBinding();
  myBinding.Security.Mode = SecurityMode.None;
  myBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.None;

  EndpointAddress ea = new EndpointAddress ("net.tcp://localhost:8056/WCFService/GetIdentity");

  GetIdentityClient gc = new GetIdentityClient(myBinding, ea);
  //為使用TcpTrace跟蹤消息設置的TcpTrace監聽端口
  ClientViaBehavior myClientViaBehavior = new ClientViaBehavior
    (new Uri ("net.tcp://localhost:8055/WCFService/GetIdentity"));
  gc.Endpoint.Behaviors.Add(myClientViaBehavior);

  //執行代理類Get方法
  string result = gc.Get(WindowsIdentity.GetCurrent().Name);
  Console.WriteLine(result);
  Console.ReadLine();
}

客戶端設置了ClientVia的Vehavior,設置8055為監聽端口,8056為實際端口 ,同時運行TcpTrace來跟蹤通訊數據,客戶端運行結果:

TCPTrace工具抓客戶端和服務端的通訊數據:

從TcpTrace的截獲的通訊數據可以看出:

l netTCPBinding綁定采用binary編碼。

l netTCPBinding的None安全模式不對消息加密,從截獲的數據可以看到返 回的消息中文本部分是明文。

2、安全模式 - Transport

2.1.客戶端驗證:Windows

這部分的測試代碼: NetTcpBinding_Transport_Windows.rar

netTCPBinding綁定的Transport安全模式,提供傳輸層的安全性,客戶端 Windows驗證,此時將采用windows security在傳輸層來保證消息的安全性。

這種方式的安全性:

完整性 由windows security提供 保密性 由windows security提供 服務端身份身份驗證 Windows集成驗證 客戶端身份驗證 客戶端Windows credential通過Windows繼承驗證客戶端身份

本例采用全代碼方式,不使用配置文件。代碼部分是在前面None安全模式代 碼基礎上在服務端和客戶端的代碼中將安全模式改為Transport,客戶端驗證方 式改為Windows即可。

myBinding.Security.Mode = SecurityMode.Transport;
myBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.Windows;

客戶端運行結果:

TCPTrace工具抓客戶端和服務端的通訊數據:

從TcpTrace的截獲的通訊數據可以看出:

l netTCPBinding綁定式采用binary編碼。

l netTCPBinding的Transport安全模式對消息加密,從截獲的數據可以看到 返回的消息中也看不到明文。

2.2.客戶端驗證:None

這部分的測試代碼: NetTcpBinding_Transport_None.rar

netTCPBinding綁定的Transport安全模式,客戶端None驗證,此時將采用TLS 協議在傳輸層來保證消息的安全性。

這種方式的安全性:

完整性 由TLS提供 保密性 由TLS提供 服務端身份身份驗證 服務端證書提供 客戶端身份驗證 沒有

2.2.1.獲得和安裝證書

TLS跟SSL一樣,需要設置服務端證書。

這裡用Makecert.exe工具生成證書,使用下面的命令:

makecert -sr localmachine -ss My -n CN=win2008 -sky exchange -pe - r

這是服務端證書,win2008是服務端的機器名。

如果做過前面BasicHttpBinding的測試,這個服務端證書就應該已經有了。

2.2.2.服務端代碼

internal static ServiceHost myServiceHost = null;
internal static void Main()
{
  NetTcpBinding myBinding = new NetTcpBinding();
  myBinding.Security.Mode = SecurityMode.Transport;
  myBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.None;
  Uri baseAddress = new Uri ("net.tcp://win2008:8056/WCFService/");
  myServiceHost = new ServiceHost(typeof(GetIdentity), baseAddress);
  ServiceEndpoint myServiceEndpoint = myServiceHost.AddServiceEndpoint
    (typeof(IGetIdentity), myBinding, "GetIdentity");
  //設置服務端證書
  myServiceHost.Credentials.ServiceCertificate.SetCertificate ("CN=win2008");
  ServiceMetadataBehavior behavior = new ServiceMetadataBehavior ();
  behavior.HttpGetEnabled = true;
  behavior.HttpGetUrl = new Uri ("http://win2008:8057/mex");
  myServiceHost.Description.Behaviors.Add(behavior);
  myServiceHost.Open();
  Console.WriteLine("Service started!");
  Console.ReadLine();
  myServiceHost.Close();
}

2.2.3.客戶端代碼

static void Main(string[] args)
{
  NetTcpBinding myBinding = new NetTcpBinding();
  myBinding.Security.Mode = SecurityMode.Transport;
  myBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.Certificate;
  EndpointAddress ea = new EndpointAddress ("net.tcp://win2008:8056/WCFService/GetIdentity");
  GetIdentityClient gc = new GetIdentityClient(myBinding, ea);
  //設置不驗證服務端證書有效性
   gc.ClientCredentials.ServiceCertificate.Authentication.CertificateVali dationMode =
     System.ServiceModel.Security.X509CertificateValidationMode.None;
  //為使用TcpTrace跟蹤消息設置的TcpTrace監聽端口
  ClientViaBehavior myClientViaBehavior = new ClientViaBehavior
    (new Uri ("net.tcp://win2008:8055/WCFService/GetIdentity"));
  gc.Endpoint.Behaviors.Add(myClientViaBehavior);
  //執行代理類Get方法
  string result = gc.Get(WindowsIdentity.GetCurrent().Name);
  Console.WriteLine(result);
  Console.ReadLine();
}

2.2.4.測試

客戶端運行結果:

TCPTrace工具抓客戶端和服務端的通訊數據:

從TcpTrace的截獲的通訊數據可以看出:

l netTCPBinding綁定式采用binary編碼。

l netTCPBinding的Transport安全模式對消息加密,從截獲的數據可以看到 返回的消息中也看不到明文。

2.3.客戶端驗證:Certificate

這部分的測試代碼: NetTcpBinding_Transport_Certificate.rar

netTCPBinding綁定的Transport安全模式,客戶端Certificate驗證,此時將 采用TLS協議在傳輸層來保證消息的安全性。

這種方式的安全性:

完整性 由TLS提供 保密性 由TLS提供 服務端身份身份驗證 服務端證書提供 客戶端身份驗證 客戶端證書提供

2.3.1.獲得和安裝證書

TLS跟SSL一樣,需要設置服務端證書。

同時客戶端驗證設置為Certificate,就需要提供客戶端證書以驗證客戶端身 份。

所有這裡需要在服務端和客戶端分別安裝證書。

這裡用Makecert.exe工具生成證書,使用下面的命令:

makecert -sr localmachine -ss My -n CN=win2008 -sky exchange -pe - r

這是服務端證書,win2008是服務端的機器名。

如果做過前面BasicHttpBinding的測試,這個服務端證書就應該已經有了。

makecert -sr currentuser -ss My -n CN=TestClient -sky exchange -pe -r

這是客戶端證書。

2.3.2.服務端代碼

internal static ServiceHost myServiceHost = null;
internal static void Main()
{
  NetTcpBinding myBinding = new NetTcpBinding();
  myBinding.Security.Mode = SecurityMode.Transport;
  myBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.Certificate;
  Uri baseAddress = new Uri ("net.tcp://win2008:8056/WCFService/");
  myServiceHost = new ServiceHost(typeof(GetIdentity), baseAddress);
  ServiceEndpoint myServiceEndpoint = myServiceHost.AddServiceEndpoint
    (typeof(IGetIdentity), myBinding, "GetIdentity");
  //設置服務端證書
  myServiceHost.Credentials.ServiceCertificate.SetCertificate ("CN=win2008");
  //設置不驗證客戶端證書的有效性
   myServiceHost.Credentials.ClientCertificate.Authentication.Certificate ValidationMode =
     System.ServiceModel.Security.X509CertificateValidationMode.None;
  ServiceMetadataBehavior behavior = new ServiceMetadataBehavior ();
  behavior.HttpGetEnabled = true;
  behavior.HttpGetUrl = new Uri ("http://win2008:8057/mex");
  myServiceHost.Description.Behaviors.Add(behavior);
  myServiceHost.Open();
  Console.WriteLine("Service started!");
  Console.ReadLine();
  myServiceHost.Close();
}

2.3.3.客戶端代碼

static void Main(string[] args)
{
  NetTcpBinding myBinding = new NetTcpBinding();
  myBinding.Security.Mode = SecurityMode.Transport;
  myBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.Certificate;
  EndpointAddress ea = new EndpointAddress ("net.tcp://win2008:8056/WCFService/GetIdentity");
  GetIdentityClient gc = new GetIdentityClient(myBinding, ea);
  //設置客戶端證書
  gc.ClientCredentials.ClientCertificate.SetCertificate ("CN=TestClient",
    StoreLocation.CurrentUser, StoreName.My);
  //設置不驗證服務端證書有效性
   gc.ClientCredentials.ServiceCertificate.Authentication.CertificateVali dationMode =
     System.ServiceModel.Security.X509CertificateValidationMode.None;
  //為使用TcpTrace跟蹤消息設置的TcpTrace監聽端口
  ClientViaBehavior myClientViaBehavior = new ClientViaBehavior
    (new Uri ("net.tcp://win2008:8055/WCFService/GetIdentity"));
  gc.Endpoint.Behaviors.Add(myClientViaBehavior);
  //執行代理類Get方法
  string result = gc.Get(WindowsIdentity.GetCurrent().Name);
  Console.WriteLine(result);
  Console.ReadLine();
}

2.3.4.測試

由於客戶端是Certificate身份驗證,到了服務端 ServiceSecurityContext.Current.WindowsIdentity.Name獲得的是證書的 subject name和證書指紋。

2.3.5.證書映射到windows用戶

有時需要把客戶端證書映射為服務端的windows用戶,這樣可以使用windows 權限控制客戶端在服務端的權限。

在本例的情況,可以設置客戶端證書跟服務端windows用戶的映射,首先在服 務端的代碼或配置文件中設置允許客戶端證書到服務端windows用戶的映射。

代碼中將客戶端驗證MapClientCertificateToWindowsAccount設為True:

myServiceHost.Credentials.ClientCertificate.Authentication.Ma pClientCertificateToWindowsAccount = true;

配置文件中將服務端Behavior的客戶端證書驗證 MapClientCertificateToWindowsAccount設為True:

<serviceBehaviors>
   <behavior>
     <serviceCredentials>
       <clientCertificate>
          <authentication certificateValidationMode="None" mapClientCertificateToWindowsAccount="True" />
       </clientCertificate>
     </serviceCredentials>
   </behavior>
</serviceBehaviors>

然後根據不同的服務端不同的宿主分別設置映射,分兩種情況:

l 宿主為IIS 7.0

在IIS中設置客戶端證書到windows用戶的映射,可以一對一的映射,也可以 多對一的映射,具體參考文章:IIS 7 Walkthrough: One to One Client Certificate Mapping Configuration: http://blogs.iis.net/rlucero/archive/2008/05/23/iis-7-walkthrough-one -to-one-client-certificate-mapping-configuration.aspx

l 宿主為console應用或服務

這是直接在操作系統上把客戶端的證書與windows用戶作映射,這必須是要在 安裝了Active Directory的服務器上做。

具體步驟參考文章:Map certificates to user accounts:

http://technet2.microsoft.com/WindowsServer/f/?en/library/0539dcf5 -82c5-48e6-be8a-57bca16c7e171033.mspx

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved