針對 ASP.NET 中的常見許可權和安全性相關問題進行疑難解答

本文介紹如何針對 ASP.NET 中的常見許可權和安全性相關問題進行疑難解答。

原始產品版本: ASP.NET
原始 KB 編號: 910449

實用的工具

在您嘗試修正任何已中斷的專案之前,您必須先熟悉一些工具,以協助您縮小問題的範圍。 在我們的案例中,我們會對 FileMon、RegMon 和安全性稽核等工具感興趣。 如需 FileMon 的詳細資訊,請參閱 適用於 Windows v7.04 的 FileMon

如需 RegMon 的詳細資訊,請參閱 Windows Sysinternals

向下切入以找出問題

  • 應用程式是否曾運作過? 如果是,那麼可能讓應用程式中斷的變更為何? 伺服器上可能已套用軟體更新或安全性更新。 程式代碼推出也可能造成問題。
  • 簡單的 .html 和.asp頁面是否可從 IIS 提供?
  • 應用程式是否已移轉至不同版本的 IIS?
  • 伺服器上的其他 ASP.NET 應用程式是否因為相同的錯誤而失敗? 這是唯一失敗的應用程式嗎?
  • 問題是否發生在所有使用者或僅適用於特定使用者?
  • 在網頁伺服器本機流覽時,問題是否可重現,或是僅供少數用戶端重現?
  • 如果您使用模擬,則模擬使用者是否具有資源的必要存取權?

上述問題有助於診斷問題。 如果您要在任何 ASP.NET 論壇張貼您的問題,而且如果您已經有大部分問題的解答,您可能會取得問題的快速指標或解決方案。 如果適用,關鍵在於張貼整個 ASP.NET 堆疊追蹤錯誤,而不是說「我在嘗試執行 ASP.NET 應用程式時收到拒絕存取錯誤。 任何人都可以提供協助嗎?」當某人看到完整的錯誤訊息時,可以更輕鬆地查看堆疊追蹤並提供指標。 所以您需要詢問自己...

確切的錯誤訊息為何?

我們詢問客戶的第一個問題是:「確切的錯誤訊息為何?」如果您有 Microsoft .NET Framework 所擲回之錯誤訊息的清楚描述,您可以略過本節。 如果您的應用程式會遮罩實際的錯誤訊息,並改為提供易記的錯誤訊息,例如「發生非預期的錯誤。 如需詳細資訊,請連絡網站管理員。「對任何人都沒有多大用用。 以下是一些步驟,可協助您取得實際的錯誤訊息。

  • 找出並開啟應用程式目錄中的 Web.config 檔案,並將 customErrors 變更為mode=“Off”。 儲存盤案,然後重現問題。

  • 在遵循上述步驟之後,可能仍然無法看到實際的錯誤訊息,因為應用程式開發人員已完成自定義事件/錯誤處理。 您可以嘗試在 Global.asax 檔案中找出Application_Error事件,並將使用 Server.Transfer("Errors.aspx") 函式的任何程式代碼批注化為移至自定義錯誤頁面。

    //Global.asax 
    void Application_Error(object sender, EventArgs e) 
    { 
        // Code that runs when an unhandled error occurs 
        //Server.Transfer("Errors.aspx"); 
    }
    

一旦您收到實際的錯誤訊息,請讀取該訊息,以判斷錯誤是因為遺失本機資源或您 ASP.NET 應用程式嘗試存取之遠端資源的許可權所造成。

提示

您可以連絡開發人員以瞭解如何查看實際的錯誤訊息。 您的開發人員可能會將它記錄到檔案或取得電子郵件通知。 請務必記得備份您要變更的任何檔案。 有了可用的備份,您一律可以復原任何變更。

發生此問題的原因,是因為 ASP.NET 應用程式嘗試存取的本機資源上缺少許可權

如果您因為自定義錯誤訊息而無法取得問題的清楚描述,請執行 FileMon 並重現問題。 將擷取停止並儲存為 FileMon.xls,然後在 Microsoft Excel 中開啟檔案。 在 [ 數據] 功能表上,按下 [ 篩選],然後按下 [自動篩選 ] 以使用Excel的篩選功能。 現在選取資料行中的 F 下拉式清單,並尋找「拒絕存取」錯誤。

範例 FileMon 輸出如下所示。

10381 1:01:11 PM w3wp.exe:2320 OPEN C:\winnt\microsoft.net\framework\v1.1.4322\Temporary ASP.NET Files\sessiontest\8832e585\275ec327\global.asax.xml 
ACCESS DENIED NT 
AUTHORITY\NETWORK SERVICE

如您從篩選的結果中所見,我們已縮小問題原因的範圍。 FileMon 顯示 NT AUTHORITY\NETWORK SERVICE 帳戶遺失資料夾的 C:\Winnt\Microsoft.net\Framework\v1.1.4322\Temporary ASP.NET Files NTFS 許可權。 這應該要直接修正。

提示

一個不錯的步驟是將 ASP.NET 進程帳戶變更為 管理員 帳戶,以查看其是否已修正問題。 在 IIS 6.0 和更新版本中,您會將 IIS AppPool 身分識別變更為「本機系統」,以查看應用程式是否可運作。

