Как прервать 401 от Аутентификации Форм в ASP.NET MVC?

Я хотел бы генерировать 401 страницу, если у пользователя нет правильного разрешения.

Пользователь запрашивает URL и перенаправляется к странице входа в систему (я имею, отклоняют всех анонимных в web.config). Пользователь входит в систему успешно и перенаправляется к исходному URL. Однако после проверки разрешения, определено, что у пользователя нет необходимого разрешения, таким образом, я хотел бы генерировать 401. Но Аутентификация Форм всегда обрабатывает 401 и перенаправляет пользователя к странице входа в систему.

Мне это не корректно. Пользователь уже прошел проверку подлинности, у пользователя просто нет соответствующих полномочий.

В других сценариях, такой как в ajax или сервисном сценарии REST, я определенно не хочу страницу входа в систему - мне нужна надлежащая 401 страница.

До сих пор я попробовал пользовательский, Разрешают фильтр возвращать ViewResult с 401, но не работал. Я затем попробовал нормальный Фильтр Действия, переопределив OnActionExecuting, который не работал также.

То, что я смог сделать, обработать событие в global.asax, PostRequestHandlerExecute, и проверка на разрешение затем выписывает непосредственно к ответу:

if (permissionDenied)
{
    Context.Response.StatusCode = 401;
    Context.Response.Clear();
    Context.Response.Write("Permission Denied");
    Context.Response.Flush();
    Context.Response.Close();
    return;
}

Это работает, но это не действительно, что я хочу. В первую очередь, я даже не уверен - ли это правильное событие или место в конвейере, чтобы сделать это. Во-вторых, я хочу, чтобы 401 страница имела немного больше содержания. Предпочтительно, это должна быть aspx страница с возможно той же основной страницей как остальная часть сайта. Тем путем любой просматривающий сайт видит, что разрешение отклонено, но с тем же стилем, и т.д. но ajax или пользователь услуги заставят надлежащий код состояния действовать на.

Какая-либо идея, как это может быть достигнуто? Я видел другие сообщения с подобными запросами, но не видел решения, которое я могу использовать.

И не, я не хочу 403.

14
задан Jiho Han 28 May 2010 в 19:05
поделиться

3 ответа

Я нашел работоспособное решение.

401 редирект по FormsAuthenticationModule происходит во время EndRequest. Поскольку при обработке событий модули вызываются до global.asax, мы можем переопределить код состояния после того, как FormsAuthenticationModule наложил свои грязные руки на запрос.

В моем пользовательском AuthorizationFilter я устанавливаю HttpContext.Items["PermissionDenied"] в true, а затем в global.asax EndRequest я меняю код состояния с 200 на 401. Затем я Server.Transfer к моему пользовательскому представлению PermissionDenied.

Я бы все еще предпочел, чтобы FormsAuthenticationModule сам был обновлен для обработки этого сценария, но я думаю, что это не слишком хакерский подход, и я думаю, что смогу с этим жить.

Очевидно, вы можете изменить способ подачи сигнала о том, что global.asax должен перевернуть код состояния. Я только что попробовал установить код состояния на что-то вроде 511 и использовать это в качестве условия, а не HttpContext.Items, и это тоже сработало. Думаю, пока правильный код состояния выходит за дверь, движку ASP.NET все равно.

8
ответ дан 1 December 2019 в 13:58
поделиться

Я согласен, что поведение по умолчанию неверно, особенно с учетом запросов Ajax. Надеюсь увидеть какое-то решение в MVCv3 (скрестив пальцы).

Единственный известный мне способ сделать это - удалить раздел Authentication из web.config, это то, что ASP.NET ищет для перенаправления неавторизованных запросов. Насколько мне известно, вы не можете отключить эту "функцию". Если у вас есть раздел аутентификации, вы будете перенаправлены на URL-адрес входа, если ASP.NET когда-либо встретит код состояния 401 .

Но, удалив это, у вас возникнут другие проблемы. Если вы когда-нибудь захотите, чтобы пользователь был перенаправлен на страницу входа в систему для запросов, отличных от ajax, вам нужно будет реализовать свой собственный AuthorizeAttribute и использовать пользовательские настройки, чтобы определить, куда перенаправить. Кроме того, вам, вероятно, придется заново реализовать что-либо еще в разделе «Аутентификация». Не очень практичное решение для сложных сайтов.

Я не делал этого сам, я решил вернуть вместо этого 403 . Раздражает отсутствие возврата правильного HttpCode, но это лучше, чем любое другое решение, которое я нашел до сих пор.

2
ответ дан 1 December 2019 в 13:58
поделиться

Вы можете посмотреть здесь: Пользовательская обработка ошибок ASP.NET MVC Application_Error Global.asax?

У вас должна быть возможность поймать 401 и перейти к настраиваемому действию на этот момент. Мы делаем это для 404 и других исключений в нашем коде, и это работает довольно хорошо.

0
ответ дан 1 December 2019 в 13:58
поделиться
Другие вопросы по тегам:

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