asp.net-mvc - page - examen mvc
ASP.NET MVC HandleError (6)
¿Cómo hago para obtener el filtro [HandleError]
en asp.net MVC Preview 5?
Configuro los customErrors en mi archivo Web.config
<customErrors mode="On" defaultRedirect="Error.aspx">
<error statusCode="403" redirect="NoAccess.htm"/>
<error statusCode="404" redirect="FileNotFound.htm"/>
</customErrors>
y coloque [HandleError] encima de mi clase de controlador de esta manera:
[HandleError]
public class DSWebsiteController: Controller
{
[snip]
public ActionResult CrashTest()
{
throw new Exception("Oh Noes!");
}
}
Luego dejo que mis controladores hereden de esta clase y llamo a CrashTest () sobre ellos. Visual Studio se detiene ante el error y después de presionar f5 para continuar, me redirigen a Error.aspx? Aspxerrorpath = / sxi.mvc / CrashTest (donde sxi es el nombre del controlador utilizado. Por supuesto, no se puede encontrar la ruta y obtengo "Error del servidor en ''/'' Aplicación." 404.
Este sitio fue portado desde la vista previa 3 a 5. Todo se ejecuta (no fue mucho trabajo portar) excepto el manejo de errores. Cuando creo un nuevo proyecto completo, el manejo de errores parece funcionar.
Ideas?
--Nota--
Dado que esta pregunta tiene más de 3,000 visitas ahora, pensé que sería beneficioso usar lo que estoy usando actualmente (ASP.NET MVC 1.0). En el proyecto mvc contrib hay un atributo brillante llamado "RescueAttribute" Probablemente también deberías verificarlo;)
Los atributos en MVC son muy útiles en el manejo de errores en los métodos get y post , también rastrean la llamada ajax .
Crea un controlador base en tu aplicación y heredadlo en tu controlador principal (EmployeeController).
public employee EmployeeController: BaseController
Agregue el código siguiente en el controlador base.
/// <summary>
/// Base Controller
/// </summary>
public class BaseController : Controller
{
protected override void OnException(ExceptionContext filterContext)
{
Exception ex = filterContext.Exception;
//Save error log in file
if (ConfigurationManager.AppSettings["SaveErrorLog"].ToString().Trim().ToUpper() == "TRUE")
{
SaveErrorLog(ex, filterContext);
}
// if the request is AJAX return JSON else view.
if (IsAjax(filterContext))
{
//Because its a exception raised after ajax invocation
//Lets return Json
filterContext.Result = new JsonResult()
{
Data = Convert.ToString(filterContext.Exception),
JsonRequestBehavior = JsonRequestBehavior.AllowGet
};
}
else
{
filterContext.ExceptionHandled = true;
filterContext.HttpContext.Response.Clear();
filterContext.Result = new ViewResult()
{
//Error page to load
ViewName = "Error",
ViewData = new ViewDataDictionary()
};
base.OnException(filterContext);
}
}
/// <summary>
/// Determines whether the specified filter context is ajax.
/// </summary>
/// <param name="filterContext">The filter context.</param>
private bool IsAjax(ExceptionContext filterContext)
{
return filterContext.HttpContext.Request.Headers["X-Requested-With"] == "XMLHttpRequest";
}
/// <summary>
/// Saves the error log.
/// </summary>
/// <param name="ex">The ex.</param>
/// <param name="filterContext">The filter context.</param>
void SaveErrorLog(Exception ex, ExceptionContext filterContext)
{
string logMessage = ex.ToString();
string logDirectory = Server.MapPath(Url.Content("~/ErrorLog/"));
DateTime currentDateTime = DateTime.Now;
string currentDateTimeString = currentDateTime.ToString();
CheckCreateLogDirectory(logDirectory);
string logLine = BuildLogLine(currentDateTime, logMessage, filterContext);
logDirectory = (logDirectory + "//Log_" + LogFileName(DateTime.Now) + ".txt");
StreamWriter streamWriter = null;
try
{
streamWriter = new StreamWriter(logDirectory, true);
streamWriter.WriteLine(logLine);
}
catch
{
}
finally
{
if (streamWriter != null)
{
streamWriter.Close();
}
}
}
/// <summary>
/// Checks the create log directory.
/// </summary>
/// <param name="logPath">The log path.</param>
bool CheckCreateLogDirectory(string logPath)
{
bool loggingDirectoryExists = false;
DirectoryInfo directoryInfo = new DirectoryInfo(logPath);
if (directoryInfo.Exists)
{
loggingDirectoryExists = true;
}
else
{
try
{
Directory.CreateDirectory(logPath);
loggingDirectoryExists = true;
}
catch
{
}
}
return loggingDirectoryExists;
}
/// <summary>
/// Builds the log line.
/// </summary>
/// <param name="currentDateTime">The current date time.</param>
/// <param name="logMessage">The log message.</param>
/// <param name="filterContext">The filter context.</param>
string BuildLogLine(DateTime currentDateTime, string logMessage, ExceptionContext filterContext)
{
string controllerName = filterContext.RouteData.Values["Controller"].ToString();
string actionName = filterContext.RouteData.Values["Action"].ToString();
RouteValueDictionary paramList = ((System.Web.Routing.Route)(filterContext.RouteData.Route)).Defaults;
if (paramList != null)
{
paramList.Remove("Controller");
paramList.Remove("Action");
}
StringBuilder loglineStringBuilder = new StringBuilder();
loglineStringBuilder.Append("Log Time : ");
loglineStringBuilder.Append(LogFileEntryDateTime(currentDateTime));
loglineStringBuilder.Append(System.Environment.NewLine);
loglineStringBuilder.Append("Username : ");
loglineStringBuilder.Append(Session["LogedInUserName"]);
loglineStringBuilder.Append(System.Environment.NewLine);
loglineStringBuilder.Append("ControllerName : ");
loglineStringBuilder.Append(controllerName);
loglineStringBuilder.Append(System.Environment.NewLine);
loglineStringBuilder.Append("ActionName : ");
loglineStringBuilder.Append(actionName);
loglineStringBuilder.Append(System.Environment.NewLine);
loglineStringBuilder.Append("----------------------------------------------------------------------------------------------------------");
loglineStringBuilder.Append(System.Environment.NewLine);
loglineStringBuilder.Append(logMessage);
loglineStringBuilder.Append(System.Environment.NewLine);
loglineStringBuilder.Append("==========================================================================================================");
return loglineStringBuilder.ToString();
}
/// <summary>
/// Logs the file entry date time.
/// </summary>
/// <param name="currentDateTime">The current date time.</param>
string LogFileEntryDateTime(DateTime currentDateTime)
{
return currentDateTime.ToString("dd-MMM-yyyy HH:mm:ss");
}
/// <summary>
/// Logs the name of the file.
/// </summary>
/// <param name="currentDateTime">The current date time.</param>
string LogFileName(DateTime currentDateTime)
{
return currentDateTime.ToString("dd_MMM_yyyy");
}
}
=============================================
Encuentra el directorio: Root / App_Start / FilterConfig.cs
Agregue el siguiente código:
/// <summary>
/// Filter Config
/// </summary>
public class FilterConfig
{
/// <summary>
/// Registers the global filters.
/// </summary>
/// <param name="filters">The filters.</param>
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
filters.Add(new HandleErrorAttribute());
}
}
Seguir el error AJAX:
Llame a CheckAJAXError función en la carga de la página de diseño.
function CheckAJAXError() {
$(document).ajaxError(function (event, jqXHR, ajaxSettings, thrownError) {
var ex;
if (String(thrownError).toUpperCase() == "LOGIN") {
var url = ''@Url.Action("Login", "Login")'';
window.location = url;
}
else if (String(jqXHR.responseText).toUpperCase().indexOf("THE DELETE STATEMENT CONFLICTED WITH THE REFERENCE CONSTRAINT") >= 0) {
toastr.error(''ReferanceExistMessage'');
}
else if (String(thrownError).toUpperCase() == "INTERNAL SERVER ERROR") {
ex = ajaxSettings.url;
//var url = ''@Url.Action("ErrorLog", "Home")?exurl='' + ex;
var url = ''@Url.Action("ErrorLog", "Home")'';
window.location = url;
}
});
};
Solución para código de error http a 500 esto es un atributo llamado [ERROR] ponerlo en una acción
public class Error: System.Web.Mvc.HandleErrorAttribute
{
public override void OnException(System.Web.Mvc.ExceptionContext filterContext)
{
if (filterContext.HttpContext.IsCustomErrorEnabled)
{
filterContext.ExceptionHandled = true;
}
base.OnException(filterContext);
//OVERRIDE THE 500 ERROR
filterContext.HttpContext.Response.StatusCode = 200;
}
private static void RaiseErrorSignal(Exception e)
{
var context = HttpContext.Current;
// using.Elmah.ErrorSignal.FromContext(context).Raise(e, context);
}
}
//EJEMPLO:
[Error]
[HandleError]
[PopulateSiteMap(SiteMapName="Mifel1", ViewDataKey="Mifel1")]
public class ApplicationController : Controller
{
}
También se debe tener en cuenta que los errores que no establecen el código de error http a 500
(por ejemplo, UnauthorizedAccessException)
no será manejado por el filtro HandleError.
Te estás perdiendo Error.aspx :) En la vista previa 5, esta se encuentra en tu carpeta Vistas / Compartidas. Solo cópielo de un nuevo proyecto de Vista previa 5.
[HandleError]
public class ErrorController : Controller
{
[AcceptVerbs(HttpVerbs.Get)]
public ViewResult NotAuthorized()
{
//401
Response.StatusCode = (int)HttpStatusCode.Unauthorized;
return View();
}
[AcceptVerbs(HttpVerbs.Get)]
public ViewResult Forbidden()
{
//403
Response.StatusCode = (int)HttpStatusCode.Forbidden;
return View();
}
[AcceptVerbs(HttpVerbs.Get)]
public ViewResult NotFound()
{
//404
Response.StatusCode = (int)HttpStatusCode.NotFound;
return View();
}
public ViewResult ServerError()
{
//500
Response.StatusCode = (int)HttpStatusCode.NotFound;
return View();
}
}
[HandleError]
Cuando proporciona solo el atributo HandleError a su clase (o su método de acción), cuando se produce una excepción no controlada MVC buscará una Vista correspondiente llamada "Error" primero en la carpeta Vista del controlador. Si no puede encontrarlo allí, procederá a buscar en la carpeta Vista compartida (que debería tener un archivo Error.aspx en ella de manera predeterminada)
[HandleError(ExceptionType = typeof(SqlException), View = "DatabaseError")]
[HandleError(ExceptionType = typeof(NullReferenceException), View = "LameErrorHandling")]
También puede apilar atributos adicionales con información específica sobre el tipo de excepción que está buscando. En ese punto, puede dirigir el Error a una vista específica que no sea la vista predeterminada de "Error".
Para obtener más información, eche un vistazo a la publicación del blog de Scott Guthrie al respecto.