注意事項

這不應該作為解決方案,而只能作為疑難解答步驟。

大部分的人通常會重新安裝 Microsoft .NET Framework,或甚至重新安裝作業系統。 這不是建議的疑難解答步驟,也不保證問題不會重複發生。 我會提供一個這類範例。 間歇性問題通常很難隔離和疑難解答。 在此案例中,客戶的應用程式會正常運作數小時,然後會突然失敗,並出現下列錯誤。 客戶已嘗試重新安裝 .NET Framework和操作系統。 這似乎要修正問題數天,但接著會重新出現。

執行 FileMon 未顯示任何 拒絕存取 錯誤。 ASPNET 帳戶的所有必要許可權都已就緒。 從問題復原的唯一方法是重新啟動方塊。 即使是 IIS 重設也沒有任何説明。 您想「好,Microsoft 軟體一律需要重新啟動才能復原?」你錯了!

這裡的重點是仔細查看錯誤訊息。 此錯誤清楚顯示「無法開啟檔案以供寫入」,而不是一般的 拒絕存取 錯誤,因此我想這是一些其他程式,會鎖定檔案或資料夾,而不允許 ASP.NET 寫入檔案。 重新啟動會終止另一個進程,而 ASP.NET 應用程式會再次開始運作,直到 Rogue 進程再次鎖定檔案為止。 要做的邏輯是關閉所有防病毒軟體程式、第三方間諜軟體,或伺服器上執行的任何其他檔案監視軟體。 我不想指出任何特定的第三方軟體。 但是,一般而言,防病毒軟體已知會對 IIS 和 ASP.NET 應用程式造成許多災難。 防病毒軟體造成的另一個已知問題是當觸碰 Bin 資料夾或 .config 檔案時,因為 AppDomain 回收而導致會話遺失。

提示

關閉第三方服務最簡單的方式是:

  1. 按兩下 [開始],按兩下 [ 執行],然後輸入 msconfig
  2. 取 [服務 ],然後核 取 [隱藏所有 Microsoft 服務]
  3. 按兩下 [全部停用] 以停止第三方服務。
  4. 按兩下 [開始],按兩下 [ 執行],然後輸入 iisreset 將 CLR 重載背景工作進程。

監視您的應用程式,以查看問題是否重複發生。 如果您執行多個防病毒程式,請使用試用和錯誤方法來判斷哪一個特定程式造成問題。

注意事項

如果相同的錯誤可在 100% 的時間內重現,您的防病毒軟體可能不是原因。 此錯誤可能還有其他原因。 請嘗試建立簡單的 ASP.NET 測試應用程式,以隔離Test.aspx頁面是否發生相同的錯誤。 如果是,請確認必要的 存取控制 清單 (ACL) 全都已就緒,以供 ASP.NET 使用。

參閱 ASP.NET 必要 存取控制 清單 (ACL)

提示

%SystemRoot%\Assembly 夾是全域程式集緩存。 您無法直接使用 Windows 檔案總管來編輯此資料夾的 ACL。

請改用命令提示字元並執行下列命令:

cacls %windir%\assembly /e /t /p domain\useraccount:r

或者,在使用 Windows 檔案總管之前,請使用下列命令取消註冊 Shfusion.dll,以透過 GUI 授與許可權:

C:\WINDOWS\Microsoft.NET\Framework\VersionNumber>regsvr32-u shfusion.dll

使用 Windows 檔案總管設定權限之後,請使用下列命令重新註冊 Shfusion.dll:

C:\WINDOWS\Microsoft.NET\Framework\VersionNumber>regsvr32 shfusion.dll

發生問題的原因是 ASP.NET 應用程式嘗試存取的遠端資源許可權遺失

當您的 ASP.NET 應用程式存取遠端資源,例如 Microsoft SQL Server 或通用命名約定 (UNC) 共用時,可能會發生許多錯誤。 此外,遠端資源上的許多專案可能設定不正確。 您必須針對這些問題進行疑難解答,才能讓資源正常運作。

