Si coloca el código en PostAuthenticateRequest que puede ser golpeado muchas veces por solicitud como todos los recursos tales como imágenes y estilo las hojas a las que se hace referencia en su página activarán este evento ya que se tratan como solicitudes separadas.
Si elige la respuesta de @ Darin, AuthorizeAttribute no procesará la acción cuando isAuthorized devuelva false, pero las personas pueden necesitar que se represente de todos modos, incluso si es una página pública (acceso no restringido) que desee mostrar un "Nombre para mostrar" guardado en la parte userData del authTicket.
Para ello, recomiendo cargar el authCookie en una ActionFilterAttribute (AuthenticationFilter):
public class LoadCustomAuthTicket : ActionFilterAttribute, IAuthenticationFilter
{
public void OnAuthentication(AuthenticationContext filterContext)
{
if (!filterContext.Principal.Identity.IsAuthenticated)
return;
HttpCookie authCookie = filterContext.HttpContext.Request.Cookies[FormsAuthentication.FormsCookieName];
if (authCookie == null)
return;
FormsAuthenticationTicket authTicket = FormsAuthentication.Decrypt(authCookie.Value);
var identity = new GenericIdentity(authTicket.Name, "Forms");
var principal = new GenericPrincipal(identity, new string[] { });
// Make sure the Principal's are in sync. see: https://www.hanselman.com/blog/SystemThreadingThreadCurrentPrincipalVsSystemWebHttpContextCurrentUserOrWhyFormsAuthenticationCanBeSubtle.aspx
filterContext.Principal = filterContext.HttpContext.User = System.Threading.Thread.CurrentPrincipal = principal;
}
public void OnAuthenticationChallenge(AuthenticationChallengeContext filterContext)
{
//This method is responsible for validating the current principal and permitting the execution of the current action/request.
//Here you should validate if the current principle is valid/permitted to invoke the current action. (However I would place this logic to an authorization filter)
//filterContext.Result = new RedirectToRouteResult("CustomErrorPage",null);
}
}
Y en global.asax.cs
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
filters.Add(new LoadCustomAuthTicket());
}
De esa manera también no tendrá que llenar todas tus acciones con el atributo.
¿Por qué recomienda aplicar filtros en todos los controladores, cuando parece mucho más limpio tener el cambio en un solo lugar en el controlador de eventos? ¿Cuál es la ganancia? –
Para este ejemplo, probablemente tendría más sentido reemplazar var identity = new GenericIdentity (authTicket.Name, "Forms"); con var identity = new FormsIdentity (authTicket); –
@zespri El evento PostAuthenticateRequest se puede llamar varias veces por página. El uso de un atributo de autorización personalizado garantiza que su código solo se llame una vez por solicitud. – Mark