Сторінка помилки видалення весняного завантаження


156

Я намагаюся видалити сторінку з помилками білої мітки, тому те, що я зробив, було створено контролер, який відображає "/ error",

@RestController
public class IndexController {

    @RequestMapping(value = "/error")
    public String error() {
        return "Error handling";
    }

}

Але тепер я отримую цю помилку.

Exception in thread "AWT-EventQueue-0" org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'requestMappingHandlerMapping' defined in class path resource   [org/springframework/web/servlet/config/annotation/DelegatingWebMvcConfiguration.class]: Invocation  of init method failed; nested exception is java.lang.IllegalStateException: Ambiguous mapping found. Cannot map 'basicErrorController' bean method 
public org.springframework.http.ResponseEntity<java.util.Map<java.lang.String, java.lang.Object>>  org.springframework.boot.autoconfigure.web.BasicErrorController.error(javax.servlet.http.HttpServletR equest)
to {[/error],methods=[],params=[],headers=[],consumes=[],produces=[],custom=[]}: There is already 'indexController' bean method

Не знаю, чи роблю я щось не так. Будь ласка, порадь.

Редагувати:

Уже додано error.whitelabel.enabled=false у файл application.properties, все-таки отримуючи ту ж помилку


1
Подивіться на цей проект github.com/paulc4/mvc-exceptions/blob/master/src/main/java/… , схоже, у них перезавантаження сторінки помилок.
Innot Kauker

Ви пробували налаштування spring.resources.add-mappings=false?
geoand

Дякую за пропозицію, так, все-таки сталася така ж помилка
Yasitha Waduge

Ви просто намагаєтесь повернути якийсь спеціальний вміст, коли /errorвикликається шлях?
geoand

Відповіді:


240

Вам потрібно змінити свій код на наступне:

@RestController
public class IndexController implements ErrorController{

    private static final String PATH = "/error";

    @RequestMapping(value = PATH)
    public String error() {
        return "Error handling";
    }

    @Override
    public String getErrorPath() {
        return PATH;
    }
}

Ваш код не працював, оскільки Spring Boot автоматично реєструє BasicErrorControllerяк Spring Bean, коли ви не вказали реалізацію ErrorController.

Щоб побачити цей факт, просто перейдіть ErrorMvcAutoConfiguration.basicErrorController сюди .


1
Я зіткнувся з тим же самим випуском, я шукав документи Spring, але в ньому не згадувалося BasicErrorController. Це працює :)
Mike R

4
Мені довелося пройти джерело, щоб знайти це :-)
geoand

1
Дякую, працювали чудово! Невелике спостереження, якщо ви можете вказати будь-які вказівки: скажімо, ми потрапили в цей обробник помилок, оскільки в нашому додатку було викинуто виняток (і Spring неявно встановлює код відповіді на 500, що є правильним); чи є тут простий спосіб отримати цей виняток (включити деякі деталі до повідомлення про помилку, що повертається)?
Джонік

1
Радий, що ти вважаєш це корисним! Хоча я ще не пробував цього, я впевнений, що ви можете використовувати принципи, знайдені у Spring Boot's BasicErrorController(див. Github.com/spring-projects/spring-boot/blob/… ), щоб досягти того, що ви хочете
geoand

3
Хм, так, ще раз дякую! Спочатку я не був впевнений, як отримати цей ErrorAttributesоб’єкт (що містить дані про помилку), але потім спробував просто @Autowiring його, і він працює. З чим я пішов зараз: gist.github.com/jonikarppinen/662c38fb57a23de61c8b
Jonik

44

Якщо ви хочете більше "JSONish" сторінки відповідей, ви можете спробувати щось подібне:

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.web.ErrorAttributes;
import org.springframework.boot.autoconfigure.web.ErrorController;
import org.springframework.util.Assert;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.context.request.RequestAttributes;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import java.util.Map;

@RestController
@RequestMapping("/error")
public class SimpleErrorController implements ErrorController {

  private final ErrorAttributes errorAttributes;

  @Autowired
  public SimpleErrorController(ErrorAttributes errorAttributes) {
    Assert.notNull(errorAttributes, "ErrorAttributes must not be null");
    this.errorAttributes = errorAttributes;
  }

  @Override
  public String getErrorPath() {
    return "/error";
  }

  @RequestMapping
  public Map<String, Object> error(HttpServletRequest aRequest){
     Map<String, Object> body = getErrorAttributes(aRequest,getTraceParameter(aRequest));
     String trace = (String) body.get("trace");
     if(trace != null){
       String[] lines = trace.split("\n\t");
       body.put("trace", lines);
     }
     return body;
  }

  private boolean getTraceParameter(HttpServletRequest request) {
    String parameter = request.getParameter("trace");
    if (parameter == null) {
        return false;
    }
    return !"false".equals(parameter.toLowerCase());
  }

  private Map<String, Object> getErrorAttributes(HttpServletRequest aRequest, boolean includeStackTrace) {
    RequestAttributes requestAttributes = new ServletRequestAttributes(aRequest);
    return errorAttributes.getErrorAttributes(requestAttributes, includeStackTrace);
  }
}

7
У Spring-Boot v2 класи ErrorController і ErrorAttributes знаходяться в пакеті org.springframework.boot.web.servlet.error та далі, підпис методу ErrorAttributes # getErrorAttributes змінився, зверніть увагу на залежність від Spring-Boot v1 і, можливо, дайте підказки для v2, Дякую.
chrisinmtown

1
Змінення: приватна карта <String, Object> getErrorAttributes (HttpServletRequest aRequest, boolean includeStackTrace) {RequestAttributes requestAttributes = new ServletRequestAttributes (aRequest); return errorAttributes.getErrorAttributes (requestAttributes, includeStackTrace); } За: приватна карта <String, Object> getErrorAttributes (HttpServletRequest запит, булевий includeStackTrace) {WebRequest webRequest = новий ServletWebRequest (запит); повернути це.errorAttributes.getErrorAttributes (webRequest, includeStackTrace); }
Rija Ramampiandra

2
Оновлену версію SimpleErrorController.java з урахуванням коментарів зверху можна знайти тут> gist.github.com/oscarnevarezleal/…
Оскар Неварес

38

Документ весняного завантаження "помилився (вони з тих пір виправили):

Щоб вимкнути його, ви можете встановити error.whitelabel.enabled = false

має бути

Щоб вимкнути його, ви можете встановити server.error.whitelabel.enabled = false


Це відключить сторінку помилки з білою міткою, але весняне завантаження все /errorодно буде відображати кінцеву точку . Для того, щоб звільнити кінцевої /errorнабір server.error.path=/error-springабо деякий альтернативний шлях.
notes-jj

32

Ви можете видалити його повністю, вказавши:

import org.springframework.context.annotation.Configuration;
import org.springframework.boot.autoconfigure.web.servlet.error.ErrorMvcAutoConfiguration;
...
@Configuration
@EnableAutoConfiguration(exclude = {ErrorMvcAutoConfiguration.class})
public static MainApp { ... }

Однак зауважте, що це, ймовірно, призведе до того, що замість цього з’являться білі мітки контейнера сервлетів :)


EDIT: Ще один спосіб зробити це через application.yaml. Просто введіть значення:

spring:
  autoconfigure:
    exclude: org.springframework.boot.autoconfigure.web.servlet.error.ErrorMvcAutoConfiguration

Документація

Для Spring Boot <2.0 клас знаходиться в пакеті org.springframework.boot.autoconfigure.web.


15

Керівництво тут говорить , що ви повинні встановити server.error.whitelabel.enabledвfalse відключити стандартну сторінку помилки. Може, це те, чого ти хочеш?

Між іншим, ця помилка виникає після додавання / відображення помилок.


