[英]ASP.NET MVC Custom Errors
我的目標是在應用程序中創建一個處理所有托管錯誤的錯誤處理,而不僅僅是與MVC相關。 所以我沒有使用HandleErrorAttribute模式,因為它僅用於MVC錯誤,而不是其他托管錯誤。
在我的Global.asax中,我有:
protected void Application_Error()
{
string displayError = ConfigurationManager.AppSettings["DisplayError"];
NameValueCollection serverVariables;
int loop1, loop2;
StringBuilder serverVariableKeys = new StringBuilder();
Exception exception = Server.GetLastError();
HttpException httpException = exception as HttpException;
if (HttpContext.Current != null)
{
// loop through and get server vars
}
if (exception != null)
// Log Error
// Redirect to Error page if set to basic mode
if (!string.IsNullOrWhiteSpace(displayError) && displayError.ToLower() == "basic")
{
Response.Clear();
Server.ClearError(); // needed for redirect to work
var routeData = new RouteData();
routeData.Values["controller"] = "Error";
routeData.Values["action"] = "General";
routeData.Values["exception"] = exception;
Response.StatusCode = 500;
if (httpException != null)
{
Response.StatusCode = httpException.GetHttpCode();
switch (Response.StatusCode)
{
case 403:
routeData.Values["action"] = "Http403";
break;
case 404:
routeData.Values["action"] = "Http404";
break;
}
}
IController errorsController = new Controllers.ErrorController();
var rc = new RequestContext(new HttpContextWrapper(Context), routeData);
errorsController.Execute(rc);
}
}
我有一個ErrorController
,它有General
, Http403
和Http404
Actions。 我有與每個動作相對應的視圖。
在我的web.config中,我有:
<system.web>
<!-- removed bits to reduce space -->
<customErrors mode="On" />
</system.web>
<system.webServer>
<validation validateIntegratedModeConfiguration="false" />
<modules >
<remove name="UrlRoutingModule-4.0" />
<add name="UrlRoutingModule-4.0" type="System.Web.Routing.UrlRoutingModule" preCondition="" />
<remove name="Session"/>
<add name="Session" type="System.Web.SessionState.SessionStateModule" preCondition=""/>
</modules>
<handlers>
<remove name="ExtensionlessUrlHandler-Integrated-4.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>
<httpErrors errorMode="Detailed" />
</system.webServer>
這適用於與托管代碼相關的許多方案,但是當IIS接管時,例如錯誤的靜態文件調用(example.com/BadFileName.gif),它將從IIS返回錯誤,該錯誤揭示了服務器詳細信息,例如本地文件路徑。 這是因為web.config中的以下行:
<httpErrors errorMode="Detailed" />
但是當我將errorMode設置為其他值(如Custom)或只刪除該行時,我的自定義錯誤處理將停止運行,並且會返回包含托管代碼錯誤在內的所有內容的默認IIS錯誤消息。
我已經嘗試了很多東西來獲得自定義錯誤,沒有這個設置就沒有運氣,包括:
CustomError
設置為mode="Off"
customError
下定義Error節點以重定向到我的控制器 httpErrors
下定義Error節點以重定向到我的控制器 當我逐步調試時,我可以看到對控制器的調用,但最后IIS發送了響應。 錯誤日志記錄確實被正確調用Application_Error,因此代碼確實允許應用程序處理它到某一點。
申請細節:
有沒有辦法不使用<httpErrors errorMode="Detailed" />
並使其工作?
您看到該行為的原因可能是您正在調用Application_Error
處理程序(並調用您的控制器),但是IIS正在攔截500錯誤並顯示其自己的錯誤頁面。 (盡管你的Application_Error
處理程序本身也可能拋出一個Exception
,這是你要排除的東西)
因為您想要處理所有錯誤(例如您提到的靜態文件錯誤),您可能無法依賴ASP.NET或ASP.NET MVC為您執行初始錯誤檢測。 並非所有錯誤都來自您的應用程序!
最好的辦法是盡可能地依靠IIS 7.5的錯誤處理,而不是試圖過早介入。 讓IIS為您執行初始錯誤檢測,這樣更容易。
嘗試將以下內容放入web.config
,替換現有的httpErrors
節點: -
<httpErrors errorMode="Custom" existingResponse="Replace">
<clear />
<error statusCode="400" responseMode="ExecuteURL" path="/Error" />
<error statusCode="403" responseMode="ExecuteURL" path="/Error/Forbidden" />
<error statusCode="404" responseMode="ExecuteURL" path="/Error/NotFound" />
<error statusCode="500" responseMode="ExecuteURL" path="/Error" />
</httpErrors>
完全刪除customErrors
節點。 這是不必要的。
記住並確保您的錯誤控制器正在設置正確的狀態代碼: -
public ActionResult Forbidden()
{
Response.StatusCode = 403;
return this.View();
}
然后,除了注銷Application_Error
處理程序之外,您應該能夠拋棄所有內容 - 盡管我認為您最好創建自己的HttpModule
; 在web.config
的modules節點上設置runAllManagedModulesForAllRequests
可以幫助您捕獲否則會runAllManagedModulesForAllRequests
的錯誤。
我已經在Azure網站預覽版上運行了這個設置(雖然我個人使用elmah進行日志記錄),並且除了顯然因未能解析web.config
而導致的任何錯誤之外,它正在捕獲所有內容。
我在github上提供了一個完整的工作示例,使用httpErrors來自定義錯誤頁面 。 您也可以在天藍色的網站上看到它 。
如果你想在你的應用程序中處理這個,你可以編寫一個自定義處理程序或使用HandleError屬性這是一個很好的例子來解決這個問題,而不必使用IIS作為拐杖。 因為並非所有IIS主機提供商都允許在服務器級別進行此類自定義,並且IMO是一種不好的方法,因為它在部署時創建了額外的配置。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.