2011年10月10日 星期一

ASP.NET MVC + ELMAH 監控並記錄你的網站錯誤資訊 2

上一篇文章「ASP.NET MVC + ELMAH 監控並記錄你的網站錯誤資訊 1」有遇到一個問題,那就是原先ELMAH所預設的設定會讓任何人都可以看到ELMAH記錄,對於網路的安全性就有極大的危險,因為錯誤記錄都記錄了許多的資訊,除了客戶資訊外也包含了Server的環境資訊,甚至於錯誤的程式碼位置'、輸入的機密資料等,怎麼可以讓任何人說進來就進來呢?

所以有些安全性的設定還是要記得去修改、去設定,免得讓有心人竊取資料或是毀損資料。

 


一般來說,ELMAH要去增加安全設定,不讓任何閒雜人等擅闖,就要修改Web.Config的設定,如下:

  <elmah>
    <errorLog type="Elmah.XmlFileErrorLog, Elmah" logPath="~/App_Data/Elmah.Errors" />
  <security allowRemoteAccess="yes" />
  </elmah>
  <location path="elmah.axd">
    <system.web>
      <authorization>
        <allow roles="Admin"/>
        <deny users="*"/>
      </authorization>
    </system.web>
  </location>

但是ELMAH.MVC就不需要,因為已經把權限設定的地方改在Controller中,使用AuthorizeAttribute,

image

預設的程式中,是預設把Controller上的AuthorizeAttribute給註解起來,

image

而我們只要把這個這解給移除就可以,

image

這時候要是我們直接進入~/Admin/Elmah的話,就會被導到登入頁面

image

不過這也要你事先把登入頁面(AccountController / LogOn)給做好,另外在Web.Config有設定(預設都會設定)

    <authentication mode="Forms">
      <forms loginUrl="~/Account/LogOn" timeout="2880" />
    </authentication>

 

這邊我是透過Forms Authentication來處理登入的權限認證,在Global.asax中增加Application_AuthenticateRequest()方法

    /// <summary>
    /// Handles the AuthenticateRequest event of the Application control.
    /// </summary>
    /// <param name="sender">The source of the event.</param>
    /// <param name="e">The <see cref="System.EventArgs"/> instance containing the event data.</param>
    protected void Application_AuthenticateRequest(Object sender, EventArgs e)
    {
      bool hasUser = HttpContext.Current.User != null;
      bool isAuthenticated = hasUser && HttpContext.Current.User.Identity.IsAuthenticated;
      bool isIdentity = isAuthenticated && HttpContext.Current.User.Identity is FormsIdentity;
      if (isIdentity)
      {
        // 取得表單認證目前這位使用者的身份
        FormsIdentity id = (FormsIdentity)HttpContext.Current.User.Identity;
        // 取得 FormsAuthenticationTicket 物件
        FormsAuthenticationTicket ticket = id.Ticket;
        // 取得 UserData 欄位資料 (這裡我們儲存的是角色)
        string userData = ticket.UserData;
        // 如果有多個角色可以用逗號分隔
        string[] roles = userData.Split(',');
        // 賦予該使用者新的身份 (含角色資訊)
        HttpContext.Current.User = new GenericPrincipal(id, roles);
      }
    }

而至於Forms Authentication的運作與登入機制的實作,可以在網路上找一下,這邊就不另做說明,

可以參考一下以下幾篇文章:

http://weblogs.asp.net/fredriknormen/archive/2008/02/07/asp-net-mvc-framework-using-forms-authentication.aspx

Demo - ASP.NET MVC 實做登入機制

Demo - ASP.NET MVC 無法正常登出的解決方式

 

好的,當網站的登入機制完成後,要看ELMAH記錄就可以藉由登入完成後得以瀏覽了。

不過呢……因為ELMAH.MVC預設在ASP.NET MVC網站裡是去建立一個Area,預設名稱是「Admin」,但是這個名稱太好猜了,先不論有心者要怎麼去猜目錄名稱以及怎麼猜網站有沒有用Elmah,總之「Admin」這個名稱太容易被猜中了,所以咧~最好的方式就是改個名稱,以降低被猜中的機率。

例如,我把原本的「Admin」改為「ErrorAdmin」,

image

如果還是從原來的「~/Admin/Elmah」進入的話,就會給你一個404錯誤頁面,

image

而如果從已經更改的「~/ErrorAdmin/Elmah」進入的話,就可以導到登入頁面或是進入到Elmah頁面,

image

 

總之,防人之心不可無,甚至我是認為我都不太想讓客戶知道怎麼進去看Elmah記錄,除了安全性問題外,最要緊的是,不太想要讓客戶看到Elmah記錄中一堆的錯誤記錄,以免被認為程式中有一堆的BUG,大家也知道,客戶……如果知道分辨什麼是錯誤、什麼是BUG、什麼是例外的話,那就不是客戶了…

 

延伸閱讀:

Demo - 如何偵錯--ELMAH 絕妙的偵錯工具安全架設於ASP.NET MVC

黑暗執行绪 - ASP.NET保安系列 - 關於elmah.axd的安全設定

Pete.NET - 好用的error logging framework - ELMAH

RiCo技術農場 - [C#][ASP.NET MVC]ELMAH On IIS7.5

 

以上

2 則留言:

提醒

千萬不要使用 Google Talk (Hangouts) 或 Facebook 及時通訊與我聯繫、提問,因為會掉訊息甚至我是過了好幾天之後才發現到你曾經傳給我訊息過,請多多使用「詢問與建議」(在左邊,就在左邊),另外比較深入的問題討論,或是有牽涉到你實作程式碼的內容,不適合在留言板裡留言討論,請務必使用「詢問與建議」功能(可以夾帶檔案),謝謝。