атрибут для метода действия контроллера .net MVC

По существу я хочу показать дружественное сообщение, когда кто-то не часть роли, перечисленной в моем атрибуте. В настоящее время мое приложение просто плюется пользователем назад к журналу на экране. Я прочитал несколько сообщений, которые говорят о создании пользовательского атрибута, который просто расширяется [AuthorizeAttribute], но я думаю, там получен, чтобы быть чем-то из поля, чтобы сделать это?

кто-то может указать на меня в правильном направлении того, где я должен надеяться не иметь его, отправляют пользователя в журнал в форме, а скорее просто стреляют в них "не авторизованное" сообщение?

8
задан Kyle 7 January 2010 в 18:25
поделиться

4 ответа

Если простота или полный контроль над логикой - это то, что вы хотите, вы можете назвать это в вашем методе действия:

User.IsInRole("NameOfRole");

Он возвращает bool, и вы можете делать остальную часть вашей логики в зависимости от этого результата.

Другой, который я использовал в некоторых случаях:

System.Web.Security.Roles.GetRolesForUser();

Я думаю, что он возвращает строку[], но не цитируйте меня по этому поводу.

EDIT: Пример всегда помогает...

public ActionResult AddUser()
{
    if(User.IsInRoles("SuperUser")
    {
        return View("AddUser");
    }
    else
    {
        return View("SorryWrongRole");
    }
}

Пока вашим типом возврата является "ActionResult", вы можете вернуть любой из принятых типов возврата (ViewResult, PartialViewResult, RedirectResult, JsonResult...)

.
2
ответ дан 5 December 2019 в 12:58
поделиться

Я столкнулся с этой проблемой несколько дней назад, и решение немного детализировано, но вот важные биты. В AuthorizeAttribute метод OnAuthorization возвращает HttpUnauthorizedResult при неудачной авторизации, что немного затрудняет возврат пользовательского результата.

В итоге я создал класс CustomAuthorizeAttribute и переопределил метод OnAuthorization, чтобы вместо этого бросить исключение. Затем я могу поймать это исключение с помощью пользовательского обработчика ошибок и вместо возврата 401 (Unauthorized) отобразить пользовательскую страницу ошибки.

public class CustomAuthorizeAttribute : AuthorizeAttribute
{
    public virtual 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 /* data */);
        }
        else {
            // auth failed, redirect to login page
            // filterContext.Result = new HttpUnauthorizedResult();

            throw new HttpException ((int)HttpStatusCode.Unauthorized, "Unauthorized");                
        }
    }
}

Затем в web.config вы можете настроить пользовательские обработчики для конкретных ошибок:

    <customErrors mode="On" defaultRedirect="~/Error">
        <error statusCode="401" redirect="~/Error/Unauthorized" />
        <error statusCode="404" redirect="~/Error/NotFound" />
    </customErrors>

и затем реализовать свой собственный ErrorController для обслуживания пользовательских страниц.

На IIS7 вам нужно посмотреть в настройках Response.TrySkipIisCustomErrors = true;, чтобы активировать пользовательские ошибки.

.
3
ответ дан 5 December 2019 в 12:58
поделиться

Нестандартное поведение заключается в том, что атрибут [Авторизовать] возвращает HTTP 401. Модуль FormsAuthenticationModule (который загружается по умолчанию) перехватывает этот 401 и перенаправляет пользователя на страницу входа. Взгляните на System.Web.Security.FormsAuthenticationModule::OnLeave in Reflector, чтобы понять, что я имею в виду.

Если Вы хотите, чтобы AuthorizeAttribute сделал что-то другое , чем возвратил HTTP 401, Вам нужно будет переопределить метод AuthorizeAttribute::HandleUnauthorizedRequest и выполнить там Вашу пользовательскую логику. Или просто измените эту часть ~\Web.config:

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

И укажите на другой URL, например ~/AccessDenied.

.
0
ответ дан 5 December 2019 в 12:58
поделиться

Возможно, я немного опоздал с добавлением своих $0,02, но когда вы создаете свой CustomAuthorizationAttribue, вы можете использовать свойство AuthorizationContext.Result, чтобы указать, где метод AuthorizeAttribute.HandleUnauthorizedRequest направляет пользователя.

Вот очень простой пример, который позволяет вам указать URL, куда должен быть перенаправлен пользователь после неудачной авторизации:

public class Authorize2Attribute : AuthorizeAttribute
{
    // Properties

    public String RedirectResultUrl { get; set; }

    // Constructors

    public Authorize2Attribute()
        : base()
    {
    }

    // Overrides

    protected override void HandleUnauthorizedRequest(AuthorizationContext filterContext)
    {
        if (String.IsNullOrEmpty(RedirectResultUrl))
            base.HandleUnauthorizedRequest(filterContext);

        else
            filterContext.Result = new RedirectResult(RedirectResultUrl);
    }
}

И если я хочу перенаправить пользователя на /Error/Unauthorized, как было предложено в предыдущем посте:

[Authorize2(Roles = "AuthorizedUsers", RedirectResultUrl = "/Error/Unauthorized")]
public ActionResult RestrictedAction()
{
    // TODO: ...
}
6
ответ дан 5 December 2019 в 12:58
поделиться
Другие вопросы по тегам:

Похожие вопросы: