使用WIF實現單點登入Part I——Windows Identity Foundation介紹及環境搭建

來源:互聯網
上載者:User

上個月有一個星期的時間都在研究asp.net mvc統一身分識別驗證及單點登入的實現。經過了一番的探索,最終決定使用微軟的Windows Identity Foundation。但是這東西用的人貌似不多,而且中文資料甚少,所以在測試的過程中走了不少彎路,所以寫下這一系列文章,希望能對以後要使用的朋友帶來一點協助。

首先先說一下什麼是WIF(Windows Identity Foundation)。由於各種曆史原因,身分識別驗證和標識的管理一般都比較無規律可循。在軟體裡加入“身分識別驗證”功能意味著要在你的代碼裡混進處理底層任務(如驗證使用者名稱和密碼,與X509認證或類似的認證打交道等)的代碼。這樣一來就得對基礎架構相當依賴,程式很難移植,除非大範圍重寫。要改變這種情況,使用宣告式身分識別(claims-based identity)可以很好的解決這個問題。這個“宣告式身分識別”是神馬東西我們留到以後再講,現在您只要知道有這麼個東西就行了。Windows
Identity Foundation(WIF)是微軟的基於宣告身份識別的協議棧。它是一個新的基礎技術,可以協助.NET開發人員利用基於聲明的方法來處理身分識別驗證,授權,定製化以及任何與標識相關的任務,而無需編寫任何底層代碼。

下面來說說WIF環境的搭建。在這裡我就走了不少冤枉路。我的悲催經曆就不跟大家分享了,直接介紹各種環境該如何搭建:

1、如果你已經安裝了VS2012,那麼WIF已經包含在了.Net Framework當中,而且版本為WIF4.5。但是注意,WIF4.5隻能用於.net 4.5的工程,如果你的asp.net或MVC項目是基於.net 4.5以下的話(即使你是在VS2012裡建立的工程),請繼續參考以下方法。

2、如果你安裝的是VS2010/VS2008,那麼你首先要先安裝WIF,然後安裝WIF SDK。

如果你用的是windows 8,那麼系統已經整合了Windows Identity Foundation 3.5了,只要開啟控制台->程式和功能->開啟或關閉Windows功能,找到 Windows
Identity Foundation 3.5
 ,將前面的勾勾上,然後點擊“確定”,完事兒以後點“關閉”即可,

 

這樣WIF 3.5就啟用成功了。

如果是其它作業系統,請點擊這裡,找到對應作業系統的exe檔案,下載安裝即可。

3、接下來安裝WIF的SDK,如果你用的是VS2012,那就不用裝任何SDK了,因為它都已經整合在.Net Framework 4.5裡了。但是你可能需要安裝一個VS的外掛程式。開啟VS2012,點擊工具->擴充和更新,在左邊列表裡點擊“聯機”,然後在右上方的搜尋方塊裡輸入"identity",點擊搜尋結果裡的“Identity
and Access Tool”,點擊下載按鈕,等待下載並安裝完成就可以了。這個工具可以讓你很快捷地為Web Application,MVC程式或者WCF服務增加一個本地開發STS(Local Development STS),來測試WIF的功能。這個工具的使用我們留到以後再講。

如果你用的不是VS2012,請點擊這裡進行下載並安裝相應的SDK。


至此,WIF所需的環境就已經搭建好了,下一步我們來通過一個小例子來說明WIF的工作原理。

這裡我用的環境是win7+vs2012,vs2010+WIF3.5/4.0的情況請參見這篇文章。


開啟VS2012,建立一個基於.net framework4.5的MVC4的工程,取名為WIFTutorial。如:


在彈出的“新ASP.NET MVC 4項目”對話方塊中直接點“確定”。

項目建立完畢後,在“方案總管”中,項目名稱上點右鍵,然後選擇“Identity and Accee...”,


在“Providers”頁簽裡選擇“Use the Local Development STS to test your application”。此時”Local Development STS"頁簽由不可用變為可用。切換到該頁簽,將Test claims to issue表格裡的第一行的Value列改為“ojlovecd”,

點擊“OK”,這個工具將會更改你的web.config檔案,我們在方案總管裡開啟web.config看看:

