Как отключить ErrorPageFilter в Spring Загрузка?

Я создаю службу SOAP, которая должна быть запущена на Tomcat.
Я использую Spring Boot для моего приложения, похожее на:

@Configuration
@EnableAutoConfiguration(exclude = ErrorMvcAutoConfiguration.class)
public class AppConfig {
}


Мой веб-сервис (пример):

@Component
@WebService
public class MyWebservice {

    @WebMethod
    @WebResult
    public String test() {
        throw new MyException();
    }
}

@WebFault
public class MyException extends Exception {
}


Проблема:
Всякий раз, когда я вызываю исключение в классе webservice, на сервере регистрируется следующее сообщение:

ErrorPageFilter: не удается переслать страницу с ошибкой для запроса [/services/MyWebservice], поскольку ответ уже сделан. В результате ответ может иметь неправильный код состояния. Если ваш приложение работает на WebSphere Application Server, вы можете для решения этой проблемы путем установки com.ibm.ws.webcontainer.invokeFlushAfterService - false


Вопрос:
Как я могу предотвратить это?

Ответы

Ответ 1

Чтобы отключить ErrorPageFilter в Spring Boot (проверено с 1.3.0.RELEASE), добавьте следующую beans в конфигурацию Spring:

@Bean
public ErrorPageFilter errorPageFilter() {
    return new ErrorPageFilter();
}

@Bean
public FilterRegistrationBean disableSpringBootErrorFilter(ErrorPageFilter filter) {
    FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean();
    filterRegistrationBean.setFilter(filter);
    filterRegistrationBean.setEnabled(false);
    return filterRegistrationBean;
}

Ответ 2

Самый простой способ отключить ErrorPageFilter:

@SpringBootApplication
public class App extends SpringBootServletInitializer {

public App() {
    super();
    setRegisterErrorPageFilter(false); // <- this one
}

@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
    return application.sources(App.class);
}

public static void main(String[] args) {
    SpringApplication.run(App.class, args);
}

Ответ 3

Я нашел в источниках, что ErrorPageFilter.java имеет следующий код:

private void doFilter(HttpServletRequest request, HttpServletResponse response,
        FilterChain chain) throws IOException, ServletException {
    ErrorWrapperResponse wrapped = new ErrorWrapperResponse(response);
    try {
        chain.doFilter(request, wrapped);
        int status = wrapped.getStatus();
        if (status >= 400) {
            handleErrorStatus(request, response, status, wrapped.getMessage());
            response.flushBuffer();
        }
        else if (!request.isAsyncStarted() && !response.isCommitted()) {
            response.flushBuffer();
        }
    }
    catch (Throwable ex) {
        handleException(request, response, wrapped, ex);
        response.flushBuffer();
    }
}

как вы можете видеть, когда вы бросаете исключение и возвращаете код ответa >= 400, он будет выполнять некоторый код. должна быть какая-то дополнительная проверка, если ответ уже был совершен или нет.

Способ удаления ErrorPageFilter выглядит следующим образом

protected WebApplicationContext run(SpringApplication application) {
application.getSources().remove(ErrorPageFilter.class);
return super.run(application);

}

Крис

Ответ 4

    @SpringBootApplication
public class MyApplication extends SpringBootServletInitializer {
    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) {
        //set register error pagefilter false
        setRegisterErrorPageFilter(false);

        builder.sources(MyApplication.class);
        return builder;
    }

}

Ответ 5

public class Application extends SpringBootServletInitializer 
{
   private static final Logger logger = LogManager.getLogger(Application.class);

   public Application()
   {
       super();
       setRegisterErrorPageFilter(false);
   }

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(Application.class);
    }

    public static void main(String[] args) throws Exception {
        SpringApplication.run(Application.class, args);
    }
}