Так, я вже встановив error.whitelabel.enabled = помилковий, але все-таки отримую ту ж помилку після відображення / відображення помилок
Yasitha Waduge

Це відключить сторінку помилки з білою міткою, але весняне завантаження все /errorодно буде відображати кінцеву точку . Для того, щоб звільнити кінцевої /errorнабір server.error.path=/error-springабо деякий альтернативний шлях.
notes-jj

11

З Spring Boot> 1.4.x ви можете це зробити:

@SpringBootApplication(exclude = {ErrorMvcAutoConfiguration.class})
public class MyApi {
  public static void main(String[] args) {
    SpringApplication.run(App.class, args);
  }
}

але тоді у випадку винятку контейнер сервлетів відображатиме власну сторінку помилок.


8

Це залежить від вашої версії весняного завантаження:

Коли SpringBootVersion <= 1.2тоді використовуйтеerror.whitelabel.enabled = false

Коли SpringBootVersion > = 1.3тоді використовуйтеserver.error.whitelabel.enabled = false


6

У Spring Boot 1.4.1, використовуючи шаблони вуса, достатньо помістити error.html під папку шаблонів:

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="utf-8">
  <title>Error</title>
</head>

<body>
  <h1>Error {{ status }}</h1>
  <p>{{ error }}</p>
  <p>{{ message }}</p>
  <p>{{ path }}</p>
</body>

</html>

Додаткові змінні можуть бути передані, створивши перехоплювач для /error


Використовуючи цей приклад: github.com/paulc4/mvc-exceptions/blob/master/src/main/resources/…
e-info128

3

Ось альтернативний метод, який дуже схожий на "старий спосіб" вказування відображень помилок у web.xml .

Просто додайте це до конфігурації Spring Boot:

@SpringBootApplication
public class Application implements WebServerFactoryCustomizer<ConfigurableServletWebServerFactory> {

    @Override
    public void customize(ConfigurableServletWebServerFactory factory) {
        factory.addErrorPages(new ErrorPage(HttpStatus.FORBIDDEN, "/errors/403.html"));
        factory.addErrorPages(new ErrorPage(HttpStatus.NOT_FOUND, "/errors/404.html"));
        factory.addErrorPages(new ErrorPage("/errors/500.html"));
    }

}

Тоді ви можете визначити сторінки помилок у статичному вмісті нормально.

За потреби користувачем може бути також окремий @Component.


3

Я використовую Spring Boot версії 2.1.2, і errorAttributes.getErrorAttributes()підпис для мене не працював (у відповідь Акона). Я хотів відповіді типу JSON, тому я трохи копав і виявив, що цей метод робив саме те, що мені потрібно.

Я отримав більшу частину своєї інформації з цієї теми, а також з цієї публікації в блозі .

По-перше, я створив CustomErrorControllerте, що Весна шукатиме для відображення будь-яких помилок.

package com.example.error;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.web.servlet.error.ErrorAttributes;
import org.springframework.boot.web.servlet.error.ErrorController;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.context.request.WebRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.HashMap;
import java.util.Map;

@RestController
public class CustomErrorController implements ErrorController {

    private static final String PATH = "error";

    @Value("${debug}")
    private boolean debug;

    @Autowired
    private ErrorAttributes errorAttributes;

    @RequestMapping(PATH)
    @ResponseBody
    public CustomHttpErrorResponse error(WebRequest request, HttpServletResponse response) {
        return new CustomHttpErrorResponse(response.getStatus(), getErrorAttributes(request));
    }

    public void setErrorAttributes(ErrorAttributes errorAttributes) {
        this.errorAttributes = errorAttributes;
    }

    @Override
    public String getErrorPath() {
        return PATH;
    }

    private Map<String, Object> getErrorAttributes(WebRequest request) {
        Map<String, Object> map = new HashMap<>();
        map.putAll(this.errorAttributes.getErrorAttributes(request, this.debug));
        return map;
    }
}

