Я бы хотел, чтобы [Authorize]
перенаправлял loginUrl, если я также не использую роль, например [Authorize (Roles="Admin")]
. В этом случае я хочу просто показать страницу, в которой пользователь не авторизовался.
Что мне делать?
Я бы хотел, чтобы [Authorize]
перенаправлял loginUrl, если я также не использую роль, например [Authorize (Roles="Admin")]
. В этом случае я хочу просто показать страницу, в которой пользователь не авторизовался.
Что мне делать?
Вот код из моей модифицированной реализации AuthorizeAttribute
; Я назвал его SecurityAttribute
. Единственное, что я изменил, это метод OnAuthorization
, и я добавил дополнительное свойство строки для перенаправления Url на страницу Unauthorized:
// Set default Unauthorized Page Url here
private string _notifyUrl = "/Error/Unauthorized";
public string NotifyUrl {
get { return _notifyUrl; } set { _notifyUrl = value; }
}
public override void OnAuthorization(AuthorizationContext filterContext) {
if (filterContext == null) {
throw new ArgumentNullException("filterContext");
}
if (AuthorizeCore(filterContext.HttpContext)) {
HttpCachePolicyBase cachePolicy =
filterContext.HttpContext.Response.Cache;
cachePolicy.SetProxyMaxAge(new TimeSpan(0));
cachePolicy.AddValidationCallback(CacheValidateHandler, null);
}
/// This code added to support custom Unauthorized pages.
else if (filterContext.HttpContext.User.Identity.IsAuthenticated)
{
if (NotifyUrl != null)
filterContext.Result = new RedirectResult(NotifyUrl);
else
// Redirect to Login page.
HandleUnauthorizedRequest(filterContext);
}
/// End of additional code
else
{
// Redirect to Login page.
HandleUnauthorizedRequest(filterContext);
}
}
Вы вызываете его так же, как оригинал AuthorizeAttribute
, за исключением того, что существует дополнительное свойство для переопределения Unauthorized Page Url:
// Use custom Unauthorized page:
[Security (Roles="Admin, User", NotifyUrl="/UnauthorizedPage")]
// Use default Unauthorized page:
[Security (Roles="Admin, User")]
Расширьте класс AuthorizeAttribute
и переопределите HandleUnauthorizedRequest
public class RoleAuthorizeAttribute : AuthorizeAttribute
{
private string redirectUrl = "";
public RoleAuthorizeAttribute() : base()
{
}
public RoleAuthorizeAttribute(string redirectUrl) : base()
{
this.redirectUrl = redirectUrl;
}
protected override void HandleUnauthorizedRequest(AuthorizationContext filterContext)
{
if (filterContext.HttpContext.Request.IsAuthenticated)
{
string authUrl = this.redirectUrl; //passed from attribute
//if null, get it from config
if (String.IsNullOrEmpty(authUrl))
authUrl = System.Web.Configuration.WebConfigurationManager.AppSettings["RolesAuthRedirectUrl"];
if (!String.IsNullOrEmpty(authUrl))
filterContext.HttpContext.Response.Redirect(authUrl);
}
//else do normal process
base.HandleUnauthorizedRequest(filterContext);
}
}
Использование
[RoleAuthorize(Roles = "Admin, Editor")]
public class AccountController : Controller
{
}
И убедитесь, что вы добавили запись AppSettings в конфигурацию
<appSettings>
<add key="RolesAuthRedirectUrl" value="http://mysite/myauthorizedpage" />
</appSettings>
Самый простой способ, который я нашел, - расширить и настроить атрибут AuthorizeAttribute, чтобы он делал что-то другое (т.е. не задавал HttpUnauthorizedResult), когда проверка роли не удалась. Я написал статью об этом в своем блоге, который может вам пригодиться. В статье описывается то, что вы хотите, хотя оно идет дальше и позволяет пользователю, который "владеет" данными, также иметь доступ к действию. Я думаю, что это довольно легко изменить для ваших целей - вам просто нужно удалить часть "или владельца".