您的第一個步驟是查看您是否可以透過 Windows 檔案總管連線到遠端伺服器。

  1. 在遠端伺服器上,建立名為Test的資料夾。 在 [測試] 資料夾的 [共用與安全性] 索引標籤上,新增您的網域/帳戶,以及 ASP.NET 應用程式所使用的進程帳戶,並同時提供這兩個完全控制權。

  2. 在 IIS 伺服器上,使用您的網域/帳戶登入,按兩下 [ 開始],按兩下 [ 執行],然後輸入遠端伺服器的 UNC 共用路徑: \\RemoteServerName*\Test

    如果您無法前往此資料夾,請連絡您的網路管理員以修正此問題。 只有這樣,您的 ASP.NET 應用程式才能存取共用。

  3. 使用下列程式代碼 建立名為 CreateUNCFile.aspx 的檔案,並將檔案儲存在應用程式目錄中。

    <%@ Page Language="vb" %>
    <%@ Import Namespace="System.IO" %>
    <html>
    <head>
    <title>Writing to a Text File</title>
    <script runat="server">
        Sub WriteToFile(ByVal sender As System.Object, ByVal e As System.EventArgs)
            Dim fp As StreamWriter
                fp = File.CreateText("\\<RemoteServerName>\Test\" & "test.txt")
                fp.WriteLine(txtMyFile.Text)
                lblStatus.Text = "The File Successfully created! Your ASP.NET process is able to access this remote share"
                fp.Close()
        End Sub
    </script>
    
    </head>
    <body style="font: 10pt verdana">
                <h3 align="center">Creating a Text File in ASP.NET</h3>
        <form id="Form1" method="post" runat="server">
                            Type your text:
                            <asp:TextBox ID="txtMyFile" TextMode="MultiLine" Rows="10" Columns="60" Runat="server" /><br>
                            <asp:button ID="btnSubmit" Text="Create File" OnClick="WriteToFile" Runat="server" />
                            <asp:Label ID="lblStatus" Font-Bold="True" ForeColor="#ff0000" Runat="server" />
        </form>
    </body>
    </html> 
    
  4. 請確定您在下列程式代碼行中修改 <RemoteServerName>

    fp = File.CreateText("\\<RemoteServerName>\Test\" &"test.txt")
    

    因此,它會反映遠端伺服器的名稱。

  5. 開啟 Windows Internet Explorer,然後從 IIS 伺服器以外的用戶端電腦瀏覽至 http://**IISServerName**/**AppName**/CreateUNCFile.aspx

  6. 如果 Test.txt 檔案成功建立,則您的 ASP.NET 應用程式可以向遠端資源進行驗證。

  7. 如果因特網總管用戶端瀏覽器的檔案建立失敗,但如果您從 IIS 伺服器本身流覽至相同的頁面,則可能是您遇到「雙躍點」案例。 如果您使用自定義建置的網頁元件來存取需要使用者驗證和授權的遠端資源,您可能會遇到「雙躍點」問題。 若要存取遠端資源,您可能需要提供使用者的認證給資源,讓資源的輸出僅限於使用者有權存取的數據。

上述步驟假設您已在 IIS 中開啟 NTLM 驗證。 基本身份驗證不會使用 Kerberos。

如需詳細資訊,請參閱 針對 Internet Explorer 中的 Kerberos 失敗進行疑難解答

如需 IIS 驗證方法的詳細資訊,請參閱 Visual Studio 2003 已淘汰技術檔

提示

如果您可以連線到遠端 UNC 共用,但無法從 ASP.NET 應用程式連線到執行 SQL Server 的遠端伺服器,則您可能必須檢查或設定 SPN (SPN) SQL Server 的服務主體名稱。 嘗試只在 IIS 中為您的應用程式啟用基本身份驗證,並查看您是否能夠連線到執行 SQL Server 的遠端伺服器。

「伺服器應用程式無法使用」錯誤訊息還有其他許多原因。 事件記錄檔是您的最佳選擇,可取得問題原因的更多詳細數據。

IIS 記錄在發生 IIS 驗證相關錯誤時很有用。

您需要尋找的是此特定錯誤的狀態和子狀態代碼。

2006-10-12 22:47:28 W3SVC1 65.52.18.230 GET /MyAPP/login.aspx - 80  
MyDomain\UserID_91 65.52.22.58 Mozilla/4.0+  
(compatible;+MSIE+6.0;+Windows+NT+5.2;+SV1;+.NET+CLR+1.1.4322;+.NET+CLR+2.0.50727;+InfoPath.1) 401 3 5

我們看到子狀態為 3 的 401,指出「因資源上的 ACL 而未經授權」。

這表示遺失檔案或資料夾的NTFS許可權。 即使您嘗試存取的檔案許可權正確,但其他 SYSTEM 和 IIS 資料夾上可能缺少預設許可權和使用者權力,還是可能會發生此錯誤。 例如,如果IUSR_ComputerName帳戶無法存取 C:\Winnt\System32\Inetsrv 目錄,您可能會看到此錯誤。

提示

單擊 [開始],按兩下 [ 執行],然後輸入logfiles以開啟包含 IIS 記錄檔的資料夾。 或者,在 IIS 中網站的 [屬性] 頁面上,按兩下 [WebSiteName] 索引 標籤,然後在 [ 使用中記錄格式] 下,按兩下 [ 屬性 ] 以查看記錄檔目錄和名稱。

這裡另一個感興趣的事項是狀態代碼 5。 您可以使用 net helpmsg 命令來取得此狀態代碼的詳細資訊:

C:\Documents and Settings\User> net helpmsg 5

拒絕存取。

讓我們試試另一個常見的狀態代碼,代碼 50:

C:\Documents and Settings\User> net helpmsg 50

不支援要求。

提示

每當您收到另一個泛型的「500 內部伺服器錯誤」訊息時,最好停用易記的 HTTP 錯誤訊息,讓您收到錯誤的詳細描述。 別忘了查看事件查看器,因為它可能也包含更多資訊。

其概念是使用所有可用的記錄資訊,以取得有關手端問題的最大詳細數據。

資源

如需詳細資訊,請參閱: