Я использую Authorize
припишите как это:
[Authorize (Roles="Admin, User")]
Public ActionResult Index(int id)
{
// blah
}
Когда пользователь не находится в указанных ролях, я получаю ошибочную страницу (ресурс, не найденный). Таким образом, я поместил HandleError
атрибут в также.
[Authorize (Roles="Admin, User"), HandleError]
Public ActionResult Index(int id)
{
// blah
}
Теперь это переходит к Странице входа в систему, если пользователь не находится в указанных ролях.
Как я заставляю это переходить к странице Unauthorized вместо страницы входа в систему, когда пользователь не встречает одну из необходимых ролей? И если другая ошибка происходит, как я отличаю ту ошибку от Несанкционированной ошибки и обрабатываю ее по-другому?
Добавьте что-то вроде этого в ваш web.config:
<customErrors mode="On" defaultRedirect="~/Login">
<error statusCode="401" redirect="~/Unauthorized" />
<error statusCode="404" redirect="~/PageNotFound" />
</customErrors>
Вы, очевидно, должны создать /PageNotFound
и /Unauthorized
маршруты, действия и представления.
EDIT: Извините, я, видимо, не до конца понял суть проблемы.
Проблема в том, что когда выполняется фильтр AuthorizeAttribute
, он решает, что пользователь не соответствует требованиям (он/она может быть залогинен, но не в правильной роли). Поэтому он устанавливает код состояния ответа на 401. Это перехватывается модулем FormsAuthentication
, который затем выполняет перенаправление.
Я вижу две альтернативы:
Отключить defaultRedirect.
Создать свой собственный IAuthorizationFilter
. Производное от AuthorizeAttribute
и переопределите HandleUnauthorizedRequest. В этом методе, если пользователь аутентифицирован, сделайте перенаправление на /Unauthorized
Мне не нравится ни то, ни другое: функциональность defaultRedirect хороша, но это не то, что вы хотите реализовать самостоятельно. Второй подход приводит к тому, что пользователю будет показана визуально корректная страница "Вы не авторизованы", но коды состояния HTTP не будут соответствовать желаемому 401.
Я не знаю достаточно о HttpModules, чтобы сказать, можно ли обойти это с помощью сносного хака.
EDIT 2: Как насчет реализации собственного IAuthorizationFilter следующим образом: скачайте код MVC2 с CodePlex и "позаимствуйте" код для AuthorizeAttribute. Измените метод OnAuthorization на следующий
public virtual void OnAuthorization(AuthorizationContext filterContext)
{
if (AuthorizeCore(filterContext.HttpContext))
{
HttpCachePolicyBase cachePolicy = filterContext.HttpContext.Response.Cache;
cachePolicy.SetProxyMaxAge(new TimeSpan(0));
cachePolicy.AddValidationCallback(CacheValidateHandler, null /* data */);
}
// Is user logged in?
else if(filterContext.HttpContext.User.Identity.IsAuthenticated)
{
// Redirect to custom Unauthorized page
filterContext.Result = new RedirectResult(unauthorizedUrl);
}
else {
// Handle in the usual way
HandleUnauthorizedRequest(filterContext);
}
}
где unauthorizedUrl
является либо свойством фильтра, либо считывается из Web.config.
Можно также наследоваться от AuthorizeAttribute и переопределить OnAuthorization
, но в итоге придется написать пару приватных методов, которые уже есть в AuthorizeAttribute.
И HttpUnauthorizedResult
(это повторное использование AuthorizeAtrribute
) просто устанавливает StatusCode равным 401. Так что, вероятно, вы можете настроить страницу 401 в IIS или настраиваемые страницы ошибок в web.config. Конечно, вы также должны убедиться, что для доступа к вашей настраиваемой странице ошибок не требуется авторизация.
В Ruby и Perl 6 это было названо «splat», и я думаю, что большинство людей из этих сообществ поймут, что вы имеете в виду, если вы назовете это так.
В руководстве Python используется фраза «распаковка перечислять аргументов», которая является длинной и описательной. Я не слышал никакого другого конкретного имени в Пайтоне.
-121--622556- Единственный раз, когда я знаю, что вы должны вручную поднять StopIteration
, это когда вы реализуете метод next ()
в классе, чтобы сообщить, что итератор завершен. Для генераторов (функции с выдают
операторов в них) конец функции или оператор возврата
правильно инициирует StopIteration
для вас.
Это можно сделать двумя способами:
Укажите ошибку в атрибуте HandleError и задайте представление, которое должно отображаться:
[HandleError (ExcepityType = тип (UnAuthorizedException), Представление = «UnauthorizedError»)]
Вы можете определить несколько различных ExceptionTypes, и взгляды