<?xml version="1.0" encoding="utf-8"?><!--  有關如何配置 ASP.NET 應用程式的詳細資料,請訪問http://go.microsoft.com/fwlink/?LinkId=169433  --><configuration>  <configSections>    <!-- For more information on Entity Framework configuration, visit http://go.microsoft.com/fwlink/?LinkID=237468 -->    <section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework, Version=5.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />    <section name="system.identityModel" type="System.IdentityModel.Configuration.SystemIdentityModelSection, System.IdentityModel, Version=4.0.0.0, Culture=neutral, PublicKeyToken=B77A5C561934E089" />    <section name="system.identityModel.services" type="System.IdentityModel.Services.Configuration.SystemIdentityModelServicesSection, System.IdentityModel.Services, Version=4.0.0.0, Culture=neutral, PublicKeyToken=B77A5C561934E089" />  </configSections>  <connectionStrings>    <add name="DefaultConnection" connectionString="Data Source=(LocalDb)\v11.0;Initial Catalog=aspnet-WIFTutorial-20130220231745;Integrated Security=SSPI;AttachDBFilename=|DataDirectory|\aspnet-WIFTutorial-20130220231745.mdf" providerName="System.Data.SqlClient" />  </connectionStrings>  <appSettings>    <add key="webpages:Version" value="2.0.0.0" />    <add key="webpages:Enabled" value="false" />    <add key="PreserveLoginUrl" value="true" />    <add key="ClientValidationEnabled" value="true" />    <add key="UnobtrusiveJavaScriptEnabled" value="true" />    <add key="ida:FederationMetadataLocation" value="http://localhost:14419/wsFederationSTS/FederationMetadata/2007-06/FederationMetadata.xml" />    <add key="ida:Issuer" value="http://localhost:14419/wsFederationSTS/Issue" />    <add key="ida:ProviderSelection" value="localSTS" />  </appSettings>  <location path="FederationMetadata">    <system.web>      <authorization>        <allow users="*" />      </authorization>    </system.web>  </location>  <system.web>    <authorization>      <deny users="?" />    </authorization>    <authentication mode="None" />    <compilation debug="true" targetFramework="4.5" />    <httpRuntime targetFramework="4.5" requestValidationMode="4.5" />    <!--Commented by Identity and Access VS Package-->    <!--<authentication mode="Forms"><forms loginUrl="~/Account/Login" timeout="2880" /></authentication>-->    <pages>      <namespaces>        <add namespace="System.Web.Helpers" />        <add namespace="System.Web.Mvc" />        <add namespace="System.Web.Mvc.Ajax" />        <add namespace="System.Web.Mvc.Html" />        <add namespace="System.Web.Optimization" />        <add namespace="System.Web.Routing" />        <add namespace="System.Web.WebPages" />      </namespaces>    </pages>  </system.web>  <system.webServer>    <validation validateIntegratedModeConfiguration="false" />    <handlers>      <remove name="ExtensionlessUrlHandler-ISAPI-4.0_32bit" />      <remove name="ExtensionlessUrlHandler-ISAPI-4.0_64bit" />      <remove name="ExtensionlessUrlHandler-Integrated-4.0" />      <add name="ExtensionlessUrlHandler-ISAPI-4.0_32bit" path="*." verb="GET,HEAD,POST,DEBUG,PUT,DELETE,PATCH,OPTIONS" modules="IsapiModule" scriptProcessor="%windir%\Microsoft.NET\Framework\v4.0.30319\aspnet_isapi.dll" preCondition="classicMode,runtimeVersionv4.0,bitness32" responseBufferLimit="0" />      <add name="ExtensionlessUrlHandler-ISAPI-4.0_64bit" path="*." verb="GET,HEAD,POST,DEBUG,PUT,DELETE,PATCH,OPTIONS" modules="IsapiModule" scriptProcessor="%windir%\Microsoft.NET\Framework64\v4.0.30319\aspnet_isapi.dll" preCondition="classicMode,runtimeVersionv4.0,bitness64" responseBufferLimit="0" />      <add name="ExtensionlessUrlHandler-Integrated-4.0" path="*." verb="GET,HEAD,POST,DEBUG,PUT,DELETE,PATCH,OPTIONS" type="System.Web.Handlers.TransferRequestHandler" preCondition="integratedMode,runtimeVersionv4.0" />    </handlers>    <modules>      <remove name="FormsAuthentication" />      <add name="WSFederationAuthenticationModule" type="System.IdentityModel.Services.WSFederationAuthenticationModule, System.IdentityModel.Services, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" preCondition="managedHandler" />      <add name="SessionAuthenticationModule" type="System.IdentityModel.Services.SessionAuthenticationModule, System.IdentityModel.Services, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" preCondition="managedHandler" />    </modules>  </system.webServer>  <runtime>    <assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">      <dependentAssembly>        <assemblyIdentity name="System.Web.Helpers" publicKeyToken="31bf3856ad364e35" />        <bindingRedirect oldVersion="1.0.0.0-2.0.0.0" newVersion="2.0.0.0" />      </dependentAssembly>      <dependentAssembly>        <assemblyIdentity name="System.Web.Mvc" publicKeyToken="31bf3856ad364e35" />        <bindingRedirect oldVersion="1.0.0.0-4.0.0.0" newVersion="4.0.0.0" />      </dependentAssembly>      <dependentAssembly>        <assemblyIdentity name="System.Web.WebPages" publicKeyToken="31bf3856ad364e35" />        <bindingRedirect oldVersion="1.0.0.0-2.0.0.0" newVersion="2.0.0.0" />      </dependentAssembly>    </assemblyBinding>  </runtime>  <entityFramework>    <defaultConnectionFactory type="System.Data.Entity.Infrastructure.LocalDbConnectionFactory, EntityFramework">      <parameters>        <parameter value="v11.0" />      </parameters>    </defaultConnectionFactory>  </entityFramework>  <system.identityModel>    <identityConfiguration>      <audienceUris>        <add value="http://localhost:8007/" />      </audienceUris>      <issuerNameRegistry type="System.IdentityModel.Tokens.ConfigurationBasedIssuerNameRegistry, System.IdentityModel, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">        <trustedIssuers>          <add thumbprint="9B74CB2F320F7AAFC156E1252270B1DC01EF40D0" name="LocalSTS" />        </trustedIssuers>      </issuerNameRegistry>      <certificateValidation certificateValidationMode="None" />    </identityConfiguration>  </system.identityModel>  <system.identityModel.services>    <federationConfiguration>      <cookieHandler requireSsl="false" />      <wsFederation passiveRedirectEnabled="true" issuer="http://localhost:14419/wsFederationSTS/Issue" realm="http://localhost:8007/" requireHttps="false" />    </federationConfiguration>  </system.identityModel.services></configuration>