По-друге, я створив CustomHttpErrorResponseклас, щоб повернути помилку як JSON.

package com.example.error;

import java.util.Map;

public class CustomHttpErrorResponse {

    private Integer status;
    private String path;
    private String errorMessage;
    private String timeStamp;
    private String trace;

    public CustomHttpErrorResponse(int status, Map<String, Object> errorAttributes) {
        this.setStatus(status);
        this.setPath((String) errorAttributes.get("path"));
        this.setErrorMessage((String) errorAttributes.get("message"));
        this.setTimeStamp(errorAttributes.get("timestamp").toString());
        this.setTrace((String) errorAttributes.get("trace"));
    }

    // getters and setters
}

Нарешті, мені довелося вимкнути Whitelabel у application.propertiesфайлі.

server.error.whitelabel.enabled=false

Це навіть має працювати для xmlзапитів / відповідей. Але я цього не перевіряв. Це було саме те, що я шукав, оскільки створив API RESTful і хотів лише повернути JSON.


2

server.error.whitelabel.enabled = false

Додайте вищевказаний рядок до папок Resources application.properties

Більше рішення про помилки див. На веб-сторінці http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#howto-customize-the-whitelabel-error-page


Я спробував application.properties у своїй папці установки, яка нічого не зробила. Папка application.properties в / src / main / ресурси - це те, що намагалася передати suganya sudarsan. Схоже, це "гаряче читання" і в Eclipse.
Річард Бредлі Сміт

1

Я намагався викликати кінцеву точку REST з мікросервісу, і я використовував метод puttemplate put .

У моїй конструкції , якщо сталася якась - або помилка всередині REST кінцевої точки він повинен повернути помилковий відповідь JSON, він працював в протягом декількох викликів , але не для цього поставлених один, він повернув білу сторінку помилки мітки замість цього.

Тому я провів деяке розслідування, і я з’ясував це;

Навесні спробуйте зрозуміти абонента, якщо це машина, тоді він повертає JSON-відповідь або якщо це браузер, ніж він повертає білу сторінку з помилкою HTML- сторінки .

Як результат: моєму клієнтському додатку потрібно було сказати кінцевій точці REST, що абонент - це машина, а не веб-переглядач. Для цього клієнтській програмі потрібно було додати ' application / json чітко " у заголовок ACCEPT для методу "put" решти шаблону. Я додав це до заголовка і вирішив проблему.

мій дзвінок до кінцевої точки:

restTemplate.put(url, request, param1, param2);

для виклику вище мені довелося додати нижче параметр заголовка.

headers.set("Accept", MediaType.APPLICATION_JSON_UTF8_VALUE);

або я намагався змінити також ставити на обмін, і в цьому випадку обмінний дзвінок додав для мене той самий заголовок і вирішив проблему, але я не знаю чому :)

restTemplate.exchange(....)

0

Spring Boot за замовчуванням містить сторінку помилок " whitelabel ", яку ви можете побачити у браузері, якщо ви зіткнулися з помилкою сервера. Сторінка помилок Whitelabel - це загальна сторінка з помилками Spring Boot, яка відображається, коли не знайдена спеціальна сторінка помилок.

Встановіть “server.error.whitelabel.enabled = false” для переключення сторінки помилок за замовчуванням


0

У мене був аналогічний випуск помилки WhiteLabel у моїй кутовій SPA, коли я робив оновлення.

Виправлення полягало в створенні контролера, який реалізує ErrorController, але замість повернення String я повинен був повернути об'єкт ModelAndView, який пересилає до /

@CrossOrigin
@RestController
public class IndexController implements ErrorController {
    
    private static final String PATH = "/error";
    
    @RequestMapping(value = PATH)
    public ModelAndView saveLeadQuery() {           
        return new ModelAndView("forward:/");
    }

    @Override
    public String getErrorPath() {
        return PATH;
    }
}
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.