|
現(xiàn)在網(wǎng)絡(luò)上的身份驗證一般都是采用用戶名+口令的形式,幾乎每到一個提供服務(wù)的網(wǎng)站都要求進(jìn)行驗證登錄。隨著網(wǎng)絡(luò)身份的增多,這也會造成用戶名與口令記憶上的負(fù)擔(dān),另外多次的輸入也存在安全隱患(輸多了,被盜的機會也多)。單點登錄就是為了解決這些問題而產(chǎn)生的,它指的是在一個地方登錄就可以到處通行。 (哇靠,發(fā)現(xiàn)自己老了幾歲,另起一段,講點實際的)。 我們公司有幾個網(wǎng)站需要維護(hù),每個站點都具有一個登錄口,我們發(fā)現(xiàn)這樣很不方便,所以第一步就是統(tǒng)一這些登錄口。雖然所有的源代碼都可以控制,我們可以把所有站點改成一個站點,這樣就不存在這個問題了,只是這樣不符合要求,所以當(dāng)時(幾前天)只能另想辦法。 我們找到了微軟的Passport,發(fā)現(xiàn)有點麻煩,要申請Web服務(wù)(也許并不麻煩,因為沒有用過,新技術(shù)總讓人感覺神秘嘛),就決定不用它,就幾點站點,不想勞師動眾。后來同事(我的經(jīng)理)找到了一篇相關(guān)的文章,在ASP.NET下,只要在Web.config下配置machineKey節(jié),可以解決這個問題(我是指我們公司的這個問題)。 在.NET Framework SDK文檔中,ASP.NET設(shè)置架構(gòu)篇中,可以找到machineKey的相關(guān)內(nèi)容: 對密鑰進(jìn)行配置,以便將其用于對 Forms 身份驗證 Cookie 數(shù)據(jù)和視圖狀態(tài)數(shù)據(jù)進(jìn)行加密和解密,并將其用于對進(jìn)程外會話狀態(tài)標(biāo)識進(jìn)行驗證。該節(jié)可在計算機、站點和應(yīng)用程序級別聲明,但不在子目錄級別聲明。 <configuration> <system.web> <machineKey> <machineKey validationKey='...' decryptionKey='...' validation='' /> 我們知道Http是無連接協(xié)議, 而Cookie可以標(biāo)識特定站點的用戶信息, ASP.NET在默認(rèn)情況下也一樣, 即使是Session在默認(rèn)情況下也是基于Cookie的, 所以如果一個站點的Cookie能被另一個站點識別,不就可以... 正常情況下, ASP.NET的Forms驗證一般是這樣做的, 受保護(hù)頁面根據(jù)權(quán)限分組放進(jìn)不同的文件夾中, 然后在各自文件夾的web.config中對這些文件進(jìn)行訪問保護(hù). 例如管理員訪問的各個頁面, 我一般會放進(jìn)一個 Admin 目錄中, 然后在Admin目錄下的Web.config中的 <authorization> 節(jié)中配置它的訪問權(quán)限,像下面這樣: <configuration> <system.web> <authorization> <deny users="?" /> <!--不允許匿名用戶訪問--> ... 如果某用戶不幸訪問了這些頁面應(yīng)該讓頁面重定向到Login.aspx中, 這需要在根目錄的Web.confg中進(jìn)行一些配置, 最簡單的情況應(yīng)該像下面這樣: <configuration> <system.web> <authentication mode="Forms"> <forms loginUrl="~/login.aspx" /> </authentication 題外話: 如果要對站點的圖片進(jìn)行訪問控制,也可以像上面這么做, 因為許多站點并不想讓其它用戶僅僅知道地址就可以直接訪問圖片信息. 但是這樣還不夠, 需要在IIS中配置一下對圖片資源的接管, 就像.aspx是由aspnet_isapi.dll處理的, 你應(yīng)該讓圖片也經(jīng)由它手. 下面就可以進(jìn)行用戶名/密碼驗證了. if (用戶名/密碼驗證通過) { System.Web.Security.FormsAuthentication.RedirectFromLoginPage(".LOGINAUTH1", false); } 這樣,如果你首先訪問了受保護(hù)頁面, 它將會重定向到登錄頁面中, 而你在這里登錄后, 它將自動重定向到先前的受保護(hù)頁面. 如果一開始你訪問的就是登錄頁面, 那么登錄后, 默認(rèn)情況下, 它會將頁面重定向到 default.aspx . 以上講這么多登錄的東東, 但是原本是講單點登錄的, 其實我并沒有離題, 只是如果你到了這一步, 那么只需要在兩個,或多個站點的WebConfig中配置一下 machineKey 就可以讓其共享Cookie, 在一個站點中登錄, 也就相當(dāng)于在另一個站點中登錄, 退出也一樣. machineKey配置節(jié)文檔如下: <machineKey validationKey="AutoGenerate|value[,IsolateApps]" decryptionKey="AutoGenerate|value[,IsolateApps]" validation="SHA1|MD5|3DES" /> 其中 validationKey 是 用于驗證加密數(shù)據(jù)的密鑰, 手動配置時, 推薦用128個十六進(jìn)制字符 decryptionKey 是 用于加密數(shù)據(jù)的密鑰, 這個的長度和加密類型(也就是第三個參數(shù)) 相關(guān), 比如選 3DES 則這里是 48 個16進(jìn)制字符 validation 是 數(shù)據(jù)驗證使用的加密類型 OK, 寫配置節(jié)前,我們還需要兩個長長的十六進(jìn)制串呢, 當(dāng)我用鍵盤敲了10幾下后, 發(fā)現(xiàn)自己是笨蛋, 應(yīng)該讓腳本幫助生成的, 否則即不隨機, 又慢, 而且長度還可能搞錯. 如果你也用Python, 那么可以用以下語句得到128位十六進(jìn)制串, 呵呵 相當(dāng)?shù)暮唵魏头奖? import random s = '' for i in range(128): s += '%X' %(random.randint(0, 15)) else: print s 配置節(jié)信息, 像下面這樣(難看死了:() <machineKey validationKey="F65E3D075FFCE2AC48F6B0ABB73BA4FAC05E7F10BB E765520EA75F4E210126F01A62BE39B1059857 A10A54FE210A14E7FD685A1040E8033202107424AFE2B443" decryptionKey="C5475E1B28958DC6373DAA37C5B92CCDD94ECDF02D7A6A66" validation="3DES" /> 你需要在兩個或多個站點上都具有相同的machineKey配置信息, 才能產(chǎn)生效果. 哦, 對了, 其實這種方法只能解決幾個站點的登錄問題, 但不能代替passport,, 想想全世界的站點配置成一樣(哦, 當(dāng)我沒說過) 我沒用過passport, 但看了看一些相關(guān)文獻(xiàn), 知道大概怎么回事. 就是讓登錄(專業(yè)一點說是身份驗證)由專門的人(一個機構(gòu), 如passport)去做, 而普通站點只做服務(wù)就行了. 這樣訪問相當(dāng)于以下流程: 1. 訪問一站點(服務(wù)站點)的頁面, 2. 服務(wù)站點去驗證站點上問問, 該用戶有沒有已登錄 3. 如果已登錄了, 那么正常服務(wù), 流程結(jié)束 4. 如果沒有登錄, 那么把該用戶重定向到驗證站點. 5. 用戶在驗證站點上驗證登錄, 一般也是輸入用戶名和密碼驗證 6. 驗證站點將驗證通過的用戶重定向到先前的服務(wù)頁面 請原諒, 英語不好, 看了一篇長長的東東, 就理出這點東西 其實這中間有很多技術(shù)的細(xì)節(jié)要處理, 數(shù)據(jù)的驗證, 以及傳遞過程一定很復(fù)雜. 文中說, Passport 是采用Kerberos 認(rèn)證機制來工作的(不要問我這是什么, 我也不知道). 哦,對了, 除了passport 還有一個 Liberty Alliance 組織也有個單點登錄. 有空我會去再看看的. |
|
|