Настроить вывод ошибки SpringAecurity OAuth 2 (неавторизованный)

Мы защищаем наши сервисы REST (для связи между сервером и сервером, без участия пользователя) с Spring Security OAuth2. Однако, когда вы пытаетесь получить доступ к защищенному ресурсу в браузере, он будет показывать:

<oauth>
    <error_description>
        An Authentication object was not found in the SecurityContext
    </error_description>
    <error>unauthorized</error>
</oauth>

Мы хотим, чтобы это была настраиваемая страница по собственному выбору. Есть ли способ?

Настройка страницы с запретом доступа не будет выполняться. Для одного это требует определения страницы входа, которой у нас нет, поскольку это чистая связь между сервером и сервером. Для другого этот атрибут предположительно устарел, поскольку Spring 3.0.. или что-то.

В любом случае.. Отладка моего пути в OAuth Error Handling. И обнаружил, что ответ, похоже, каким-то образом обогащается информацией, которую я вижу на странице с ошибкой. По-видимому, никакой рендеринг страниц не производится, поэтому похоже, что на странице ошибки не появляется.?!

По крайней мере, мы хотим скрыть тот факт, что мы используем OAuth и просто отображаем базовый текст "Отказано", если у нас не может быть "реальной" страницы. Поэтому, возможно, мне придется расширить защиту Spring обработчик или добавить настраиваемый фильтр, чтобы изменить ответ?!

Может быть, перенаправление на нашу страницу ошибок?

Спасибо!

Edit

Для нашей текущей настройки проверьте мой другой вопрос SO здесь

Ответ 1

Мне также пришлось удалить деталь oauth, и моим решением было реализовать собственный OAuth2ExceptionRenderer

package org.some.nice.code;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpInputMessage;
import org.springframework.http.HttpOutputMessage;
import org.springframework.http.ResponseEntity;
import org.springframework.http.server.ServerHttpResponse;
import org.springframework.http.server.ServletServerHttpRequest;
import org.springframework.http.server.ServletServerHttpResponse;
import org.springframework.security.oauth2.provider.error.OAuth2ExceptionRenderer;
import org.springframework.web.context.request.NativeWebRequest;
import org.springframework.web.context.request.ServletWebRequest;

public class HeaderOnlyOAuth2ExceptionRenderer implements OAuth2ExceptionRenderer
{
    private final Log logger = LogFactory
            .getLog(MyOAuth2ExceptionRenderer.class);

    public void handleHttpEntityResponse(HttpEntity<?> responseEntity,
            ServletWebRequest webRequest) throws Exception
    {
        if (responseEntity == null)
        {
            return;
        }
        HttpInputMessage inputMessage = createHttpInputMessage(webRequest);
        HttpOutputMessage outputMessage = createHttpOutputMessage(webRequest);
        logger.info("filtering headers only...");
        if (responseEntity instanceof ResponseEntity
                && outputMessage instanceof ServerHttpResponse)
        {
            ((ServerHttpResponse) outputMessage)
                    .setStatusCode(((ResponseEntity<?>) responseEntity)
                            .getStatusCode());
        }
        HttpHeaders entityHeaders = responseEntity.getHeaders();
        if (!entityHeaders.isEmpty())
        {
            outputMessage.getHeaders().putAll(entityHeaders);
        }
    }

    private HttpInputMessage createHttpInputMessage(NativeWebRequest webRequest)
            throws Exception
    {
        HttpServletRequest servletRequest = webRequest
                .getNativeRequest(HttpServletRequest.class);
        return new ServletServerHttpRequest(servletRequest);
    }

    private HttpOutputMessage createHttpOutputMessage(
            NativeWebRequest webRequest) throws Exception
    {
        HttpServletResponse servletResponse = (HttpServletResponse) webRequest
                .getNativeResponse();
        return new ServletServerHttpResponse(servletResponse);
    }
}

Затем вам придется ссылаться на него в контексте spring

     <bean id="oauthAuthenticationEntryPoint" class="org.springframework.security.oauth2.provider.error.OAuth2AuthenticationEntryPoint">
        <property name="realmName" value="theRealm" />
<property name="exceptionRenderer" ref="headerOnlyExceptionRender" />
    </bean>

    <bean id="clientAuthenticationEntryPoint" class="org.springframework.security.oauth2.provider.error.OAuth2AuthenticationEntryPoint">
        <property name="realmName" value="theRealm/client" />
        <property name="typeName" value="Basic" />
<property name="exceptionRenderer" ref="headerOnlyExceptionRender" />
    </bean>



    <bean id="oauthAccessDeniedHandler" class="org.springframework.security.oauth2.provider.error.OAuth2AccessDeniedHandler">
<property name="exceptionRenderer" ref="headerOnlyExceptionRender" />
</bean>


    <bean id="headerOnlyExceptionRender" class="org.some.nice.code.HeaderOnlyOAuth2ExceptionRenderer"/>

Надеюсь, что это поможет.