其中標紅色的部分即為工具自動產生的。同時此工具還會在你的程式跟目錄下建立了一個名為FederationMetadata的目錄,通過在方案總管中點擊“顯示所有檔案”按鈕就可以看到了。

然後我們按F5,結果報錯了,

看提示,是因為要啟動LocalSTS必須要用管理員身份來運行。好吧,關掉VS,以管理員身份再次開啟,載入項目,再次按F5運行程式,此時看到右下角托盤處LocalSTS已經運行了,而開啟的首頁中,右上方顯示使用者ojlovecd已經處於登入狀態。

這一連串操作到底都幹了什嗎?

首先,剛才已經說到,Identity and Access Tool先修改了web.config,增加了WIF要用到的一些配置資訊,在程式啟動的時候,首先一併啟動LocalSTS,這個LocalSTS起什麼作用?由於web.config中配置了authorization節點,拒絕匿名使用者存取,因此在你的程式運行起來以後,對程式的請求資訊被重新導向到LocalSTS,向LocalSTS請求身份資訊,LocalSTS收到請求後,返回身份資訊。那麼返回的身份資訊怎麼來的?沒錯,就是在Identity and Access
Tool工具裡的第三個頁簽裡配置的。

至此,我們沒有編寫任何代碼,就已經實現了一個很簡單的身分識別驗證功能,關於此例子的詳細講解,以及我們要重點介紹的WIF原理及單點登入的實現,我們將留到下面的文章進行講解。

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.